Add ROS Level 2 RTT Test

A new Level 2 ROS test is defined, that is similar to the DDS loopback test
and can be used to measure the round trip time between a server and a client.
L2_Testbench_ROS_Lib6 is the server implementation, while L2_Testbench_ROS_Lib7
is the client implementation.
A custom (ROS) type is also defined (Type1).
Read the comments in L2_ROS_Loopback_test1 for implementation details.
This commit is contained in:
John Ring 2023-07-22 14:48:14 +02:00
parent a1e0297fcb
commit c667c6ed5e
13 changed files with 3038 additions and 1 deletions

View File

@ -0,0 +1,124 @@
onerror {resume}
radix define ROS_RETCODE {
"10#0#" "ROS_RET_OK",
"10#1#" "ROS_RET_ERROR",
"10#2#" "ROS_RET_TIMEOUT",
"10#3#" "ROS_RET_UNSUPPORTED",
"10#10#" "ROS_RET_BAD_ALLOC",
"10#11#" "ROS_RET_INVALID_ARGUMENT",
"10#12#" "ROS_RET_INCORRECT_RMW_IMPLEMENTATION",
"10#100#" "ROS_RET_ALREADY_INIT",
"10#101#" "ROS_RET_NOT_INIT",
"10#102#" "ROS_RET_MISMATCHED_RMW",
"10#103#" "ROS_RET_TOPIC_NAME_INVALID",
"10#104#" "ROS_RET_SERVICE_NAME_INVALID",
"10#105#" "ROS_RET_UNKNOWN_SUBSTITUTION",
"10#106#" "ROS_RET_ALREADY_SHUTDOWN",
"10#200#" "ROS_RET_NODE_INVALID",
"10#201#" "ROS_RET_NODE_INVALID_NAME",
"10#202#" "ROS_RET_NODE_INVALID_NAMESPACE",
"10#203#" "ROS_RET_NODE_NAME_NON_EXISTENT",
"10#400#" "ROS_RET_SUBSCRIPTION_INVALID",
"10#401#" "ROS_RET_SUBSCRIPTION_TAKE_FAILED",
"10#500#" "ROS_RET_CLIENT_INVALID",
"10#501#" "ROS_RET_CLIENT_TAKE_FAILED",
"10#600#" "ROS_RET_SERVICE_INVALID",
"10#601#" "ROS_RET_SERVICE_TAKE_FAILED",
"10#800#" "ROS_RET_TIMER_INVALID",
"10#801#" "ROS_RET_TIMER_CANCELED",
"10#900#" "ROS_RET_WAIT_SET_INVALID",
"10#901#" "ROS_RET_WAIT_SET_EMPTY",
"10#902#" "ROS_RET_WAIT_SET_FULL",
"10#1001#" "ROS_RET_INVALID_REMAP_RULE",
"10#1002#" "ROS_RET_WRONG_LEXEME",
"10#1003#" "ROS_RET_INVALID_ROS_ARGS",
"10#1010#" "ROS_RET_INVALID_PARAM_RULE",
"10#1020#" "ROS_RET_INVALID_LOG_LEVEL_RULE",
"10#2001#" "ROS_RET_EVENT_TAKE_FAILED",
"10#2000#" "ROS_RET_ACTION_NAME_INVALID",
"10#2100#" "ROS_RET_ACTION_GOAL_ACCEPTED",
"10#2101#" "ROS_RET_ACTION_GOAL_REJECTED",
"10#2102#" "ROS_RET_ACTION_CLIENT_INVALID",
"10#2103#" "ROS_RET_ACTION_CLIENT_TAKE_FAILED",
"10#2200#" "ROS_RET_ACTION_SERVER_INVALID",
"10#2201#" "ROS_RET_ACTION_SERVER_TAKE_FAILED",
"10#2300#" "ROS_RET_ACTION_GOAL_HANDLE_INVALID",
"10#2301#" "ROS_RET_ACTION_GOAL_EVENT_INVALID",
"10#3000#" "ROS_RET_LIFECYCLE_STATE_REGISTERED",
"10#3001#" "ROS_RET_LIFECYCLE_STATE_NOT_REGISTERED",
-default unsigned
}
radix define GOAL_STATUS {
"10#0#" "STATUS_UNKNOWN",
"10#1#" "STATUS_ACCEPTED",
"10#2#" "STATUS_EXECUTING",
"10#3#" "STATUS_CANCELING",
"10#4#" "STATUS_SUCCEEDED",
"10#5#" "STATUS_CANCELED",
"10#6#" "STATUS_ABORTED",
-default unsigned
}
quietly WaveActivateNextPane {} 0
add wave -noupdate -divider SYSTEM
add wave -noupdate /l2_ros_loopback_test1/clk
add wave -noupdate /l2_ros_loopback_test1/reset
add wave -noupdate -divider {Lib7 ROS Publish}
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/start_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/opcode_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/ack_user
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/id
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/a
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/done_user
add wave -noupdate -radix ROS_RETCODE /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/return_code_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_pub_inst/stage
add wave -noupdate -divider {Lib6 ROS Subscriber}
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/start_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/opcode_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/ack_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/done_user
add wave -noupdate -radix ROS_RETCODE /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/return_code_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/data_available_user
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/id
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/a
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/message_info_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/taken_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_sub_inst/stage
add wave -noupdate -divider {Lib6 ROS Publisher}
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/start_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/opcode_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/ack_user
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/id
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/a
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/done_user
add wave -noupdate -radix ROS_RETCODE /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/return_code_user
add wave -noupdate /l2_ros_loopback_test1/Lib6_inst/Type1_ros_pub_inst/stage
add wave -noupdate -divider {Lib7 ROS Subscribe}
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/start_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/opcode_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/ack_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/done_user
add wave -noupdate -radix ROS_RETCODE /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/return_code_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/data_available_user
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/id
add wave -noupdate -radix unsigned /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/a
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/message_info_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/taken_user
add wave -noupdate /l2_ros_loopback_test1/Lib7_inst/Type1_ros_sub_inst/stage
TreeUpdate [SetDefaultTree]
WaveRestoreCursors {{Cursor 1} {2981796 ps} 0}
quietly wave cursor active 1
configure wave -namecolwidth 150
configure wave -valuecolwidth 100
configure wave -justifyvalue left
configure wave -signalnamewidth 1
configure wave -snapdistance 10
configure wave -datasetprefix 0
configure wave -rowmargin 4
configure wave -childrowmargin 2
configure wave -gridoffset 0
configure wave -gridperiod 1
configure wave -griddelta 40
configure wave -timeline 0
configure wave -timelineunits ns
update
WaveRestoreZoom {0 ps} {2042496 ps}

View File

@ -28,6 +28,8 @@ Testbench_ROS_Lib2 = /tmp/sim_temp/VHDL_LIBS/ModelSim-2020.02/Testbench_ROS_Lib2
Testbench_ROS_Lib3 = /tmp/sim_temp/VHDL_LIBS/ModelSim-2020.02/Testbench_ROS_Lib3.lib
Testbench_ROS_Lib4 = /tmp/sim_temp/VHDL_LIBS/ModelSim-2020.02/Testbench_ROS_Lib4.lib
Testbench_ROS_Lib5 = /tmp/sim_temp/VHDL_LIBS/ModelSim-2020.02/Testbench_ROS_Lib5.lib
Testbench_ROS_Lib6 = /tmp/sim_temp/VHDL_LIBS/ModelSim-2020.02/Testbench_ROS_Lib6.lib
Testbench_ROS_Lib7 = /tmp/sim_temp/VHDL_LIBS/ModelSim-2020.02/Testbench_ROS_Lib7.lib
[vcom]
; VHDL93 variable selects language version as the default.
; Default is VHDL-2002.

View File

