1
0
SEm-Labos/Libs/Memory_test/hdl/fifo_tester_test.vhd

340 lines
12 KiB
VHDL
Raw Permalink Normal View History

2024-02-23 13:01:05 +00:00
--LIBRARY std;
-- USE std.textio.ALL;
LIBRARY COMMON_TEST;
USE COMMON_TEST.testUtils.all;
ARCHITECTURE test OF fifo_tester IS
constant clockFrequency: real := 66.0E6;
constant clockPeriod: time := (1.0/clockFrequency) * 1 sec;
signal clock_int: std_ulogic := '1';
constant testInterval: time := 10*clockPeriod;
signal dataIn_int: integer;
signal read_int: std_ulogic;
signal dataOffset: integer;
signal dataValid: std_ulogic;
signal dataRead: integer;
BEGIN
------------------------------------------------------------------------------
-- reset and clock
reset <= '1', '0' after 2*clockPeriod;
clock_int <= not clock_int after clockPeriod/2;
clock <= transport clock_int after clockPeriod*9/10;
------------------------------------------------------------------------------
-- test sequence
process
variable readIndex: integer;
begin
write <= '0';
read_int <= '0';
dataOffset <= -16#10#;
wait for 5*clockPeriod;
print(
lf & lf & lf &
"----------------------------------------------------------------" & lf &
"Starting testbench" & lf &
lf & lf
);
--..........................................................................
-- full write / read after end of write
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", full FIFO write direclty followed by full read" &
lf & lf
);
-- write FIFO
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
write <= '1';
for index in 0 to fifoDepth-1 loop
dataIn_int <= dataOffset + index;
wait for clockPeriod;
end loop;
write <= '0';
-- read FIFO
read_int <= '1';
readIndex := 0;
while empty = '0' loop
assert unsigned(dataOut) = dataOffset + readIndex
report "FIFO readback error"
severity error;
readIndex := readIndex + 1;
wait until rising_edge(clock_int);
end loop;
read_int <= '0';
--..........................................................................
-- full write / read after some time
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", full FIFO write and delay before read" &
lf & lf
);
-- write FIFO
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
write <= '1';
for index in 0 to fifoDepth-1 loop
dataIn_int <= dataOffset + index;
wait for clockPeriod;
end loop;
write <= '0';
-- wait before read
wait for 4*clockPeriod;
-- read FIFO
read_int <= '1';
readIndex := 0;
while empty = '0' loop
assert unsigned(dataOut) = dataOffset + readIndex
report "FIFO readback error"
severity error;
readIndex := readIndex + 1;
wait until rising_edge(clock_int);
end loop;
read_int <= '0';
--..........................................................................
-- write / read direct
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", full FIFO write with asynchronous direct read" &
lf & lf
);
-- write FIFO
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
write <= '1', '0' after 8*clockPeriod;
dataIn_int <= dataOffset + 16#00#,
dataOffset + 16#01# after 1*clockPeriod,
dataOffset + 16#02# after 2*clockPeriod,
dataOffset + 16#03# after 3*clockPeriod,
dataOffset + 16#04# after 4*clockPeriod,
dataOffset + 16#05# after 5*clockPeriod,
dataOffset + 16#06# after 6*clockPeriod,
dataOffset + 16#07# after 7*clockPeriod;
-- read FIFO
wait until empty = '0';
read_int <= '1';
readIndex := -1;
while empty = '0' loop
if readIndex >= 0 then
assert unsigned(dataOut) = dataOffset + readIndex
report "FIFO readback error"
severity error;
end if;
readIndex := readIndex + 1;
wait until rising_edge(clock_int);
end loop;
read_int <= '0';
--..........................................................................
-- write / read direct with clock period delay
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", full FIFO write with synchronous direct read" &
lf & lf
);
-- write FIFO
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
write <= '1', '0' after 8*clockPeriod;
dataIn_int <= dataOffset + 16#00#,
dataOffset + 16#01# after 1*clockPeriod,
dataOffset + 16#02# after 2*clockPeriod,
dataOffset + 16#03# after 3*clockPeriod,
dataOffset + 16#04# after 4*clockPeriod,
dataOffset + 16#05# after 5*clockPeriod,
dataOffset + 16#06# after 6*clockPeriod,
dataOffset + 16#07# after 7*clockPeriod;
-- read FIFO
wait until empty = '0';
wait until rising_edge(clock_int);
read_int <= '1';
readIndex := 0;
while empty = '0' loop
assert unsigned(dataOut) = dataOffset + readIndex
report "FIFO readback error"
severity error;
readIndex := readIndex + 1;
wait until rising_edge(clock_int);
end loop;
read_int <= '0';
--..........................................................................
-- slow read sets FIFO full
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", slow reading sets FIFO full and requires waiting before writing on" &
lf & lf
);
-- prepare slow FIFO reading
wait until rising_edge(clock_int);
wait for 2*clockPeriod;
read_int <= '1' after 4*clockPeriod,
'0' after 5*clockPeriod,
'1' after 14*clockPeriod,
'0' after 15*clockPeriod,
'1' after 24*clockPeriod,
'0' after 25*clockPeriod,
'1' after 34*clockPeriod,
'0' after 35*clockPeriod,
'1' after 44*clockPeriod,
'0' after (45+2*fifoDepth-5)*clockPeriod;
-- write 2*FIFO depth
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
for index in 0 to 2*fifoDepth-1 loop
dataIn_int <= dataOffset + index;
if full = '1' then
wait until full = '0';
wait for clockPeriod/8;
end if;
write <= '1';
wait until rising_edge(clock_int);
write <= '0';
end loop;
--..........................................................................
-- write over full
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", attempt to write after FIFO full" &
lf & lf
);
-- write FIFO
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
write <= '1';
for index in 0 to fifoDepth+3 loop
dataIn_int <= dataOffset + index;
wait for clockPeriod;
end loop;
write <= '0';
--..........................................................................
-- read FIFO once too much
print(
"At time " & sprintf("%9.3tu", now) &
", attempt to read after FIFO empty" &
lf & lf
);
read_int <= '1';
wait for clockPeriod;
wait until empty = '1';
wait for clockPeriod;
read_int <= '0';
-- read when empty
wait until rising_edge(clock_int);
wait for 2*clockPeriod;
read_int <= '1';
wait for 2*clockPeriod;
read_int <= '0';
--..........................................................................
-- read constantly
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", reading FIFO constantly (data valid when empty = '0')" &
lf & lf
);
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
read_int <= '1';
wait for 2*clockPeriod;
wait until rising_edge(clock_int);
readIndex := -1;
write <= '1';
for index in 0 to fifoDepth-1 loop
if empty = '0' then
readIndex := readIndex + 1;
end if;
if (readIndex >= 0) and (empty = '0') then
assert unsigned(dataOut) = dataOffset + readIndex
report "FIFO readback error"
severity error;
end if;
dataIn_int <= dataOffset + index;
wait until rising_edge(clock_int);
end loop;
write <= '0';
wait until empty = '1';
wait for 2*clockPeriod;
read_int <= '0';
--..........................................................................
-- full write / read with breaks
wait for testInterval;
print(
"At time " & sprintf("%9.3tu", now) &
", reading FIFO with breaks" &
lf & lf
);
-- write FIFO
dataOffset <= dataOffset + 16#10#;
wait until rising_edge(clock_int);
write <= '1';
for index in 0 to fifoDepth-1 loop
dataIn_int <= dataOffset + index;
wait for clockPeriod;
end loop;
write <= '0';
-- wait before read
wait for 2*clockPeriod;
-- read FIFO
wait until rising_edge(clock_int);
readIndex := 0;
for index in 0 to fifoDepth/4-1 loop
read_int <= '1';
for rdIndex in 1 to 2 loop
assert unsigned(dataOut) = dataOffset + readIndex
report "FIFO readback error"
severity error;
readIndex := readIndex + 1;
wait until rising_edge(clock_int);
end loop;
read_int <= '0';
wait for 2*clockPeriod;
end loop;
read_int <= '1';
while empty = '0' loop
assert unsigned(dataOut) = dataOffset + readIndex
report "FIFO readback error"
severity error;
readIndex := readIndex + 1;
wait until rising_edge(clock_int);
end loop;
read_int <= '0';
--..........................................................................
-- end of tests
wait for testInterval;
assert false
report "END SIMULATION"
severity failure;
wait;
end process;
dataIn <= std_ulogic_vector(to_signed(dataIn_int, dataIn'length));
read <= read_int;
dataValid <= '1' when (read_int = '1') and (empty = '0')
else '0';
dataRead <= to_integer(signed(dataOut)) when dataValid = '1'
else 0;
END ARCHITECTURE test;