@ -0,0 +1,300 @@
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library osvvm; -- Utility Library
context osvvm.OsvvmContext;
library Testbench_ROS_Lib6;
library Testbench_ROS_Lib7;
use work.rtps_package.all;
use work.ros_package.all;
use work.rtps_test_package.all;
-- This testbench tests a loopback application in ROS and can be used to measure the Round Trip Time (RTT) of messages between a client and server.
-- The client writes messages to the server, and the server "mirrors" this messages back to the client.
-- The server also instantiates moving_averages for the current utilization of the input & output FIFOs, and sends them periodically to the client.
-- The client and server implementations are put in different Libraries(Testbench_ROS_Lib6 for server and Testbench_ROS_Lib7 for client).
-- This testbench directly interfaces Testbench_ROS_Lib7 and implements the client logic.
-- Because ROS does not use keyed Topics, 2 Topics are defined for the intercommunication:
-- * rt/Loopback_1 client->server
-- * rt/Loopback_2 server->client
-- A custom type containing an id and an integer (a) is used for the communication. The id differentiates what 'a' is containing:
-- * ID=1: 'a' contains the ID of the sent message by the client. The ID (in 'a') is a incrementing counter of sent messages.
-- * ID=2: 'a' contains the ID of the sent message by the server. The ID (in 'a') is the same ID contained in the message received from the client (Message with ID=1)
-- * ID=3: 'a' contains the average number of free slots in the input FIFO of the server implementation, and can be used to calculate the average FIFO utilization.
-- * ID=4: 'a' contains the average number of free slots in the output FIFO of the server implementation, and can be used to calculate the average FIFO utilization.
-- The client/testbench sends 5 messages to the server and checks the expected contents of the messages sent by the server.
entity L2_ROS_Loopback_test1 is
end entity;
architecture testbench of L2_ROS_Loopback_test1 is
signal clk, reset : std_logic := '0';
signal time : TIME_TYPE := TIME_ZERO;
signal empty_l6, empty_l7, read_l6, read_l7, full_l6, full_l7, write_l6, write_l7 : std_logic := '0';
signal data_in_l6, data_in_l7, data_out_l6, data_out_l7 : std_logic_vector(WORD_WIDTH-1 downto 0) := (others => '0');
signal input_util, output_util : std_logic_vector(WORD_WIDTH-1 downto 0) := (others => '0');
signal start_r, ack_r, done_r, data_available_r, taken_r, start_w, ack_w, done_w : std_logic := '0';
signal opcode_r, opcode_w : ROS_TOPIC_OPCODE_TYPE := NOP;
signal id_r, a_r, id_w, a_w : std_logic_vector(CDR_LONG_WIDTH-1 downto 0) := (others => '0');
signal message_info_r : Testbench_ROS_Lib7.ros_package.MESSAGE_INFO_TYPE := Testbench_ROS_Lib7.ros_package.EMPTY_MESSAGE_INFO;
signal return_code_r, return_code_w : std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0);
shared variable SB : osvvm.ScoreBoardPkg_slv.ScoreBoardPType;
signal write_done : std_logic := '0';
-- HACK: For some reason (possibly Modelsim/Questasim Bug) I cannot declare the opcode signals from their respective Library sources,
-- because I cannot use a qualified expression to define an enumeration literal (and direct type casting cannot be done because
-- the types are not closely related). So I have to do define explicit type conversions between the types...
function to_Lib7(input : ROS_TOPIC_OPCODE_TYPE) return Testbench_ROS_Lib7.ros_package.ROS_TOPIC_OPCODE_TYPE is
begin
return Testbench_ROS_Lib7.ros_package.ROS_TOPIC_OPCODE_TYPE'VAL(ROS_TOPIC_OPCODE_TYPE'POS(input));
end function;
-- Waits until signal toggles high for at least 1 ps
procedure wait_on_sig(signal sig : std_logic) is
begin
loop
if (sig /= '1') then
wait on sig until sig = '1';
end if;
-- Prevent triggering on glitches
wait for 1 ps;
if (sig = '1') then
exit;
end if;
end loop;
end procedure;
procedure wait_clock(num : in natural := 1) is
begin
assert (num > 0) report "Num has to be > 0" severity FAILURE;
for i in 0 to num-1 loop
wait until rising_edge(clk);
end loop;
end procedure;
begin
Lib6_inst : entity Testbench_ROS_Lib6.L2_Testbench_ROS_Lib6(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => Testbench_ROS_Lib6.rtps_package.TIME_TYPE(time),
-- UTILIZATION
input_util => input_util,
output_util => output_util,
-- INPUT
empty => empty_l6,
read => read_l6,
data_in => data_in_l6,
-- OUTPUT
full => full_l6,
write => write_l6,
data_out => data_out_l6
);
fifo_l6_l7_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 65536/(WORD_WIDTH/BYTE_WIDTH),
DATA_WIDTH => WORD_WIDTH
)
port map
(
clk => clk,
reset => reset,
empty => empty_l7,
read => read_l7,
data_out => data_in_l7,
full => full_l6,
write => write_l6,
data_in => data_out_l6,
free => open
);
fifo_l7_l6_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 65536/(WORD_WIDTH/BYTE_WIDTH),
DATA_WIDTH => WORD_WIDTH
)
port map
(
clk => clk,
reset => reset,
empty => empty_l6,
read => read_l6,
data_out => data_in_l6,
full => full_l7,
write => write_l7,
data_in => data_out_l7,
free => open
);
Lib7_inst : entity Testbench_ROS_Lib7.L2_Testbench_ROS_Lib7(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => Testbench_ROS_Lib7.rtps_package.TIME_TYPE(time),
-- INPUT
empty => empty_l7,
read => read_l7,
data_in => data_in_l7,
-- OUTPUT
full => full_l7,
write => write_l7,
data_out => data_out_l7,
-- READER
start_r => start_r,
opcode_r => to_Lib7(opcode_r),
ack_r => ack_r,
done_r => done_r,
return_code_r => return_code_r,
data_available_r => data_available_r,
id_r => id_r,
a_r => a_r,
message_info_r => message_info_r,
taken_r => taken_r,
-- WRITER
start_w => start_w,
opcode_w => to_Lib7(opcode_w),
ack_w => ack_w,
id_w => id_w,
a_w => a_w,
done_w => done_w,
return_code_w => return_code_w
);
stimulus_prc : process
variable RV : RandomPType;
begin
SetAlertLogName("L2_ROS_Loopback_test1 - Loopback");
SetAlertEnable(FAILURE, TRUE);
SetAlertEnable(ERROR, TRUE);
SetAlertEnable(WARNING, TRUE);
SetLogEnable(DEBUG, FALSE);
SetLogEnable(PASSED, FALSE);
SetLogEnable(INFO, TRUE);
RV.InitSeed(RV'instance_name);
Log("Initial Reset", INFO);
reset <= '1';
wait_clock(2);
reset <= '0';
wait_on_sig(write_done);
while not SB.empty loop
wait_clock;
end loop;
TranscriptOpen(RESULTS_FILE, APPEND_MODE);
SetTranscriptMirror;
ReportAlerts;
TranscriptClose;
std.env.stop;
wait;
end process;
write_prc : process
begin
start_w <= '0';
opcode_w <= NOP;
id_w <= int(1,CDR_LONG_WIDTH);
a_w <= (others => '0');
write_done <= '0';
wait until falling_edge(reset);
Log("Begin Publishing Samples", INFO);
for i in 1 to 5 loop
Log("Publish Sample " & integer'image(i), INFO);
start_w <= '1';
opcode_w <= PUBLISH;
a_w <= int(i,CDR_LONG_WIDTH);
wait_on_sig(ack_w);
wait_clock;
start_w <= '0';
SB.push(a_w);
wait_on_sig(done_w);
AlertIf(return_code_w /= RETCODE_OK, "Publish Operation Failed", FAILURE);
wait_clock;
end loop;
Log("DONE Publishing Samples", INFO);
write_done <= '1';
wait;
end process;
read_prc : process
begin
start_r <= '0';
opcode_r <= NOP;
wait_on_sig(data_available_r);
Log("DATA Available on Subscriber", INFO);
start_r <= '1';
opcode_r <= TAKE;
wait_on_sig(ack_r);
wait_clock;
start_r <= '0';
wait_on_sig(done_r);
AlertIf(return_code_r /= RETCODE_OK, "Take Operation Failed", FAILURE);
Log("Received Sample with ID:" & integer'image(to_integer(unsigned(id_r))), INFO);
if (taken_r = '1') then
case (to_integer(unsigned(id_r))) is
when 2 =>
SB.Check(a_r);
when 3 =>
AlertIf(unsigned(a_r) /= 50, "Content of received sample with ID:3 is incorrect.",ERROR);
when 4 =>
AlertIf(unsigned(a_r) /= 25, "Content of received sample with ID:4 is incorrect.",ERROR);
when others =>
Alert("Sample received has Unknown id", ERROR);
end case;
end if;
wait_clock;
end process;
util_prc : process
begin
input_util <= int(0,WORD_WIDTH);
output_util <= int(0,WORD_WIDTH);
wait_clock;
input_util <= int(100,WORD_WIDTH);
output_util <= int(50,WORD_WIDTH);
wait_clock;
end process;
clock_prc : process
begin
clk <= '0';
wait for TEST_CLOCK_PERIOD/2;
clk <= '1';
wait for TEST_CLOCK_PERIOD/2;
end process;
time_prc : process(clk)
begin
if rising_edge(clk) then
if (reset = '1') then
time <= TIME_ZERO;
else
time <= time + gen_duration(TEST_CLOCK_PERIOD);
end if;
end if;
end process;
watchdog : process
begin
wait for 1 ms;
Alert("Test timeout", FAILURE);
std.env.stop;
end process;
end architecture;

View File

@ -0,0 +1,668 @@
-- altera vhdl_input_version vhdl_2008
-- XXX: QSYS Fix (https://www.intel.com/content/www/us/en/support/programmable/articles/000079458.html)
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.ros_package.all;
use work.ros_config.all;
use work.rtps_package.all;
use work.user_config.all;
use work.rtps_config_package.all;
entity L2_Testbench_ROS_Lib6 is
port (
-- SYSTEM
clk : in std_logic;
reset : in std_logic;
time : in TIME_TYPE;
-- UTILIZATION
input_util : in std_logic_vector(WORD_WIDTH-1 downto 0);
output_util : in std_logic_vector(WORD_WIDTH-1 downto 0);
-- INPUT
empty : in std_logic;
read : out std_logic;
data_in : in std_logic_vector(WORD_WIDTH-1 downto 0);
-- OUTPUT
full : in std_logic;
write : out std_logic;
data_out : out std_logic_vector(WORD_WIDTH-1 downto 0)
);
end entity;
architecture arch of L2_Testbench_ROS_Lib6 is
signal full_fire_rh, write_rh_fire : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal last_word_rh_firb, last_word_rh_fire : std_logic;
signal data_rh_fire, data_rh_firb : std_logic_vector(WORD_WIDTH-1 downto 0);
signal full_firb_rh, write_rh_firb : std_logic;
signal read_rb_firb, empty_firb_rb, last_word_firb_rb : std_logic;
signal data_firb_rb : std_logic_vector(WORD_WIDTH-1 downto 0);
signal read_re_fire, last_word_fire_re : std_logic_vector(0 to 1);
signal empty_fire_re : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal data_fire_re : WORD_ARRAY_TYPE(0 to 1);
signal alive_re_rb, full_frbre_re, write_rb_frbre : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal last_word_rb_frbre , last_word_rb_firo : std_logic;
signal data_rb_frbre , data_rb_firo : std_logic_vector(WORD_WIDTH-1 downto 0);
signal full_firo_rb, write_rb_firo : std_logic;
signal read_re_frbre, last_word_frbre_re : std_logic_vector(0 to 1);
signal empty_frbre_re : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal data_frbre_re : WORD_ARRAY_TYPE(0 to 1);
signal full_firo_re, write_re_firo, last_word_re_firo : std_logic_vector(0 to 1);
signal data_re_firo : WORD_ARRAY_TYPE(0 to 1);
signal start_rr_dr, ack_dr_rr, done_dr_rr, valid_rr_dr, ready_dr_rr, last_word_rr_dr : std_logic_vector(0 to NUM_READERS-1);
signal opcode_rr_dr : HISTORY_CACHE_OPCODE_ARRAY_TYPE(0 to NUM_READERS-1);
signal ret_dr_rr : HISTORY_CACHE_RESPONSE_ARRAY_TYPE(0 to NUM_READERS-1);
signal data_rr_dr : WORD_ARRAY_TYPE(0 to NUM_READERS-1);
signal liveliness_assertion_dw_rw, data_available_dw_rw, start_rw_dw, ack_dw_rw, done_rw_dw, get_data_rw_dw, valid_dw_rw, ready_rw_dw, last_word_dw_rw : std_logic_vector(0 to NUM_WRITERS-1);
signal opcode_rw_dw : HISTORY_CACHE_OPCODE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal seq_nr_rw_dw, cc_seq_nr_dw_rw : SEQUENCENUMBER_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal ret_dw_rw : HISTORY_CACHE_RESPONSE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal data_dw_rw : WORD_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal cc_instance_handle_dw_rw : INSTANCE_HANDLE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal cc_kind_dw_rw : CACHE_CHANGE_KIND_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal cc_source_timestamp_dw_rw : TIME_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal sample_info_dr_ri : SAMPLE_INFO_ARRAY_TYPE(0 to NUM_READERS-1);
signal start_ri_dr, ack_dr_ri, get_data_ri_dr, done_dr_ri, ready_ri_dr, valid_dr_ri, sample_info_valid_dr_ri, sample_info_ack_ri_dr, eoc_dr_ri, last_word_dr_ri : std_logic_vector(0 to NUM_READERS-1);
signal opcode_ri_dr : DDS_READER_OPCODE_ARRAY_TYPE(0 to NUM_READERS-1);
signal instance_state_ri_dr : INSTANCE_STATE_ARRAY_TYPE(0 to NUM_READERS-1);
signal view_state_ri_dr : VIEW_STATE_ARRAY_TYPE(0 to NUM_READERS-1);
signal sample_state_ri_dr : SAMPLE_STATE_ARRAY_TYPE(0 to NUM_READERS-1);
signal instance_handle_ri_dr : INSTANCE_HANDLE_ARRAY_TYPE(0 to NUM_READERS-1);
signal max_samples_ri_dr : MAX_SAMPLES_ARRAY_TYPE(0 to NUM_READERS-1);
signal return_code_dr_ri : RETURN_CODE_ARRAY_TYPE(0 to NUM_READERS-1);
signal data_dr_ri : WORD_ARRAY_TYPE(0 to NUM_READERS-1);
signal status_dr_ri : STATUS_KIND_ARRAY_TYPE(0 to NUM_READERS-1);
signal start_wi_dw, ack_dw_wi, done_dw_wi, valid_wi_dw, valid_dw_wi, ready_wi_dw, ready_dw_wi, last_word_wi_dw, last_word_dw_wi : std_logic_vector(0 to NUM_WRITERS-1);
signal opcode_wi_dw : DDS_WRITER_OPCODE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal instance_handle_wi_dw, instance_handle_dw_wi : INSTANCE_HANDLE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal source_ts_wi_dw : TIME_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal max_wait_wi_dw : DURATION_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal return_code_dw_wi : RETURN_CODE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal data_dw_wi, data_wi_dw : WORD_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal status_dw_wi : STATUS_KIND_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal empty_firo_ro, read_ro_firo, last_word_firo_ro : std_logic_vector(0 to 2);
signal data_firo_ro : WORD_ARRAY_TYPE(0 to 2);
-- ###GENERATED START###
signal start_user_wi, start_user_ri, ack_wi_user, ack_ri_user, done_wi_user, done_ri_user, taken_ri_user, data_available_ri_user : std_logic;
signal opcode_user_wi, opcode_user_ri : ROS_TOPIC_OPCODE_TYPE;
signal id_user_wi, a_user_wi, id_ri_user, a_ri_user : std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
signal return_code_wi_user, return_code_ri_user : std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0);
signal message_info_ri_user : MESSAGE_INFO_TYPE;
-- ###GENERATED END###
begin
rtps_handler_inst : entity work.rtps_handler(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- INPUT
empty => empty,
rd => read,
data_in => data_in,
-- TO DISCOVERY MODULE
full_dm => full_firb_rh,
wr_dm => write_rh_firb,
data_out_dm => data_rh_firb,
last_word_out_dm => last_word_rh_firb,
-- TO USER ENDPOINTS
full_rtps => full_fire_rh,
wr_rtps => write_rh_fire,
data_out_rtps => data_rh_fire,
last_word_out_rtps => last_word_rh_fire
);
fifo_in_rb_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_firb_rh,
write => write_rh_firb,
data_in(WORD_WIDTH-1 downto 0) => data_rh_firb,
data_in(WORD_WIDTH) => last_word_rh_firb,
-- OUTPUT
empty => empty_firb_rb,
read => read_rb_firb,
data_out(WORD_WIDTH-1 downto 0) => data_firb_rb,
data_out(WORD_WIDTH) => last_word_firb_rb,
-- MISC
free => open
);
fifo_in_re_r_if : if (NUM_READERS > 0) generate
fifo_in_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_READERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_fire_rh(0 to NUM_READERS-1),
write => write_rh_fire(0 to NUM_READERS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rh_fire, -- Multicast
data_in(WORD_WIDTH) => last_word_rh_fire, -- Multicast
-- OUTPUT
empty => empty_fire_re(0 to NUM_READERS-1),
read => read_re_fire(0),
data_out(WORD_WIDTH-1 downto 0) => data_fire_re(0),
data_out(WORD_WIDTH) => last_word_fire_re(0)
);
end generate;
fifo_in_re_w_if : if (NUM_WRITERS > 0) generate
fifo_in_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_WRITERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_fire_rh(NUM_READERS to NUM_ENDPOINTS-1),
write => write_rh_fire(NUM_READERS to NUM_ENDPOINTS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rh_fire, -- Multicast
data_in(WORD_WIDTH) => last_word_rh_fire, -- Multicast
-- OUTPUT
empty => empty_fire_re(NUM_READERS to NUM_ENDPOINTS-1),
read => read_re_fire(1),
data_out(WORD_WIDTH-1 downto 0) => data_fire_re(1),
data_out(WORD_WIDTH) => last_word_fire_re(1)
);
end generate;
rtps_discovery_module_inst : entity work.rtps_discovery_module(arch)
generic map (
MAX_REMOTE_PARTICIPANTS => MAX_REMOTE_PARTICIPANTS,
PREFER_MULTICAST => PREFER_MULTICAST_LOCATORS
)
port map (
clk => clk,
reset => reset,
time => time,
-- FROM RTPS HANDLER
empty => empty_firb_rb,
rd => read_rb_firb,
data_in => data_firb_rb,
last_word_in => last_word_firb_rb,
-- FROM USER ENDPOINTS
alive => alive_re_rb,
-- TO USER ENDPOINTS
full_rtps => full_frbre_re,
wr_rtps => write_rb_frbre,
data_out_rtps => data_rb_frbre,
last_word_out_rtps => last_word_rb_frbre,
-- TO RTPS OUT
full_ro => full_firo_rb,
wr_ro => write_rb_firo,
data_out_ro => data_rb_firo,
last_word_out_ro => last_word_rb_firo
);
fifo_rb_re_r_if : if (NUM_READERS > 0) generate
fifo_rb_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_READERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_frbre_re(0 to NUM_READERS-1),
write => write_rb_frbre(0 to NUM_READERS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rb_frbre,
data_in(WORD_WIDTH) => last_word_rb_frbre,
-- OUTPUT
empty => empty_frbre_re(0 to NUM_READERS-1),
read => read_re_frbre(0),
data_out(WORD_WIDTH-1 downto 0) => data_frbre_re(0),
data_out(WORD_WIDTH) => last_word_frbre_re(0)
);
end generate;
fifo_rb_re_w_if : if (NUM_WRITERS > 0) generate
fifo_rb_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_WRITERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_frbre_re(NUM_READERS to NUM_ENDPOINTS-1),
write => write_rb_frbre(NUM_READERS to NUM_ENDPOINTS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rb_frbre,
data_in(WORD_WIDTH) => last_word_rb_frbre,
-- OUTPUT
empty => empty_frbre_re(NUM_READERS to NUM_ENDPOINTS-1),
read => read_re_frbre(1),
data_out(WORD_WIDTH-1 downto 0) => data_frbre_re(1),
data_out(WORD_WIDTH) => last_word_frbre_re(1)
);
end generate;
rtps_endpoint_r_if : if (NUM_READERS > 0) generate
rtps_reader_inst : entity work.rtps_reader(arch)
generic map (
NUM_READERS => NUM_READERS,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(0 to NUM_READERS-1)),
ENTITYID => ENTITYID(0 to NUM_READERS-1),
MAX_REMOTE_ENDPOINTS => MAX_REMOTE_ENDPOINTS
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- FROM RTPS_HANDLER (USER TRAFFIC)
empty_user => empty_fire_re(0 to NUM_READERS-1),
rd_user => read_re_fire(0),
data_in_user => data_fire_re(0),
last_word_in_user => last_word_fire_re(0),
-- FROM DISCOVERY MODULE (META TRAFFIC)
empty_meta => empty_frbre_re(0 to NUM_READERS-1),
rd_meta => read_re_frbre(0),
data_in_meta => data_frbre_re(0),
last_word_in_meta => last_word_frbre_re(0),
-- RTPS OUTPUT
full_ro => full_firo_re(0),
wr_ro => write_re_firo(0),
data_out_ro => data_re_firo(0),
last_word_out_ro => last_word_re_firo(0),
-- TO HISTORY CACHE
start_hc => start_rr_dr(0 to NUM_READERS-1),
opcode_hc => opcode_rr_dr(0 to NUM_READERS-1),
ack_hc => ack_dr_rr(0 to NUM_READERS-1),
done_hc => done_dr_rr(0 to NUM_READERS-1),
ret_hc => ret_dr_rr(0 to NUM_READERS-1),
valid_out_hc => valid_rr_dr(0 to NUM_READERS-1),
ready_out_hc => ready_dr_rr(0 to NUM_READERS-1),
data_out_hc => data_rr_dr(0 to NUM_READERS-1),
last_word_out_hc => last_word_rr_dr(0 to NUM_READERS-1)
);
-- Set Alive Signals of Readers to Zero
alive_re_rb(0 to NUM_READERS-1) <= (others => '0');
end generate;
rtps_endpoint_w_if : if (NUM_WRITERS > 0) generate
rtps_writer_inst : entity work.rtps_writer(arch)
generic map (
NUM_WRITERS => NUM_WRITERS,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(NUM_READERS to NUM_ENDPOINTS-1)),
ENTITYID => ENTITYID(NUM_READERS to NUM_ENDPOINTS-1),
INLINE_QOS => INLINE_QOS_DATA(0 to NUM_WRITERS-1),
MAX_REMOTE_ENDPOINTS => MAX_REMOTE_ENDPOINTS
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- FROM RTPS_HANDLER (USER TRAFFIC)
empty_user => empty_fire_re(NUM_READERS to NUM_ENDPOINTS-1),
rd_user => read_re_fire(1),
data_in_user => data_fire_re(1),
last_word_in_user => last_word_fire_re(1),
-- FROM DISCOVERY MODULE (META TRAFFIC)
empty_meta => empty_frbre_re(NUM_READERS to NUM_ENDPOINTS-1),
rd_meta => read_re_frbre(1),
data_in_meta => data_frbre_re(1),
last_word_in_meta => last_word_frbre_re(1),
-- TO DISCOVERY MODULE (META TRAFFIC)
alive_sig => alive_re_rb(NUM_READERS to NUM_ENDPOINTS-1),
-- RTPS OUTPUT
full_ro => full_firo_re(1),
wr_ro => write_re_firo(1),
data_out_ro => data_re_firo(1),
last_word_out_ro => last_word_re_firo(1),
-- FROM HC
liveliness_assertion => liveliness_assertion_dw_rw(0 to NUM_WRITERS-1),
data_available => data_available_dw_rw(0 to NUM_WRITERS-1),
start_hc => start_rw_dw(0 to NUM_WRITERS-1),
opcode_hc => opcode_rw_dw(0 to NUM_WRITERS-1),
ack_hc => ack_dw_rw(0 to NUM_WRITERS-1),
seq_nr_hc => seq_nr_rw_dw(0 to NUM_WRITERS-1),
done_hc => done_rw_dw(0 to NUM_WRITERS-1),
ret_hc => ret_dw_rw(0 to NUM_WRITERS-1),
get_data_hc => get_data_rw_dw(0 to NUM_WRITERS-1),
valid_in_hc => valid_dw_rw(0 to NUM_WRITERS-1),
ready_in_hc => ready_rw_dw(0 to NUM_WRITERS-1),
data_in_hc => data_dw_rw(0 to NUM_WRITERS-1),
last_word_in_hc => last_word_dw_rw(0 to NUM_WRITERS-1),
cc_instance_handle => cc_instance_handle_dw_rw(0 to NUM_WRITERS-1),
cc_kind => cc_kind_dw_rw(0 to NUM_WRITERS-1),
cc_source_timestamp => cc_source_timestamp_dw_rw(0 to NUM_WRITERS-1),
cc_seq_nr => cc_seq_nr_dw_rw(0 to NUM_WRITERS-1)
);
end generate;
dds_endpoint_w_if : if (NUM_WRITERS > 1) generate
dds_writer_inst : entity work.dds_writer(arch)
generic map (
NUM_WRITERS => NUM_WRITERS-1,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(NUM_READERS to NUM_ENDPOINTS-2))
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- TO/FROM RTPS ENDPOINT
start_rtps => start_rw_dw(0 to NUM_WRITERS-2),
opcode_rtps => opcode_rw_dw(0 to NUM_WRITERS-2),
ack_rtps => ack_dw_rw(0 to NUM_WRITERS-2),
done_rtps => done_rw_dw(0 to NUM_WRITERS-2),
ret_rtps => ret_dw_rw(0 to NUM_WRITERS-2),
seq_nr_rtps => seq_nr_rw_dw(0 to NUM_WRITERS-2),
get_data_rtps => get_data_rw_dw(0 to NUM_WRITERS-2),
valid_out_rtps => valid_dw_rw(0 to NUM_WRITERS-2),
ready_out_rtps => ready_rw_dw(0 to NUM_WRITERS-2),
data_out_rtps => data_dw_rw(0 to NUM_WRITERS-2),
last_word_out_rtps => last_word_dw_rw(0 to NUM_WRITERS-2),
liveliness_assertion => liveliness_assertion_dw_rw(0 to NUM_WRITERS-2),
data_available => data_available_dw_rw(0 to NUM_WRITERS-2),
-- Cache Change
cc_instance_handle => cc_instance_handle_dw_rw(0 to NUM_WRITERS-2),
cc_kind => cc_kind_dw_rw(0 to NUM_WRITERS-2),
cc_source_timestamp => cc_source_timestamp_dw_rw(0 to NUM_WRITERS-2),
cc_seq_nr => cc_seq_nr_dw_rw(0 to NUM_WRITERS-2),
-- TO/FROM USER ENTITY
start_dds => start_wi_dw(0 to NUM_WRITERS-2),
ack_dds => ack_dw_wi(0 to NUM_WRITERS-2),
opcode_dds => opcode_wi_dw(0 to NUM_WRITERS-2),
instance_handle_in_dds => instance_handle_wi_dw(0 to NUM_WRITERS-2),
source_ts_dds => source_ts_wi_dw(0 to NUM_WRITERS-2),
max_wait_dds => max_wait_wi_dw(0 to NUM_WRITERS-2),
done_dds => done_dw_wi(0 to NUM_WRITERS-2),
return_code_dds => return_code_dw_wi(0 to NUM_WRITERS-2),
instance_handle_out_dds => instance_handle_dw_wi(0 to NUM_WRITERS-2),
valid_in_dds => valid_wi_dw(0 to NUM_WRITERS-2),
ready_in_dds => ready_dw_wi(0 to NUM_WRITERS-2),
data_in_dds => data_wi_dw(0 to NUM_WRITERS-2),
last_word_in_dds => last_word_wi_dw(0 to NUM_WRITERS-2),
valid_out_dds => valid_dw_wi(0 to NUM_WRITERS-2),
ready_out_dds => ready_wi_dw(0 to NUM_WRITERS-2),
data_out_dds => data_dw_wi(0 to NUM_WRITERS-2),
last_word_out_dds => last_word_dw_wi(0 to NUM_WRITERS-2),
-- Communication Status
status => status_dw_wi(0 to NUM_WRITERS-2)
);
end generate;
dds_endpoint_r_if : if (NUM_READERS > 0) generate
dds_reader_inst : entity work.dds_reader(arch)
generic map (
NUM_READERS => NUM_READERS,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(0 to NUM_READERS-1)),
MAX_REMOTE_ENDPOINTS => MAX_REMOTE_ENDPOINTS
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- FROM RTPS ENDPOINT
start_rtps => start_rr_dr(0 to NUM_READERS-1),
opcode_rtps => opcode_rr_dr(0 to NUM_READERS-1),
ack_rtps => ack_dr_rr(0 to NUM_READERS-1),
done_rtps => done_dr_rr(0 to NUM_READERS-1),
ret_rtps => ret_dr_rr(0 to NUM_READERS-1),
valid_in_rtps => valid_rr_dr(0 to NUM_READERS-1),
ready_in_rtps => ready_dr_rr(0 to NUM_READERS-1),
data_in_rtps => data_rr_dr(0 to NUM_READERS-1),
last_word_in_rtps => last_word_rr_dr(0 to NUM_READERS-1),
-- TO USER ENTITY
start_dds => start_ri_dr(0 to NUM_READERS-1),
ack_dds => ack_dr_ri(0 to NUM_READERS-1),
opcode_dds => opcode_ri_dr(0 to NUM_READERS-1),
instance_state_dds => instance_state_ri_dr(0 to NUM_READERS-1),
view_state_dds => view_state_ri_dr(0 to NUM_READERS-1),
sample_state_dds => sample_state_ri_dr(0 to NUM_READERS-1),
instance_handle_dds => instance_handle_ri_dr(0 to NUM_READERS-1),
max_samples_dds => max_samples_ri_dr(0 to NUM_READERS-1),
get_data_dds => get_data_ri_dr(0 to NUM_READERS-1),
done_dds => done_dr_ri(0 to NUM_READERS-1),
return_code_dds => return_code_dr_ri(0 to NUM_READERS-1),
valid_out_dds => valid_dr_ri(0 to NUM_READERS-1),
ready_out_dds => ready_ri_dr(0 to NUM_READERS-1),
data_out_dds => data_dr_ri(0 to NUM_READERS-1),
last_word_out_dds => last_word_dr_ri(0 to NUM_READERS-1),
sample_info => sample_info_dr_ri(0 to NUM_READERS-1),
sample_info_valid => sample_info_valid_dr_ri(0 to NUM_READERS-1),
sample_info_ack => sample_info_ack_ri_dr(0 to NUM_READERS-1),
eoc => eoc_dr_ri(0 to NUM_READERS-1),
-- Communication Status
status => status_dr_ri(0 to NUM_READERS-1)
);
end generate;
ros_discovery_writer_inst : entity work.ros_static_discovery_writer(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- TO/FROM RTPS ENDPOINT
start => start_rw_dw(NUM_WRITERS-1),
opcode => opcode_rw_dw(NUM_WRITERS-1),
ack => ack_dw_rw(NUM_WRITERS-1),
done => done_rw_dw(NUM_WRITERS-1),
ret => ret_dw_rw(NUM_WRITERS-1),
seq_nr => seq_nr_rw_dw(NUM_WRITERS-1),
get_data => get_data_rw_dw(NUM_WRITERS-1),
valid_out => valid_dw_rw(NUM_WRITERS-1),
ready_out => ready_rw_dw(NUM_WRITERS-1),
data_out => data_dw_rw(NUM_WRITERS-1),
last_word_out => last_word_dw_rw(NUM_WRITERS-1),
liveliness_assertion => liveliness_assertion_dw_rw(NUM_WRITERS-1),
data_available => data_available_dw_rw(NUM_WRITERS-1),
-- Cache Change
cc_instance_handle => cc_instance_handle_dw_rw(NUM_WRITERS-1),
cc_kind => cc_kind_dw_rw(NUM_WRITERS-1),
cc_source_timestamp => cc_source_timestamp_dw_rw(NUM_WRITERS-1),
cc_seq_nr => cc_seq_nr_dw_rw(NUM_WRITERS-1)
);
fifo_in_ro_gen : for i in 0 to 2 generate
fifo_in_ro_if : if (i = 2) generate
fifo_in_ro_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_firo_rb,
write => write_rb_firo,
data_in(WORD_WIDTH-1 downto 0) => data_rb_firo,
data_in(WORD_WIDTH) => last_word_rb_firo,
-- OUTPUT
empty => empty_firo_ro(i),
read => read_ro_firo(i),
data_out(WORD_WIDTH) => last_word_firo_ro(i),
data_out(WORD_WIDTH-1 downto 0) => data_firo_ro(i),
-- MISC
free => open
);
else generate
fifo_in_ro_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_firo_re(i),
write => write_re_firo(i),
data_in(WORD_WIDTH-1 downto 0) => data_re_firo(i),
data_in(WORD_WIDTH) => last_word_re_firo(i),
-- OUTPUT
empty => empty_firo_ro(i),
read => read_ro_firo(i),
data_out(WORD_WIDTH) => last_word_firo_ro(i),
data_out(WORD_WIDTH-1 downto 0) => data_firo_ro(i),
-- MISC
free => open
);
end generate;
end generate;
rtps_out_inst : entity work.rtps_out(arch)
generic map (
RTPS_OUT_WIDTH => 3
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- INPUT
empty => empty_firo_ro,
rd => read_ro_firo,
data_in => data_firo_ro,
last_word_in => last_word_firo_ro,
-- OUTPUT
full => full,
wr => write,
data_out => data_out
);
-- ######GENERATED START######
Type1_ros_sub_inst : entity work.Type1_ros_sub(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- FROM DDS READER
start_dds => start_ri_dr(0),
ack_dds => ack_dr_ri(0),
opcode_dds => opcode_ri_dr(0),
instance_state_dds => instance_state_ri_dr(0),
view_state_dds => view_state_ri_dr(0),
sample_state_dds => sample_state_ri_dr(0),
instance_handle_dds => instance_handle_ri_dr(0),
max_samples_dds => max_samples_ri_dr(0),
get_data_dds => get_data_ri_dr(0),
done_dds => done_dr_ri(0),
return_code_dds => return_code_dr_ri(0),
valid_in_dds => valid_dr_ri(0),
ready_in_dds => ready_ri_dr(0),
data_in_dds => data_dr_ri(0),
last_word_in_dds => last_word_dr_ri(0),
sample_info_dds => sample_info_dr_ri(0),
sample_info_valid_dds => sample_info_valid_dr_ri(0),
sample_info_ack_dds => sample_info_ack_ri_dr(0),
eoc_dds => eoc_dr_ri(0),
-- Communication Status
status_dds => status_dr_ri(0),
-- TO USER ENTITY
start_user => start_user_ri,
ack_user => ack_ri_user,
opcode_user => opcode_user_ri,
done_user => done_ri_user,
return_code_user => return_code_ri_user,
data_available_user => data_available_ri_user,
-- ###GENERATED START###
id => id_ri_user,
a => a_ri_user,
-- ###GENERATED END###
message_info_user => message_info_ri_user,
taken_user => taken_ri_user
);
Type1_ros_pub_inst : entity work.Type1_ros_pub(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- FROM DDS WRITER
start_dds => start_wi_dw(0),
ack_dds => ack_dw_wi(0),
opcode_dds => opcode_wi_dw(0),
instance_handle_in_dds => instance_handle_wi_dw(0),
source_ts_dds => source_ts_wi_dw(0),
max_wait_dds => max_wait_wi_dw(0),
done_dds => done_dw_wi(0),
return_code_dds => return_code_dw_wi(0),
instance_handle_out_dds => instance_handle_dw_wi(0),
valid_out_dds => valid_wi_dw(0),
ready_out_dds => ready_dw_wi(0),
data_out_dds => data_wi_dw(0),
last_word_out_dds => last_word_wi_dw(0),
valid_in_dds => valid_dw_wi(0),
ready_in_dds => ready_wi_dw(0),
data_in_dds => data_dw_wi(0),
last_word_in_dds => last_word_dw_wi(0),
-- Communication Status
status_dds => status_dw_wi(0),
-- TO USER ENTITY
start_user => start_user_wi,
ack_user => ack_wi_user,
opcode_user => opcode_user_wi,
-- ###GENERATED START###
id => id_user_wi,
a => a_user_wi,
-- ###GENERATED END###
done_user => done_wi_user,
return_code_user => return_code_wi_user
);
test_loopback_util_inst : entity work.test_loopback_util(arch)
port map(
clk => clk,
reset => reset,
input_util => input_util,
output_util => output_util,
start_r => start_user_ri,
opcode_r => opcode_user_ri,
ack_r => ack_ri_user,
done_r => done_ri_user,
return_code_r => return_code_ri_user,
data_available_r => data_available_ri_user,
id_r => id_ri_user,
a_r => a_ri_user,
message_info_r => message_info_ri_user,
taken_r => taken_ri_user,
start_w => start_user_wi,
opcode_w => opcode_user_wi,
ack_w => ack_wi_user,
id_w => id_user_wi,
a_w => a_user_wi,
done_w => done_wi_user,
return_code_w => return_code_wi_user
);
-- ######GENERATED END######
end architecture;

View File

@ -0,0 +1,98 @@
-- altera vhdl_input_version vhdl_2008
-- XXX: QSYS Fix (https://www.intel.com/content/www/us/en/support/programmable/articles/000079458.html)
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.rtps_package.all;
use work.ros_package.all;
use work.Type1_package.all;
package ros_config is
-- Period of ros system clock
constant ROS_CLOCK_PERIOD : time := 50 ns;
-- IPv4 Address of ROS System [Default 192.168.0.133]
constant ROS_ADDRESS : std_logic_vector(IPv4_ADDRESS_WIDTH-1 downto 0) := x"C0A80084";
-- Random Key used to generate GUIDs
constant ROS_RAND_KEY : std_logic_vector(47 downto 0) := x"5BC9374EE750";
constant NUM_NODES : natural := 1;
constant ROS_NODES : ROS_NODE_ARRAY_TYPE(0 to NUM_NODES-1) := (
0 => (
name => gen_user_string("test_loopback_server"),
namespace => gen_user_string(""),
domain_id => 0,
NUM_PUBS => 1,
NUM_SUBS => 1,
NUM_SERVICES => 0,
NUM_ACTIONS => 0
)
);
constant NUM_PUBS : natural := get_num_pubs(ROS_NODES);
constant NUM_SUBS : natural := get_num_subs(ROS_NODES);
constant NUM_SERVICES : natural := get_num_services(ROS_NODES);
constant NUM_ACTIONS : natural := get_num_actions(ROS_NODES);
constant ROS_PUBLICATIONS : ROS_TOPIC_ARRAY_TYPE(0 to NUM_PUBS-1) := (
0 => (
node_id => 0,
TOPICNAME => gen_user_string("Loopback_2"),
TYPENAME => gen_user_string("tutorial_interfaces::msg::dds_::Type1_"),
QOS => ROS_QOS_PROFILE_TRANSIENT,
MAX_SIZE => MAX_TYPE1_SIZE
)
);
constant ROS_SUBSCRIPTIONS : ROS_TOPIC_ARRAY_TYPE(0 to NUM_SUBS-1) := (
0 => (
node_id => 0,
TOPICNAME => gen_user_string("Loopback_1"),
TYPENAME => gen_user_string("tutorial_interfaces::msg::dds_::Type1_"),
QOS => ROS_QOS_PROFILE_TRANSIENT,
MAX_SIZE => MAX_TYPE1_SIZE
)
);
constant ROS_SERVICES : ROS_SERVICE_ARRAY_TYPE(0 to NUM_SERVICES-1) := (
others => (
node_id => 0,
SERVICENAME => gen_user_string(""),
RQ_TYPENAME => gen_user_string(""),
RR_TYPENAME => gen_user_string(""),
QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
MAX_RQ_SIZE => 0,
MAX_RR_SIZE => 0,
is_client => FALSE
)
);
constant ROS_ACTIONS : ROS_ACTION_ARRAY_TYPE(0 to NUM_ACTIONS-1) := (
others => (
node_id => 0,
ACTIONNAME => gen_user_string(""),
GOAL_RQ_TYPENAME => gen_user_string(""),
GOAL_RR_TYPENAME => gen_user_string(""),
RESULT_RQ_TYPENAME => gen_user_string(""),
RESULT_RR_TYPENAME => gen_user_string(""),
FEEDBACK_TYPENAME => gen_user_string(""),
GOAL_QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
RESULT_QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
FEEDBACK_QOS => ROS_QOS_PROFILE_DEFAULT,
CANCEL_QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
MAX_GOAL_RQ_SIZE => 0,
MAX_GOAL_RR_SIZE => 0,
MAX_RESULT_RQ_SIZE => 0,
MAX_RESULT_RR_SIZE => 0,
MAX_FEEDBACK_SIZE => 0,
is_client => FALSE,
enable_feedback => TRUE
)
);
-- Defines sensible RTPS timings for simulation
constant SIMULATION_TIMING : boolean := TRUE;
end package;

View File

@ -0,0 +1,654 @@
-- altera vhdl_input_version vhdl_2008
-- XXX: QSYS Fix (https://www.intel.com/content/www/us/en/support/programmable/articles/000079458.html)
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.ros_package.all;
use work.ros_config.all;
use work.rtps_package.all;
use work.user_config.all;
use work.rtps_config_package.all;
entity L2_Testbench_ROS_Lib7 is
port (
-- SYSTEM
clk : in std_logic;
reset : in std_logic;
time : in TIME_TYPE;
-- INPUT
empty : in std_logic;
read : out std_logic;
data_in : in std_logic_vector(WORD_WIDTH-1 downto 0);
-- OUTPUT
full : in std_logic;
write : out std_logic;
data_out : out std_logic_vector(WORD_WIDTH-1 downto 0);
-- READER
start_r : in std_logic;
opcode_r : in ROS_TOPIC_OPCODE_TYPE;
ack_r : out std_logic;
done_r : out std_logic;
return_code_r : out std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0);
data_available_r : out std_logic;
id_r : out std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
a_r : out std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
message_info_r : out MESSAGE_INFO_TYPE;
taken_r : out std_logic;
-- WRITER
start_w : in std_logic;
opcode_w : in ROS_TOPIC_OPCODE_TYPE;
ack_w : out std_logic;
id_w : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
a_w : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
done_w : out std_logic;
return_code_w : out std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0)
);
end entity;
architecture arch of L2_Testbench_ROS_Lib7 is
signal full_fire_rh, write_rh_fire : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal last_word_rh_firb, last_word_rh_fire : std_logic;
signal data_rh_fire, data_rh_firb : std_logic_vector(WORD_WIDTH-1 downto 0);
signal full_firb_rh, write_rh_firb : std_logic;
signal read_rb_firb, empty_firb_rb, last_word_firb_rb : std_logic;
signal data_firb_rb : std_logic_vector(WORD_WIDTH-1 downto 0);
signal read_re_fire, last_word_fire_re : std_logic_vector(0 to 1);
signal empty_fire_re : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal data_fire_re : WORD_ARRAY_TYPE(0 to 1);
signal alive_re_rb, full_frbre_re, write_rb_frbre : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal last_word_rb_frbre , last_word_rb_firo : std_logic;
signal data_rb_frbre , data_rb_firo : std_logic_vector(WORD_WIDTH-1 downto 0);
signal full_firo_rb, write_rb_firo : std_logic;
signal read_re_frbre, last_word_frbre_re : std_logic_vector(0 to 1);
signal empty_frbre_re : std_logic_vector(0 to NUM_ENDPOINTS-1);
signal data_frbre_re : WORD_ARRAY_TYPE(0 to 1);
signal full_firo_re, write_re_firo, last_word_re_firo : std_logic_vector(0 to 1);
signal data_re_firo : WORD_ARRAY_TYPE(0 to 1);
signal start_rr_dr, ack_dr_rr, done_dr_rr, valid_rr_dr, ready_dr_rr, last_word_rr_dr : std_logic_vector(0 to NUM_READERS-1);
signal opcode_rr_dr : HISTORY_CACHE_OPCODE_ARRAY_TYPE(0 to NUM_READERS-1);
signal ret_dr_rr : HISTORY_CACHE_RESPONSE_ARRAY_TYPE(0 to NUM_READERS-1);
signal data_rr_dr : WORD_ARRAY_TYPE(0 to NUM_READERS-1);
signal liveliness_assertion_dw_rw, data_available_dw_rw, start_rw_dw, ack_dw_rw, done_rw_dw, get_data_rw_dw, valid_dw_rw, ready_rw_dw, last_word_dw_rw : std_logic_vector(0 to NUM_WRITERS-1);
signal opcode_rw_dw : HISTORY_CACHE_OPCODE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal seq_nr_rw_dw, cc_seq_nr_dw_rw : SEQUENCENUMBER_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal ret_dw_rw : HISTORY_CACHE_RESPONSE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal data_dw_rw : WORD_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal cc_instance_handle_dw_rw : INSTANCE_HANDLE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal cc_kind_dw_rw : CACHE_CHANGE_KIND_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal cc_source_timestamp_dw_rw : TIME_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal sample_info_dr_ri : SAMPLE_INFO_ARRAY_TYPE(0 to NUM_READERS-1);
signal start_ri_dr, ack_dr_ri, get_data_ri_dr, done_dr_ri, ready_ri_dr, valid_dr_ri, sample_info_valid_dr_ri, sample_info_ack_ri_dr, eoc_dr_ri, last_word_dr_ri : std_logic_vector(0 to NUM_READERS-1);
signal opcode_ri_dr : DDS_READER_OPCODE_ARRAY_TYPE(0 to NUM_READERS-1);
signal instance_state_ri_dr : INSTANCE_STATE_ARRAY_TYPE(0 to NUM_READERS-1);
signal view_state_ri_dr : VIEW_STATE_ARRAY_TYPE(0 to NUM_READERS-1);
signal sample_state_ri_dr : SAMPLE_STATE_ARRAY_TYPE(0 to NUM_READERS-1);
signal instance_handle_ri_dr : INSTANCE_HANDLE_ARRAY_TYPE(0 to NUM_READERS-1);
signal max_samples_ri_dr : MAX_SAMPLES_ARRAY_TYPE(0 to NUM_READERS-1);
signal return_code_dr_ri : RETURN_CODE_ARRAY_TYPE(0 to NUM_READERS-1);
signal data_dr_ri : WORD_ARRAY_TYPE(0 to NUM_READERS-1);
signal status_dr_ri : STATUS_KIND_ARRAY_TYPE(0 to NUM_READERS-1);
signal start_wi_dw, ack_dw_wi, done_dw_wi, valid_wi_dw, valid_dw_wi, ready_wi_dw, ready_dw_wi, last_word_wi_dw, last_word_dw_wi : std_logic_vector(0 to NUM_WRITERS-1);
signal opcode_wi_dw : DDS_WRITER_OPCODE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal instance_handle_wi_dw, instance_handle_dw_wi : INSTANCE_HANDLE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal source_ts_wi_dw : TIME_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal max_wait_wi_dw : DURATION_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal return_code_dw_wi : RETURN_CODE_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal data_dw_wi, data_wi_dw : WORD_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal status_dw_wi : STATUS_KIND_ARRAY_TYPE(0 to NUM_WRITERS-1);
signal empty_firo_ro, read_ro_firo, last_word_firo_ro : std_logic_vector(0 to 2);
signal data_firo_ro : WORD_ARRAY_TYPE(0 to 2);
-- ###GENERATED START###
-- ###GENERATED END###
begin
rtps_handler_inst : entity work.rtps_handler(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- INPUT
empty => empty,
rd => read,
data_in => data_in,
-- TO DISCOVERY MODULE
full_dm => full_firb_rh,
wr_dm => write_rh_firb,
data_out_dm => data_rh_firb,
last_word_out_dm => last_word_rh_firb,
-- TO USER ENDPOINTS
full_rtps => full_fire_rh,
wr_rtps => write_rh_fire,
data_out_rtps => data_rh_fire,
last_word_out_rtps => last_word_rh_fire
);
fifo_in_rb_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_firb_rh,
write => write_rh_firb,
data_in(WORD_WIDTH-1 downto 0) => data_rh_firb,
data_in(WORD_WIDTH) => last_word_rh_firb,
-- OUTPUT
empty => empty_firb_rb,
read => read_rb_firb,
data_out(WORD_WIDTH-1 downto 0) => data_firb_rb,
data_out(WORD_WIDTH) => last_word_firb_rb,
-- MISC
free => open
);
fifo_in_re_r_if : if (NUM_READERS > 0) generate
fifo_in_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_READERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_fire_rh(0 to NUM_READERS-1),
write => write_rh_fire(0 to NUM_READERS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rh_fire, -- Multicast
data_in(WORD_WIDTH) => last_word_rh_fire, -- Multicast
-- OUTPUT
empty => empty_fire_re(0 to NUM_READERS-1),
read => read_re_fire(0),
data_out(WORD_WIDTH-1 downto 0) => data_fire_re(0),
data_out(WORD_WIDTH) => last_word_fire_re(0)
);
end generate;
fifo_in_re_w_if : if (NUM_WRITERS > 0) generate
fifo_in_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_WRITERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_fire_rh(NUM_READERS to NUM_ENDPOINTS-1),
write => write_rh_fire(NUM_READERS to NUM_ENDPOINTS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rh_fire, -- Multicast
data_in(WORD_WIDTH) => last_word_rh_fire, -- Multicast
-- OUTPUT
empty => empty_fire_re(NUM_READERS to NUM_ENDPOINTS-1),
read => read_re_fire(1),
data_out(WORD_WIDTH-1 downto 0) => data_fire_re(1),
data_out(WORD_WIDTH) => last_word_fire_re(1)
);
end generate;
rtps_discovery_module_inst : entity work.rtps_discovery_module(arch)
generic map (
MAX_REMOTE_PARTICIPANTS => MAX_REMOTE_PARTICIPANTS,
PREFER_MULTICAST => PREFER_MULTICAST_LOCATORS
)
port map (
clk => clk,
reset => reset,
time => time,
-- FROM RTPS HANDLER
empty => empty_firb_rb,
rd => read_rb_firb,
data_in => data_firb_rb,
last_word_in => last_word_firb_rb,
-- FROM USER ENDPOINTS
alive => alive_re_rb,
-- TO USER ENDPOINTS
full_rtps => full_frbre_re,
wr_rtps => write_rb_frbre,
data_out_rtps => data_rb_frbre,
last_word_out_rtps => last_word_rb_frbre,
-- TO RTPS OUT
full_ro => full_firo_rb,
wr_ro => write_rb_firo,
data_out_ro => data_rb_firo,
last_word_out_ro => last_word_rb_firo
);
fifo_rb_re_r_if : if (NUM_READERS > 0) generate
fifo_rb_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_READERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_frbre_re(0 to NUM_READERS-1),
write => write_rb_frbre(0 to NUM_READERS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rb_frbre,
data_in(WORD_WIDTH) => last_word_rb_frbre,
-- OUTPUT
empty => empty_frbre_re(0 to NUM_READERS-1),
read => read_re_frbre(0),
data_out(WORD_WIDTH-1 downto 0) => data_frbre_re(0),
data_out(WORD_WIDTH) => last_word_frbre_re(0)
);
end generate;
fifo_rb_re_w_if : if (NUM_WRITERS > 0) generate
fifo_rb_re_inst : entity work.vector_FIFO
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1,
FIFO_WIDTH => NUM_WRITERS
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_frbre_re(NUM_READERS to NUM_ENDPOINTS-1),
write => write_rb_frbre(NUM_READERS to NUM_ENDPOINTS-1),
data_in(WORD_WIDTH-1 downto 0) => data_rb_frbre,
data_in(WORD_WIDTH) => last_word_rb_frbre,
-- OUTPUT
empty => empty_frbre_re(NUM_READERS to NUM_ENDPOINTS-1),
read => read_re_frbre(1),
data_out(WORD_WIDTH-1 downto 0) => data_frbre_re(1),
data_out(WORD_WIDTH) => last_word_frbre_re(1)
);
end generate;
rtps_endpoint_r_if : if (NUM_READERS > 0) generate
rtps_reader_inst : entity work.rtps_reader(arch)
generic map (
NUM_READERS => NUM_READERS,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(0 to NUM_READERS-1)),
ENTITYID => ENTITYID(0 to NUM_READERS-1),
MAX_REMOTE_ENDPOINTS => MAX_REMOTE_ENDPOINTS
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- FROM RTPS_HANDLER (USER TRAFFIC)
empty_user => empty_fire_re(0 to NUM_READERS-1),
rd_user => read_re_fire(0),
data_in_user => data_fire_re(0),
last_word_in_user => last_word_fire_re(0),
-- FROM DISCOVERY MODULE (META TRAFFIC)
empty_meta => empty_frbre_re(0 to NUM_READERS-1),
rd_meta => read_re_frbre(0),
data_in_meta => data_frbre_re(0),
last_word_in_meta => last_word_frbre_re(0),
-- RTPS OUTPUT
full_ro => full_firo_re(0),
wr_ro => write_re_firo(0),
data_out_ro => data_re_firo(0),
last_word_out_ro => last_word_re_firo(0),
-- TO HISTORY CACHE
start_hc => start_rr_dr(0 to NUM_READERS-1),
opcode_hc => opcode_rr_dr(0 to NUM_READERS-1),
ack_hc => ack_dr_rr(0 to NUM_READERS-1),
done_hc => done_dr_rr(0 to NUM_READERS-1),
ret_hc => ret_dr_rr(0 to NUM_READERS-1),
valid_out_hc => valid_rr_dr(0 to NUM_READERS-1),
ready_out_hc => ready_dr_rr(0 to NUM_READERS-1),
data_out_hc => data_rr_dr(0 to NUM_READERS-1),
last_word_out_hc => last_word_rr_dr(0 to NUM_READERS-1)
);
-- Set Alive Signals of Readers to Zero
alive_re_rb(0 to NUM_READERS-1) <= (others => '0');
end generate;
rtps_endpoint_w_if : if (NUM_WRITERS > 0) generate
rtps_writer_inst : entity work.rtps_writer(arch)
generic map (
NUM_WRITERS => NUM_WRITERS,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(NUM_READERS to NUM_ENDPOINTS-1)),
ENTITYID => ENTITYID(NUM_READERS to NUM_ENDPOINTS-1),
INLINE_QOS => INLINE_QOS_DATA(0 to NUM_WRITERS-1),
MAX_REMOTE_ENDPOINTS => MAX_REMOTE_ENDPOINTS
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- FROM RTPS_HANDLER (USER TRAFFIC)
empty_user => empty_fire_re(NUM_READERS to NUM_ENDPOINTS-1),
rd_user => read_re_fire(1),
data_in_user => data_fire_re(1),
last_word_in_user => last_word_fire_re(1),
-- FROM DISCOVERY MODULE (META TRAFFIC)
empty_meta => empty_frbre_re(NUM_READERS to NUM_ENDPOINTS-1),
rd_meta => read_re_frbre(1),
data_in_meta => data_frbre_re(1),
last_word_in_meta => last_word_frbre_re(1),
-- TO DISCOVERY MODULE (META TRAFFIC)
alive_sig => alive_re_rb(NUM_READERS to NUM_ENDPOINTS-1),
-- RTPS OUTPUT
full_ro => full_firo_re(1),
wr_ro => write_re_firo(1),
data_out_ro => data_re_firo(1),
last_word_out_ro => last_word_re_firo(1),
-- FROM HC
liveliness_assertion => liveliness_assertion_dw_rw(0 to NUM_WRITERS-1),
data_available => data_available_dw_rw(0 to NUM_WRITERS-1),
start_hc => start_rw_dw(0 to NUM_WRITERS-1),
opcode_hc => opcode_rw_dw(0 to NUM_WRITERS-1),
ack_hc => ack_dw_rw(0 to NUM_WRITERS-1),
seq_nr_hc => seq_nr_rw_dw(0 to NUM_WRITERS-1),
done_hc => done_rw_dw(0 to NUM_WRITERS-1),
ret_hc => ret_dw_rw(0 to NUM_WRITERS-1),
get_data_hc => get_data_rw_dw(0 to NUM_WRITERS-1),
valid_in_hc => valid_dw_rw(0 to NUM_WRITERS-1),
ready_in_hc => ready_rw_dw(0 to NUM_WRITERS-1),
data_in_hc => data_dw_rw(0 to NUM_WRITERS-1),
last_word_in_hc => last_word_dw_rw(0 to NUM_WRITERS-1),
cc_instance_handle => cc_instance_handle_dw_rw(0 to NUM_WRITERS-1),
cc_kind => cc_kind_dw_rw(0 to NUM_WRITERS-1),
cc_source_timestamp => cc_source_timestamp_dw_rw(0 to NUM_WRITERS-1),
cc_seq_nr => cc_seq_nr_dw_rw(0 to NUM_WRITERS-1)
);
end generate;
dds_endpoint_w_if : if (NUM_WRITERS > 1) generate
dds_writer_inst : entity work.dds_writer(arch)
generic map (
NUM_WRITERS => NUM_WRITERS-1,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(NUM_READERS to NUM_ENDPOINTS-2))
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- TO/FROM RTPS ENDPOINT
start_rtps => start_rw_dw(0 to NUM_WRITERS-2),
opcode_rtps => opcode_rw_dw(0 to NUM_WRITERS-2),
ack_rtps => ack_dw_rw(0 to NUM_WRITERS-2),
done_rtps => done_rw_dw(0 to NUM_WRITERS-2),
ret_rtps => ret_dw_rw(0 to NUM_WRITERS-2),
seq_nr_rtps => seq_nr_rw_dw(0 to NUM_WRITERS-2),
get_data_rtps => get_data_rw_dw(0 to NUM_WRITERS-2),
valid_out_rtps => valid_dw_rw(0 to NUM_WRITERS-2),
ready_out_rtps => ready_rw_dw(0 to NUM_WRITERS-2),
data_out_rtps => data_dw_rw(0 to NUM_WRITERS-2),
last_word_out_rtps => last_word_dw_rw(0 to NUM_WRITERS-2),
liveliness_assertion => liveliness_assertion_dw_rw(0 to NUM_WRITERS-2),
data_available => data_available_dw_rw(0 to NUM_WRITERS-2),
-- Cache Change
cc_instance_handle => cc_instance_handle_dw_rw(0 to NUM_WRITERS-2),
cc_kind => cc_kind_dw_rw(0 to NUM_WRITERS-2),
cc_source_timestamp => cc_source_timestamp_dw_rw(0 to NUM_WRITERS-2),
cc_seq_nr => cc_seq_nr_dw_rw(0 to NUM_WRITERS-2),
-- TO/FROM USER ENTITY
start_dds => start_wi_dw(0 to NUM_WRITERS-2),
ack_dds => ack_dw_wi(0 to NUM_WRITERS-2),
opcode_dds => opcode_wi_dw(0 to NUM_WRITERS-2),
instance_handle_in_dds => instance_handle_wi_dw(0 to NUM_WRITERS-2),
source_ts_dds => source_ts_wi_dw(0 to NUM_WRITERS-2),
max_wait_dds => max_wait_wi_dw(0 to NUM_WRITERS-2),
done_dds => done_dw_wi(0 to NUM_WRITERS-2),
return_code_dds => return_code_dw_wi(0 to NUM_WRITERS-2),
instance_handle_out_dds => instance_handle_dw_wi(0 to NUM_WRITERS-2),
valid_in_dds => valid_wi_dw(0 to NUM_WRITERS-2),
ready_in_dds => ready_dw_wi(0 to NUM_WRITERS-2),
data_in_dds => data_wi_dw(0 to NUM_WRITERS-2),
last_word_in_dds => last_word_wi_dw(0 to NUM_WRITERS-2),
valid_out_dds => valid_dw_wi(0 to NUM_WRITERS-2),
ready_out_dds => ready_wi_dw(0 to NUM_WRITERS-2),
data_out_dds => data_dw_wi(0 to NUM_WRITERS-2),
last_word_out_dds => last_word_dw_wi(0 to NUM_WRITERS-2),
-- Communication Status
status => status_dw_wi(0 to NUM_WRITERS-2)
);
end generate;
dds_endpoint_r_if : if (NUM_READERS > 0) generate
dds_reader_inst : entity work.dds_reader(arch)
generic map (
NUM_READERS => NUM_READERS,
CONFIG_ARRAY => to_QUARTUS_CONFIG_ARRAY_TYPE(ENDPOINT_CONFIG(0 to NUM_READERS-1)),
MAX_REMOTE_ENDPOINTS => MAX_REMOTE_ENDPOINTS
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
time => time,
-- FROM RTPS ENDPOINT
start_rtps => start_rr_dr(0 to NUM_READERS-1),
opcode_rtps => opcode_rr_dr(0 to NUM_READERS-1),
ack_rtps => ack_dr_rr(0 to NUM_READERS-1),
done_rtps => done_dr_rr(0 to NUM_READERS-1),
ret_rtps => ret_dr_rr(0 to NUM_READERS-1),
valid_in_rtps => valid_rr_dr(0 to NUM_READERS-1),
ready_in_rtps => ready_dr_rr(0 to NUM_READERS-1),
data_in_rtps => data_rr_dr(0 to NUM_READERS-1),
last_word_in_rtps => last_word_rr_dr(0 to NUM_READERS-1),
-- TO USER ENTITY
start_dds => start_ri_dr(0 to NUM_READERS-1),
ack_dds => ack_dr_ri(0 to NUM_READERS-1),
opcode_dds => opcode_ri_dr(0 to NUM_READERS-1),
instance_state_dds => instance_state_ri_dr(0 to NUM_READERS-1),
view_state_dds => view_state_ri_dr(0 to NUM_READERS-1),
sample_state_dds => sample_state_ri_dr(0 to NUM_READERS-1),
instance_handle_dds => instance_handle_ri_dr(0 to NUM_READERS-1),
max_samples_dds => max_samples_ri_dr(0 to NUM_READERS-1),
get_data_dds => get_data_ri_dr(0 to NUM_READERS-1),
done_dds => done_dr_ri(0 to NUM_READERS-1),
return_code_dds => return_code_dr_ri(0 to NUM_READERS-1),
valid_out_dds => valid_dr_ri(0 to NUM_READERS-1),
ready_out_dds => ready_ri_dr(0 to NUM_READERS-1),
data_out_dds => data_dr_ri(0 to NUM_READERS-1),
last_word_out_dds => last_word_dr_ri(0 to NUM_READERS-1),
sample_info => sample_info_dr_ri(0 to NUM_READERS-1),
sample_info_valid => sample_info_valid_dr_ri(0 to NUM_READERS-1),
sample_info_ack => sample_info_ack_ri_dr(0 to NUM_READERS-1),
eoc => eoc_dr_ri(0 to NUM_READERS-1),
-- Communication Status
status => status_dr_ri(0 to NUM_READERS-1)
);
end generate;
ros_discovery_writer_inst : entity work.ros_static_discovery_writer(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- TO/FROM RTPS ENDPOINT
start => start_rw_dw(NUM_WRITERS-1),
opcode => opcode_rw_dw(NUM_WRITERS-1),
ack => ack_dw_rw(NUM_WRITERS-1),
done => done_rw_dw(NUM_WRITERS-1),
ret => ret_dw_rw(NUM_WRITERS-1),
seq_nr => seq_nr_rw_dw(NUM_WRITERS-1),
get_data => get_data_rw_dw(NUM_WRITERS-1),
valid_out => valid_dw_rw(NUM_WRITERS-1),
ready_out => ready_rw_dw(NUM_WRITERS-1),
data_out => data_dw_rw(NUM_WRITERS-1),
last_word_out => last_word_dw_rw(NUM_WRITERS-1),
liveliness_assertion => liveliness_assertion_dw_rw(NUM_WRITERS-1),
data_available => data_available_dw_rw(NUM_WRITERS-1),
-- Cache Change
cc_instance_handle => cc_instance_handle_dw_rw(NUM_WRITERS-1),
cc_kind => cc_kind_dw_rw(NUM_WRITERS-1),
cc_source_timestamp => cc_source_timestamp_dw_rw(NUM_WRITERS-1),
cc_seq_nr => cc_seq_nr_dw_rw(NUM_WRITERS-1)
);
fifo_in_ro_gen : for i in 0 to 2 generate
fifo_in_ro_if : if (i = 2) generate
fifo_in_ro_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_firo_rb,
write => write_rb_firo,
data_in(WORD_WIDTH-1 downto 0) => data_rb_firo,
data_in(WORD_WIDTH) => last_word_rb_firo,
-- OUTPUT
empty => empty_firo_ro(i),
read => read_ro_firo(i),
data_out(WORD_WIDTH) => last_word_firo_ro(i),
data_out(WORD_WIDTH-1 downto 0) => data_firo_ro(i),
-- MISC
free => open
);
else generate
fifo_in_ro_inst : configuration work.FWFT_FIFO_cfg
generic map (
FIFO_DEPTH => 2,
DATA_WIDTH => WORD_WIDTH+1
)
port map (
-- SYSTEM
reset => reset,
clk => clk,
-- INPUT
full => full_firo_re(i),
write => write_re_firo(i),
data_in(WORD_WIDTH-1 downto 0) => data_re_firo(i),
data_in(WORD_WIDTH) => last_word_re_firo(i),
-- OUTPUT
empty => empty_firo_ro(i),
read => read_ro_firo(i),
data_out(WORD_WIDTH) => last_word_firo_ro(i),
data_out(WORD_WIDTH-1 downto 0) => data_firo_ro(i),
-- MISC
free => open
);
end generate;
end generate;
rtps_out_inst : entity work.rtps_out(arch)
generic map (
RTPS_OUT_WIDTH => 3
)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- INPUT
empty => empty_firo_ro,
rd => read_ro_firo,
data_in => data_firo_ro,
last_word_in => last_word_firo_ro,
-- OUTPUT
full => full,
wr => write,
data_out => data_out
);
-- ######GENERATED START######
Type1_ros_sub_inst : entity work.Type1_ros_sub(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- FROM DDS READER
start_dds => start_ri_dr(0),
ack_dds => ack_dr_ri(0),
opcode_dds => opcode_ri_dr(0),
instance_state_dds => instance_state_ri_dr(0),
view_state_dds => view_state_ri_dr(0),
sample_state_dds => sample_state_ri_dr(0),
instance_handle_dds => instance_handle_ri_dr(0),
max_samples_dds => max_samples_ri_dr(0),
get_data_dds => get_data_ri_dr(0),
done_dds => done_dr_ri(0),
return_code_dds => return_code_dr_ri(0),
valid_in_dds => valid_dr_ri(0),
ready_in_dds => ready_ri_dr(0),
data_in_dds => data_dr_ri(0),
last_word_in_dds => last_word_dr_ri(0),
sample_info_dds => sample_info_dr_ri(0),
sample_info_valid_dds => sample_info_valid_dr_ri(0),
sample_info_ack_dds => sample_info_ack_ri_dr(0),
eoc_dds => eoc_dr_ri(0),
-- Communication Status
status_dds => status_dr_ri(0),
-- TO USER ENTITY
start_user => start_r,
ack_user => ack_r,
opcode_user => opcode_r,
done_user => done_r,
return_code_user => return_code_r,
data_available_user => data_available_r,
-- ###GENERATED START###
id => id_r,
a => a_r,
-- ###GENERATED END###
message_info_user => message_info_r,
taken_user => taken_r
);
Type1_ros_pub_inst : entity work.Type1_ros_pub(arch)
port map (
-- SYSTEM
clk => clk,
reset => reset,
-- FROM DDS WRITER
start_dds => start_wi_dw(0),
ack_dds => ack_dw_wi(0),
opcode_dds => opcode_wi_dw(0),
instance_handle_in_dds => instance_handle_wi_dw(0),
source_ts_dds => source_ts_wi_dw(0),
max_wait_dds => max_wait_wi_dw(0),
done_dds => done_dw_wi(0),
return_code_dds => return_code_dw_wi(0),
instance_handle_out_dds => instance_handle_dw_wi(0),
valid_out_dds => valid_wi_dw(0),
ready_out_dds => ready_dw_wi(0),
data_out_dds => data_wi_dw(0),
last_word_out_dds => last_word_wi_dw(0),
valid_in_dds => valid_dw_wi(0),
ready_in_dds => ready_wi_dw(0),
data_in_dds => data_dw_wi(0),
last_word_in_dds => last_word_dw_wi(0),
-- Communication Status
status_dds => status_dw_wi(0),
-- TO USER ENTITY
start_user => start_w,
ack_user => ack_w,
opcode_user => opcode_w,
-- ###GENERATED START###
id => id_w,
a => a_w,
-- ###GENERATED END###
done_user => done_w,
return_code_user => return_code_w
);
-- ######GENERATED END######
end architecture;

View File

@ -0,0 +1,98 @@
-- altera vhdl_input_version vhdl_2008
-- XXX: QSYS Fix (https://www.intel.com/content/www/us/en/support/programmable/articles/000079458.html)
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.rtps_package.all;
use work.ros_package.all;
use work.Type1_package.all;
package ros_config is
-- Period of ros system clock
constant ROS_CLOCK_PERIOD : time := 50 ns;
-- IPv4 Address of ROS System [Default 192.168.0.134]
constant ROS_ADDRESS : std_logic_vector(IPv4_ADDRESS_WIDTH-1 downto 0) := x"C0A80085";
-- Random Key used to generate GUIDs
constant ROS_RAND_KEY : std_logic_vector(47 downto 0) := x"8BD9DA5FB97D";
constant NUM_NODES : natural := 1;
constant ROS_NODES : ROS_NODE_ARRAY_TYPE(0 to NUM_NODES-1) := (
0 => (
name => gen_user_string("test_loopback_client"),
namespace => gen_user_string(""),
domain_id => 0,
NUM_PUBS => 1,
NUM_SUBS => 1,
NUM_SERVICES => 0,
NUM_ACTIONS => 0
)
);
constant NUM_PUBS : natural := get_num_pubs(ROS_NODES);
constant NUM_SUBS : natural := get_num_subs(ROS_NODES);
constant NUM_SERVICES : natural := get_num_services(ROS_NODES);
constant NUM_ACTIONS : natural := get_num_actions(ROS_NODES);
constant ROS_PUBLICATIONS : ROS_TOPIC_ARRAY_TYPE(0 to NUM_PUBS-1) := (
0 => (
node_id => 0,
TOPICNAME => gen_user_string("Loopback_1"),
TYPENAME => gen_user_string("tutorial_interfaces::msg::dds_::Type1_"),
QOS => ROS_QOS_PROFILE_TRANSIENT,
MAX_SIZE => MAX_TYPE1_SIZE
)
);
constant ROS_SUBSCRIPTIONS : ROS_TOPIC_ARRAY_TYPE(0 to NUM_SUBS-1) := (
0 => (
node_id => 0,
TOPICNAME => gen_user_string("Loopback_2"),
TYPENAME => gen_user_string("tutorial_interfaces::msg::dds_::Type1_"),
QOS => ROS_QOS_PROFILE_TRANSIENT,
MAX_SIZE => MAX_TYPE1_SIZE
)
);
constant ROS_SERVICES : ROS_SERVICE_ARRAY_TYPE(0 to NUM_SERVICES-1) := (
others => (
node_id => 0,
SERVICENAME => gen_user_string(""),
RQ_TYPENAME => gen_user_string(""),
RR_TYPENAME => gen_user_string(""),
QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
MAX_RQ_SIZE => 0,
MAX_RR_SIZE => 0,
is_client => FALSE
)
);
constant ROS_ACTIONS : ROS_ACTION_ARRAY_TYPE(0 to NUM_ACTIONS-1) := (
others => (
node_id => 0,
ACTIONNAME => gen_user_string(""),
GOAL_RQ_TYPENAME => gen_user_string(""),
GOAL_RR_TYPENAME => gen_user_string(""),
RESULT_RQ_TYPENAME => gen_user_string(""),
RESULT_RR_TYPENAME => gen_user_string(""),
FEEDBACK_TYPENAME => gen_user_string(""),
GOAL_QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
RESULT_QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
FEEDBACK_QOS => ROS_QOS_PROFILE_DEFAULT,
CANCEL_QOS => ROS_QOS_PROFILE_SERVICES_DEFAULT,
MAX_GOAL_RQ_SIZE => 0,
MAX_GOAL_RR_SIZE => 0,
MAX_RESULT_RQ_SIZE => 0,
MAX_RESULT_RR_SIZE => 0,
MAX_FEEDBACK_SIZE => 0,
is_client => FALSE,
enable_feedback => TRUE
)
);
-- Defines sensible RTPS timings for simulation
constant SIMULATION_TIMING : boolean := TRUE;
end package;

5
src/ros2/Tests/Type1.idl Normal file
View File

@ -0,0 +1,5 @@
@extensibility(FINAL)
struct Type1 {
long id;
long a;
};

View File

@ -0,0 +1,14 @@
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.math_pkg.all;
use work.rtps_package.all;
package Type1_package is
constant MAX_ID_SIZE : natural := 4;
constant MAX_A_SIZE : natural := 4; -- 8
constant MAX_TYPE1_SIZE : natural := 8 + RTPS_PAYLOAD_HEADER_SIZE;
end package;

View File

@ -0,0 +1,269 @@
-- altera vhdl_input_version vhdl_2008
-- XXX: QSYS Fix (https://www.intel.com/content/www/us/en/support/programmable/articles/000079458.html)
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.rtps_package.all;
use work.rtps_config_package.all;
use work.ros_package.all;
use work.Type1_package.all;
entity Type1_ros_pub is
generic (
LITTLE_ENDIAN : std_logic := '0'
);
port (
-- SYSTEM
clk : in std_logic;
reset : in std_logic;
-- FROM DDS WRITER
start_dds : out std_logic;
ack_dds : in std_logic;
opcode_dds : out DDS_WRITER_OPCODE_TYPE;
instance_handle_in_dds : out INSTANCE_HANDLE_TYPE;
source_ts_dds : out TIME_TYPE;
max_wait_dds : out DURATION_TYPE;
done_dds : in std_logic;
return_code_dds : in std_logic_vector(RETURN_CODE_WIDTH-1 downto 0);
instance_handle_out_dds : in INSTANCE_HANDLE_TYPE;
valid_out_dds : out std_logic;
ready_out_dds : in std_logic;
data_out_dds : out std_logic_vector(WORD_WIDTH-1 downto 0);
last_word_out_dds : out std_logic;
valid_in_dds : in std_logic;
ready_in_dds : out std_logic;
data_in_dds : in std_logic_vector(WORD_WIDTH-1 downto 0);
last_word_in_dds : in std_logic;
-- Communication Status
status_dds : in std_logic_vector(STATUS_KIND_WIDTH-1 downto 0);
-- TO USER ENTITY
start_user : in std_logic;
opcode_user : in ROS_TOPIC_OPCODE_TYPE;
ack_user : out std_logic;
-- ###GENERATED START###
id : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
a : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
-- ###GENERATED END###
done_user : out std_logic;
return_code_user : out std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0)
);
end entity;
architecture arch of Type1_ros_pub is
--*****TYPE DECLARATION*****
-- FSM states. Explained below in detail
type STAGE_TYPE is (IDLE,INITIATE_WRITE,WRITE_PAYLOAD_HEADER,PUSH,ALIGN_STREAM,ENCODE_PAYLOAD,WAIT_FOR_WRITER,RETURN_ROS);
-- ###GENERATED START###
type ENCODE_STAGE_TYPE is (WRITE_ID, WRITE_A);
-- ###GENERATED END###
-- *MAIN PROCESS*
signal stage, stage_next : STAGE_TYPE;
signal cnt, cnt_next : natural range 0 to 5;
signal align_offset, align_offset_next : unsigned(MAX_ALIGN_OFFSET_WIDTH-1 downto 0);
signal align_op, align_op_next : std_logic;
signal target_align, target_align_next : ALIGN_TYPE;
signal data_out_latch, data_out_latch_next : std_logic_vector(WORD_WIDTH-1 downto 0);
signal abort_mem : std_logic;
signal finalize_payload, finalize_payload_next : std_logic;
signal return_code_latch, return_code_latch_next : std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0);
signal encode_stage, encode_stage_next : ENCODE_STAGE_TYPE;
begin
-- PASSTHROUGH
instance_handle_in_dds <= HANDLE_NIL;
source_ts_dds <= TIME_INVALID;
max_wait_dds <= DURATION_ZERO;
ready_in_dds <= '0'; -- DDS Writer Input is unused
-- ###GENERATED START###
-- PORT SIGNAL CONNECTIONS
-- ###GENERATED END###
main_prc : process (all)
begin
-- DEFAULT
stage_next <= stage;
encode_stage_next <= encode_stage;
cnt_next <= cnt;
align_offset_next <= align_offset;
align_op_next <= align_op;
target_align_next <= target_align;
data_out_latch_next <= data_out_latch;
finalize_payload_next <= finalize_payload;
return_code_latch_next <= return_code_latch;
abort_mem <= '0';
start_dds <= '0';
opcode_dds <= NOP;
valid_out_dds <= '0';
last_word_out_dds <= '0';
ack_user <= '0';
done_user <= '0';
return_code_user <= ROS_RET_OK;
data_out_dds <= (others => '0');
case (stage) is
when IDLE =>
if (start_user = '1') then
ack_user <= '1';
case (opcode_user) is
when PUBLISH =>
stage_next <= INITIATE_WRITE;
when others =>
return_code_latch_next <= ROS_RET_UNSUPPORTED;
stage_next <= RETURN_ROS;
end case;
-- RESET
abort_mem <= '1';
else
null;
end if;
when RETURN_ROS =>
done_user <= '1';
return_code_user <= return_code_latch;
-- DONE
stage_next <= IDLE;
when INITIATE_WRITE =>
start_dds <= '1';
opcode_dds <= WRITE;
if (ack_dds = '1') then
stage_next <= WRITE_PAYLOAD_HEADER;
end if;
when WRITE_PAYLOAD_HEADER =>
valid_out_dds <= '1';
if (LITTLE_ENDIAN = '0') then
data_out_dds <= CDR_BE & x"0000";
else
data_out_dds <= CDR_LE & x"0000";
end if;
-- Output Guard
if (ready_out_dds = '1') then
stage_next <= ENCODE_PAYLOAD;
-- Reset
align_offset_next <= (others => '0');
data_out_latch_next <= (others => '0');
-- ###GENERATED START###
encode_stage_next <= WRITE_ID;
-- ###GENERATED END###
end if;
when PUSH =>
-- Mark Last Word
if (finalize_payload = '1') then
last_word_out_dds <= '1';
end if;
valid_out_dds <= '1';
data_out_dds <= data_out_latch;
-- Output Guard
if (ready_out_dds = '1') then
-- NOTE: Ensures all padding is zero.
data_out_latch_next <= (others => '0');
-- Alignment Operation in process
if (align_op = '1') then
stage_next <= ALIGN_STREAM;
-- Reset
align_op_next <= '0';
-- DONE
elsif (finalize_payload = '1') then
finalize_payload_next <= '0';
stage_next <= WAIT_FOR_WRITER;
else
stage_next <= ENCODE_PAYLOAD;
end if;
end if;
when ALIGN_STREAM =>
-- Target Stream Alignment reached
if (check_align(align_offset, target_align)) then
-- DONE
stage_next <= ENCODE_PAYLOAD;
else
align_offset_next <= align_offset + 1;
-- Need to push Word
if (align_offset(1 downto 0) = "11") then
align_op_next <= '1';
stage_next <= PUSH;
end if;
end if;
when ENCODE_PAYLOAD =>
case (encode_stage) is
-- ###GENERATED START###
when WRITE_ID =>
-- ALIGN GUARD
if (not check_align(align_offset, ALIGN_4)) then
target_align_next <= ALIGN_4;
stage_next <= ALIGN_STREAM;
else
data_out_latch_next <= endian_swap(LITTLE_ENDIAN,id);
align_offset_next <= align_offset + 4;
stage_next <= PUSH;
-- Next Member
encode_stage_next <= WRITE_A;
end if;
when WRITE_A =>
-- ALIGN GUARD
if (not check_align(align_offset, ALIGN_4)) then
target_align_next <= ALIGN_4;
stage_next <= ALIGN_STREAM;
else
data_out_latch_next <= endian_swap(LITTLE_ENDIAN,a);
align_offset_next <= align_offset + 4;
-- DONE
stage_next <= PUSH;
finalize_payload_next <= '1';
end if;
-- ###GENERATED END###
when others =>
null;
end case;
when WAIT_FOR_WRITER =>
if (done_dds = '1') then
case (return_code_dds) is
when RETCODE_OK =>
return_code_latch_next <= ROS_RET_OK;
stage_next <= RETURN_ROS;
when others =>
return_code_latch_next <= ROS_RET_ERROR;
stage_next <= RETURN_ROS;
end case;
end if;
end case;
end process;
sync_prc : process(clk)
begin
if rising_edge(clk) then
if (reset = '1') then
stage <= IDLE;
encode_stage <= WRITE_ID;
target_align <= ALIGN_1;
return_code_latch <= ROS_RET_OK;
cnt <= 0;
finalize_payload <= '0';
align_op <= '0';
align_offset <= (others => '0');
data_out_latch <= (others => '0');
else
stage <= stage_next;
encode_stage <= encode_stage_next;
target_align <= target_align_next;
return_code_latch <= return_code_latch_next;
cnt <= cnt_next;
finalize_payload <= finalize_payload_next;
align_op <= align_op_next;
align_offset <= align_offset_next;
data_out_latch <= data_out_latch_next;
end if;
end if;
end process;
end architecture;

View File

@ -0,0 +1,440 @@
-- altera vhdl_input_version vhdl_2008
-- XXX: QSYS Fix (https://www.intel.com/content/www/us/en/support/programmable/articles/000079458.html)
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.rtps_package.all;
use work.rtps_config_package.all;
use work.ros_package.all;
use work.Type1_package.all;
entity Type1_ros_sub is
port (
-- SYSTEM
clk : in std_logic;
reset : in std_logic;
-- FROM DDS READER
start_dds : out std_logic;
ack_dds : in std_logic;
opcode_dds : out DDS_READER_OPCODE_TYPE;
instance_state_dds : out std_logic_vector(INSTANCE_STATE_KIND_WIDTH-1 downto 0);
view_state_dds : out std_logic_vector(VIEW_STATE_KIND_WIDTH-1 downto 0);
sample_state_dds : out std_logic_vector(SAMPLE_STATE_KIND_WIDTH-1 downto 0);
instance_handle_dds : out INSTANCE_HANDLE_TYPE;
max_samples_dds : out std_logic_vector(MAX_SAMPLES_WIDTH-1 downto 0);
get_data_dds : out std_logic;
done_dds : in std_logic;
return_code_dds : in std_logic_vector(RETURN_CODE_WIDTH-1 downto 0);
valid_in_dds : in std_logic;
ready_in_dds : out std_logic;
data_in_dds : in std_logic_vector(WORD_WIDTH-1 downto 0);
last_word_in_dds : in std_logic;
sample_info_dds : in SAMPLE_INFO_TYPE;
sample_info_valid_dds : in std_logic;
sample_info_ack_dds : out std_logic;
eoc_dds : in std_logic;
-- Communication Status
status_dds : in std_logic_vector(STATUS_KIND_WIDTH-1 downto 0);
-- TO USER ENTITY
start_user : in std_logic;
opcode_user : in ROS_TOPIC_OPCODE_TYPE;
ack_user : out std_logic;
done_user : out std_logic;
return_code_user : out std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0);
data_available_user : out std_logic;
-- ###GENERATED START###
id : out std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
a : out std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
-- ###GENERATED END###
message_info_user : out MESSAGE_INFO_TYPE;
taken_user : out std_logic
);
end entity;
architecture arch of Type1_ros_sub is
--*****TYPE DECLARATION*****
-- FSM states. Explained below in detail
type STAGE_TYPE is (IDLE,INITIATE_READ,WAIT_FOR_READER,WAIT_FOR_DATA,GET_PAYLOAD_HEADER,FETCH,ALIGN_STREAM,SKIP_PAYLOAD,DECODE_PAYLOAD,RETURN_ROS);
-- ###GENERATED START###
type DECODE_STAGE_TYPE is (GET_ID, GET_A, GET_OPTIONAL_HEADER);
-- ###GENERATED END###
-- *MAIN PROCESS*
signal stage, stage_next : STAGE_TYPE;
signal cnt, cnt_next : natural range 0 to 5;
signal endian_flag, endian_flag_next : std_logic;
signal last_word_in_latch, last_word_in_latch_next : std_logic;
signal decode_error_latch, decode_error_latch_next : std_logic;
signal align_offset, align_offset_next : unsigned(MAX_ALIGN_OFFSET_WIDTH-1 downto 0);
signal align_op, align_op_next : std_logic;
signal target_align, target_align_next : ALIGN_TYPE;
signal data_in_latch, data_in_latch_next : std_logic_vector(WORD_WIDTH-1 downto 0);
signal optional, optional_next : std_logic;
signal abort_mem : std_logic;
signal ready_in_dds_sig : std_logic;
signal taken_sig, taken_sig_next : std_logic;
signal data_available_sig, data_available_sig_next : std_logic;
signal message_info_sig, message_info_sig_next : MESSAGE_INFO_TYPE;
signal return_code_latch, return_code_latch_next : std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0);
signal decode_stage, decode_stage_next : DECODE_STAGE_TYPE;
signal return_stage, return_stage_next : DECODE_STAGE_TYPE;
-- ###GENERATED START###
signal id_latch, id_latch_next : std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
signal a_latch, a_latch_next : std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
-- ###GENERATED END###
--*****ALIAS DECLARATION*****
alias representation_id : std_logic_vector(PAYLOAD_REPRESENTATION_ID_WIDTH-1 downto 0) is data_in_dds(WORD_WIDTH-1 downto WORD_WIDTH-PAYLOAD_REPRESENTATION_ID_WIDTH);
alias representation_options : std_logic_vector(PAYLOAD_REPRESENTATION_ID_WIDTH-1 downto 0) is data_in_dds(PAYLOAD_REPRESENTATION_OPTIONS_WIDTH-1 downto 0);
alias parameter_id : std_logic_vector(PARAMETER_ID_WIDTH-1 downto 0) is data_in_latch(WORD_WIDTH-1 downto WORD_WIDTH-PARAMETER_ID_WIDTH);
alias parameter_length : std_logic_vector(PARAMETER_LENGTH_WIDTH-1 downto 0) is data_in_latch(PARAMETER_LENGTH_WIDTH-1 downto 0);
begin
-- PASSTHROUGH
taken_user <= taken_sig;
ready_in_dds <= ready_in_dds_sig;
message_info_user <= message_info_sig;
data_available_user <= data_available_sig;
instance_state_dds <= ANY_INSTANCE_STATE;
view_state_dds <= ANY_VIEW_STATE;
sample_state_dds <= ANY_SAMPLE_STATE;
instance_handle_dds <= HANDLE_NIL;
max_samples_dds <= (others => '0');
-- ###GENERATED START###
id <= id_latch;
a <= a_latch;
-- ###GENERATED END###
main_prc : process (all)
variable tmp_length : unsigned(WORD_WIDTH-1 downto 0);
begin
-- DEFAULT
stage_next <= stage;
decode_stage_next <= decode_stage;
return_stage_next <= return_stage;
cnt_next <= cnt;
endian_flag_next <= endian_flag;
last_word_in_latch_next <= last_word_in_latch;
decode_error_latch_next <= decode_error_latch;
align_offset_next <= align_offset;
target_align_next <= target_align;
optional_next <= optional;
taken_sig_next <= taken_sig;
data_in_latch_next <= data_in_latch;
align_op_next <= align_op;
data_available_sig_next <= data_available_sig;
return_code_latch_next <= return_code_latch;
message_info_sig_next <= message_info_sig;
abort_mem <= '0';
ready_in_dds_sig <= '0';
sample_info_ack_dds <= '0';
get_data_dds <= '0';
start_dds <= '0';
opcode_dds <= NOP;
ack_user <= '0';
done_user <= '0';
return_code_user <= ROS_RET_OK;
-- ###GENERATED START###
id_latch_next <= id_latch;
a_latch_next <= a_latch;
-- ###GENERATED END###
-- Last Word Latch Setter
if (last_word_in_dds = '1' and valid_in_dds = '1') then
last_word_in_latch_next <= '1';
end if;
-- Data Available Setter
if (check_mask(status_dds, DATA_AVAILABLE_STATUS)) then
data_available_sig_next <= '1';
end if;
case (stage) is
when IDLE =>
if (start_user = '1') then
ack_user <= '1';
case (opcode_user) is
when TAKE =>
stage_next <= INITIATE_READ;
when others =>
return_code_latch_next <= ROS_RET_UNSUPPORTED;
stage_next <= RETURN_ROS;
end case;
-- RESET
taken_sig_next <= '0';
abort_mem <= '1';
else
null;
end if;
when RETURN_ROS =>
done_user <= '1';
return_code_user <= return_code_latch;
-- DONE
stage_next <= IDLE;
when INITIATE_READ =>
start_dds <= '1';
opcode_dds <= TAKE_NEXT_SAMPLE;
if (ack_dds = '1') then
stage_next <= WAIT_FOR_READER;
end if;
when WAIT_FOR_READER =>
if (done_dds = '1') then
case (return_code_dds) is
when RETCODE_OK =>
stage_next <= WAIT_FOR_DATA;
when RETCODE_NO_DATA =>
assert (taken_sig = '0') severity FAILURE;
-- Data Available Resetter
data_available_sig_next <= '0';
return_code_latch_next <= ROS_RET_OK;
stage_next <= RETURN_ROS;
when others =>
return_code_latch_next <= ROS_RET_ERROR;
stage_next <= RETURN_ROS;
end case;
end if;
when WAIT_FOR_DATA =>
if (sample_info_valid_dds = '1') then
sample_info_ack_dds <= '1';
-- Meta Sample
if (sample_info_dds.valid_data = '0') then
-- Ignore and read Next Sample
stage_next <= INITIATE_READ;
else
get_data_dds <= '1';
stage_next <= GET_PAYLOAD_HEADER;
message_info_sig_next.publisher_gid <= to_gid(GUID_UNKNOWN);
message_info_sig_next.received_timestamp <= TIME_INVALID;
message_info_sig_next.source_timestamp <= sample_info_dds.source_timestamp;
end if;
end if;
when GET_PAYLOAD_HEADER =>
-- TODO: Latch Offset from Options Field?
ready_in_dds_sig <= '1';
-- Input Guard
if (valid_in_dds = '1') then
case (representation_id) is
when CDR_BE =>
endian_flag_next <= '0';
stage_next <= FETCH;
-- Alignment Reset
align_offset_next <= (others => '0');
-- ###GENERATED START###
decode_stage_next <= GET_ID;
-- ###GENERATED END###
-- Initial Fetch
when CDR_LE =>
endian_flag_next <= '1';
stage_next <= FETCH;
-- Alignment Reset
align_offset_next <= (others => '0');
-- ###GENERATED START###
decode_stage_next <= GET_ID;
-- ###GENERATED END###
when others =>
-- Unknown Payload Encoding
stage_next <= SKIP_PAYLOAD;
decode_error_latch_next <= '1';
end case;
end if;
when FETCH =>
ready_in_dds_sig <= '1';
-- Input Guard
if (valid_in_dds = '1') then
data_in_latch_next <= data_in_dds;
-- Alignment Operation in progress
if (align_op = '1') then
stage_next <= ALIGN_STREAM;
-- Reset
align_op_next <= '0';
else
stage_next <= DECODE_PAYLOAD;
end if;
end if;
when ALIGN_STREAM =>
-- Target Stream Alignment reached
if (check_align(align_offset, target_align)) then
-- DONE
stage_next <= DECODE_PAYLOAD;
else
align_offset_next <= align_offset + 1;
-- Need to fetch new Input Word
if (align_offset(1 downto 0) = "11") then
align_op_next <= '1';
stage_next <= FETCH;
end if;
end if;
when DECODE_PAYLOAD =>
case (decode_stage) is
-- ###GENERATED START###
when GET_ID =>
-- ALIGN GUARD
if (not check_align(align_offset, ALIGN_4)) then
target_align_next <= ALIGN_4;
stage_next <= ALIGN_STREAM;
else
id_latch_next <= endian_swap(endian_flag, data_in_latch);
align_offset_next <= align_offset + 4;
stage_next <= FETCH;
-- Next Member
decode_stage_next <= GET_A;
end if;
when GET_A =>
-- ALIGN GUARD
if (not check_align(align_offset, ALIGN_4)) then
target_align_next <= ALIGN_4;
stage_next <= ALIGN_STREAM;
else
a_latch_next <= endian_swap(endian_flag, data_in_latch);
align_offset_next <= align_offset + 4;
stage_next <= FETCH;
-- Next Member
stage_next <= SKIP_PAYLOAD;
end if;
-- ###GENERATED END###
when GET_OPTIONAL_HEADER =>
-- ALIGN GUARD
if (not check_align(align_offset, ALIGN_4)) then
target_align_next <= ALIGN_4;
stage_next <= ALIGN_STREAM;
else
case (cnt) is
-- Optional Member Header
when 0 =>
-- Extended Parameter Header
if (endian_swap(endian_flag,parameter_id) = PID_EXTENDED) then
cnt_next <= cnt + 1;
stage_next <= FETCH;
else
stage_next <= FETCH;
decode_stage_next <= return_stage;
cnt_next <= 0;
-- Alignment Reset
align_offset_next <= (others => '0');
-- Optional omitted
if(endian_swap(endian_flag,parameter_length) = (parameter_length'reverse_range => '0')) then
optional_next <= '0';
else
optional_next <= '1';
end if;
end if;
-- eMemberHeader
when 1 =>
-- Ignore Parameter ID
cnt_next <= cnt + 1;
stage_next <= FETCH;
-- Llength
when 2 =>
stage_next <= FETCH;
decode_stage_next <= return_stage;
cnt_next <= 0;
-- Alignment Reset
align_offset_next <= (others => '0');
-- Optional omitted
if(endian_swap(endian_flag, data_in_dds) = (data_in_dds'reverse_range => '0')) then
optional_next <= '0';
else
optional_next <= '1';
end if;
when others =>
null;
end case;
end if;
when others =>
null;
end case;
when SKIP_PAYLOAD =>
if (last_word_in_latch = '0') then
-- Skip Read
ready_in_dds_sig <= '1';
else
-- Reset
last_word_in_latch_next <= '0';
-- If no Decode Error, mark output as valid
if (decode_error_latch = '0') then
taken_sig_next <= '1';
return_code_latch_next <= ROS_RET_OK;
else
taken_sig_next <= '0';
return_code_latch_next <= ROS_RET_ERROR;
end if;
stage_next <= RETURN_ROS;
end if;
end case;
-- OVERREAD GUARD
-- Attempted read on empty input
if (last_word_in_latch = '1' and last_word_in_dds = '0' and ready_in_dds_sig = '1') then
stage_next <= SKIP_PAYLOAD;
decode_error_latch_next <= '1';
end if;
end process;
sync_prc : process(clk)
begin
if rising_edge(clk) then
if (reset = '1') then
stage <= IDLE;
decode_stage <= GET_ID;
return_stage <= GET_ID;
target_align <= ALIGN_1;
return_code_latch <= ROS_RET_OK;
message_info_sig <= EMPTY_MESSAGE_INFO;
cnt <= 0;
endian_flag <= '0';
last_word_in_latch <= '0';
decode_error_latch <= '0';
optional <= '0';
taken_sig <= '0';
align_op <= '0';
data_available_sig <= '0';
align_offset <= (others => '0');
data_in_latch <= (others => '0');
-- ###GENERATED START###
id_latch <= (others => '0');
a_latch <= (others => '0');
-- ###GENERATED END###
else
stage <= stage_next;
decode_stage <= decode_stage_next;
return_stage <= return_stage_next;
target_align <= target_align_next;
return_code_latch <= return_code_latch_next;
message_info_sig <= message_info_sig_next;
cnt <= cnt_next;
endian_flag <= endian_flag_next;
last_word_in_latch <= last_word_in_latch_next;
decode_error_latch <= decode_error_latch_next;
optional <= optional_next;
taken_sig <= taken_sig_next;
align_op <= align_op_next;
data_available_sig <= data_available_sig_next;
align_offset <= align_offset_next;
data_in_latch <= data_in_latch_next;
-- ###GENERATED START###
id_latch <= id_latch_next;
a_latch <= a_latch_next;
-- ###GENERATED END###
end if;
end if;
end process;
end architecture;

View File

@ -201,6 +201,101 @@ analyze ../example_interfaces/Fibonacci_ros_action_client.vhd
analyze ../example_interfaces/Fibonacci_ros_action_server.vhd
analyze Level_2/L2_Testbench_ROS_Lib5.vhd
library Testbench_ROS_Lib6
analyze ../../math_pkg.vhd
analyze ../../rtps_package.vhd
analyze ../ros_package.vhd
analyze ../rcl_interfaces/action_msgs/GoalInfo_package.vhd
analyze ../rcl_interfaces/action_msgs/GoalStatus_package.vhd
analyze ../rcl_interfaces/action_msgs/GoalStatusArray_package.vhd
analyze ../rcl_interfaces/action_msgs/CancelGoal_package.vhd
analyze Type1_package.vhd
analyze Level_2/L2_Testbench_ROS_Lib6_config.vhd
analyze ../dds_user_config.vhd
analyze ../../rtps_config_package.vhd
analyze ../../rtps_test_package.vhd
analyze ../ros_config_package.vhd
analyze ../../single_port_ram.vhd
analyze ../../single_port_ram_Altera.vhd
analyze ../../single_port_ram_cfg.vhd
analyze ../../dual_port_ram.vhd
analyze ../../dual_port_ram_Altera.vhd
analyze ../../dual_port_ram_cfg.vhd
analyze ../../FWFT_FIFO.vhd
analyze ../../FWFT_FIFO_Altera.vhd
analyze ../../FWFT_FIFO_cfg.vhd
analyze ../../vector_FIFO.vhd
analyze ../../mem_ctrl.vhd
analyze ../../dp_mem_ctrl.vhd
analyze ../../moving_average.vhd
analyze ../../moving_average_wrapper.vhd
analyze ../../rtps_handler.vhd
analyze ../../rtps_discovery_module.vhd
analyze ../../rtps_out.vhd
analyze ../../rtps_reader.vhd
analyze ../../rtps_writer.vhd
analyze ../../dds_writer.vhd
analyze ../../dds_reader.vhd
analyze ../../key_holder.vhd
analyze ../../key_hash_generator.vhd
analyze ../../Tests/test_key_holder.vhd
analyze ../../Tests/test_key_hash_generator.vhd
analyze ../../mult.vhd
analyze ../../mult_Altera.vhd
analyze ../../mult_cfg.vhd
analyze ../ros_time_converter.vhd
analyze ../ros_static_discovery_writer.vhd
analyze Type1_ros_pub.vhd
analyze Type1_ros_sub.vhd
analyze test_loopback_util.vhd
analyze Level_2/L2_Testbench_ROS_Lib6.vhd
library Testbench_ROS_Lib7
analyze ../../math_pkg.vhd
analyze ../../rtps_package.vhd
analyze ../ros_package.vhd
analyze ../rcl_interfaces/action_msgs/GoalInfo_package.vhd
analyze ../rcl_interfaces/action_msgs/GoalStatus_package.vhd
analyze ../rcl_interfaces/action_msgs/GoalStatusArray_package.vhd
analyze ../rcl_interfaces/action_msgs/CancelGoal_package.vhd
analyze Type1_package.vhd
analyze Level_2/L2_Testbench_ROS_Lib7_config.vhd
analyze ../dds_user_config.vhd
analyze ../../rtps_config_package.vhd
analyze ../../rtps_test_package.vhd
analyze ../ros_config_package.vhd
analyze ../../single_port_ram.vhd
analyze ../../single_port_ram_Altera.vhd
analyze ../../single_port_ram_cfg.vhd
analyze ../../dual_port_ram.vhd
analyze ../../dual_port_ram_Altera.vhd
analyze ../../dual_port_ram_cfg.vhd
analyze ../../FWFT_FIFO.vhd
analyze ../../FWFT_FIFO_Altera.vhd
analyze ../../FWFT_FIFO_cfg.vhd
analyze ../../vector_FIFO.vhd
analyze ../../mem_ctrl.vhd
analyze ../../dp_mem_ctrl.vhd
analyze ../../rtps_handler.vhd
analyze ../../rtps_discovery_module.vhd
analyze ../../rtps_out.vhd
analyze ../../rtps_reader.vhd
analyze ../../rtps_writer.vhd
analyze ../../dds_writer.vhd
analyze ../../dds_reader.vhd
analyze ../../key_holder.vhd
analyze ../../key_hash_generator.vhd
analyze ../../Tests/test_key_holder.vhd
analyze ../../Tests/test_key_hash_generator.vhd
analyze ../../mult.vhd
analyze ../../mult_Altera.vhd
analyze ../../mult_cfg.vhd
analyze ../ros_time_converter.vhd
analyze ../ros_static_discovery_writer.vhd
analyze Type1_ros_pub.vhd
analyze Type1_ros_sub.vhd
analyze Level_2/L2_Testbench_ROS_Lib7.vhd
library Testbench_ROS_Lib1
analyze ../../math_pkg.vhd
analyze ../../rtps_package.vhd
@ -252,6 +347,7 @@ analyze Level_0/L0_ros_action_server_test2.vhd
analyze Level_1/L1_Fibonacci_ros_action_test1.vhd
analyze Level_1/L1_Fibonacci_ros_action_test2.vhd
analyze Level_2/L2_Fibonacci_ros_action_test1.vhd
analyze Level_2/L2_ROS_Loopback_test1.vhd
simulate L1_AddTwoInts_ros_srv_test1
@ -271,4 +367,5 @@ simulate L0_ros_action_server_test1
simulate L0_ros_action_server_test2
simulate L1_Fibonacci_ros_action_test1
simulate L1_Fibonacci_ros_action_test2
simulate L2_Fibonacci_ros_action_test1
simulate L2_Fibonacci_ros_action_test1
simulate L2_ROS_Loopback_test1

View File

@ -0,0 +1,268 @@
-- altera vhdl_input_version vhdl_2008
-- XXX: QSYS Fix (https://www.intel.com/content/www/us/en/support/programmable/articles/000079458.html)
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use work.rtps_package.all;
use work.rtps_config_package.all;
use work.user_config.all;
use work.ros_package.all;
entity test_loopback_util is
port (
-- SYSTEM
clk : in std_logic;
reset : in std_logic;
-- UTILIZATION
input_util : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
output_util : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
-- READER
start_r : out std_logic;
opcode_r : out ROS_TOPIC_OPCODE_TYPE;
ack_r : in std_logic;
done_r : in std_logic;
return_code_r : in std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0);
data_available_r : in std_logic;
id_r : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
a_r : in std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
message_info_r : in MESSAGE_INFO_TYPE;
taken_r : in std_logic;
-- WRITER
start_w : out std_logic;
opcode_w : out ROS_TOPIC_OPCODE_TYPE;
ack_w : in std_logic;
id_w : out std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
a_w : out std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
done_w : in std_logic;
return_code_w : in std_logic_vector(ROS_RETCODE_WIDTH-1 downto 0)
);
end entity;
architecture arch of test_loopback_util is
--*****TYPE DECLARATION*****
type STAGE_TYPE is (IDLE, READ, WRITE);
function gen_window_size return natural is
variable ret : natural := 0;
begin
if (SIMULATION_FLAG) then
ret := 64;
else
ret := 8192;
end if;
return ret;
end function;
constant WINDOW_SIZE : natural := gen_window_size;
--*****SIGNAL DECLARATION*****
signal stage, stage_next : STAGE_TYPE;
signal cnt, cnt_next : natural range 0 to 1;
signal id_latch, id_latch_next, a_latch, a_latch_next : std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
signal input_average, input_average_latch : std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
signal output_average, output_average_latch : std_logic_vector(CDR_LONG_WIDTH-1 downto 0);
signal input_trigger, input_trigger_latch, input_trigger_latch_next, input_overflow, input_overflow_latch : std_logic;
signal output_trigger, output_trigger_latch, output_trigger_latch_next, output_overflow, output_overflow_latch : std_logic;
begin
input_util_average_inst : entity work.moving_average_wrapper(arch)
generic map(
INNER_WINDOW_SIZE => WINDOW_SIZE,
OUTER_WINDOW_SIZE => WINDOW_SIZE,
DATA_WIDTH => CDR_LONG_WIDTH,
ENABLE_ROUNDING => TRUE
)
port map(
clk => clk,
reset => reset,
data_in => input_util,
average => input_average,
trigger => input_trigger,
overflow => input_overflow
);
output_util_average_inst : entity work.moving_average_wrapper(arch)
generic map(
INNER_WINDOW_SIZE => WINDOW_SIZE,
OUTER_WINDOW_SIZE => WINDOW_SIZE,
DATA_WIDTH => CDR_LONG_WIDTH,
ENABLE_ROUNDING => TRUE
)
port map(
clk => clk,
reset => reset,
data_in => output_util,
average => output_average,
trigger => output_trigger,
overflow => output_overflow
);
latch_prc : process(clk)
begin
if rising_edge(clk) then
if (reset = '1') then
input_average_latch <= (others => '0');
output_average_latch <= (others => '0');
input_trigger_latch <= '0';
output_trigger_latch <= '0';
input_overflow_latch <= '0';
output_overflow_latch <= '0';
else
if (input_trigger = '1') then
input_trigger_latch <= input_trigger;
input_average_latch <= input_average;
end if;
if (output_trigger = '1') then
output_trigger_latch <= output_trigger;
output_average_latch <= output_average;
end if;
if (input_overflow = '1') then
input_overflow_latch <= input_overflow;
end if;
if (output_overflow = '1') then
output_overflow_latch <= output_overflow;
end if;
end if;
end if;
end process;
main_prc : process(all)
begin
-- DEFAULT
stage_next <= stage;
cnt_next <= cnt;
id_latch_next <= id_latch;
a_latch_next <= a_latch;
input_trigger_latch_next <= input_trigger_latch;
output_trigger_latch_next <= output_trigger_latch;
-- DEFAULT Unregistered
start_r <= '0';
opcode_r <= NOP;
start_w <= '0';
opcode_w <= NOP;
id_w <= (others => '0');
a_w <= (others => '0');
-- Latch Setter
if (input_trigger = '1') then
input_trigger_latch_next <= '1';
end if;
if (output_trigger = '1') then
output_trigger_latch_next <= '1';
end if;
case (stage) is
when IDLE =>
-- Input FIFO Utilization Report
if (input_trigger_latch = '1') then
id_latch_next <= std_logic_vector(to_unsigned(3,CDR_LONG_WIDTH));
a_latch_next <= input_average_latch;
stage_next <= WRITE;
cnt_next <= 0;
-- Reset
input_trigger_latch_next <= '0';
-- Output FIFO Utilization Report
elsif (output_trigger_latch = '1') then
id_latch_next <= std_logic_vector(to_unsigned(4,CDR_LONG_WIDTH));
a_latch_next <= output_average_latch;
stage_next <= WRITE;
cnt_next <= 0;
-- Reset
output_trigger_latch_next <= '0';
-- Reader has Available Data
elsif (data_available_r = '1') then
stage_next <= READ;
cnt_next <= 0;
end if;
when READ =>
case (cnt) is
when 0 =>
start_r <= '1';
opcode_r <= TAKE;
if (ack_r = '1') then
cnt_next <= cnt + 1;
end if;
when 1 =>
if (done_r = '1') then
case (return_code_r) is
when ROS_RET_OK =>
if (taken_r = '1') then
if (unsigned(id_r) = 1) then
id_latch_next <= std_logic_vector(to_unsigned(2,CDR_LONG_WIDTH));
a_latch_next <= a_r;
stage_next <= WRITE;
cnt_next <= 0;
-- Unknown Instance
else
-- Take Next Sample
cnt_next <= 0;
end if;
elsif (data_available_r = '1') then
-- Take Next Sample
cnt_next <= 0;
else
-- DONE
stage_next <= IDLE;
end if;
when others =>
-- ERROR
assert FALSE report "Unexpected DDS Reader Return Code" severity FAILURE;
stage_next <= IDLE;
end case;
end if;
when others =>
null;
end case;
when WRITE =>
id_w <= id_latch;
a_w <= a_latch;
case (cnt) is
when 0 =>
start_w <= '1';
opcode_w <= PUBLISH;
if (ack_w = '1') then
cnt_next <= cnt + 1;
end if;
when 1 =>
if (done_w = '1') then
case (return_code_w) is
when ROS_RET_OK =>
-- DONE
stage_next <= IDLE;
when others =>
-- ERROR
assert FALSE report "Unexpected DDS Writer Return Code" severity FAILURE;
stage_next <= IDLE;
end case;
end if;
when others =>
null;
end case;
end case;
end process;
sync_prc : process(clk)
begin
if rising_edge(clk) then
if (reset = '1') then
stage <= IDLE;
cnt <= 0;
id_latch <= (others => '0');
a_latch <= (others => '0');
input_trigger_latch <= '0';
output_trigger_latch <= '0';
else
stage <= stage_next;
cnt <= cnt_next;
id_latch <= id_latch_next;
a_latch <= a_latch_next;
input_trigger_latch <= input_trigger_latch_next;
output_trigger_latch <= output_trigger_latch_next;
end if;
end if;
end process;
end architecture;