Organized VUnit testbenches into test cases.

Several of the testbenches have stimuli code divided into sections preceded with a header comment explaining
what is being tested. These sections have been made into VUnit test cases. The default behavior of VUnit is
to run each test case in a separate simulation which comes with a number of benefits:

* A failing test case doesn't prevent other test cases to be executed
* Test cases are independent. A test case cannot fail as a side-effect to a problem with another test case
* Test execution can be more parallelized and the overall test execution time reduced

Signed-off-by: Lars Asplund <lars.anders.asplund@gmail.com>
pull/295/head
Lars Asplund 4 years ago
parent 08c0c4c1b4
commit 0940b8a9d3

@ -49,75 +49,77 @@ begin


test_runner_setup(runner, runner_cfg); test_runner_setup(runner, runner_cfg);


-- test with input = 0 while test_suite loop
report "test zero input"; if run("Test with input = 0") then
rs <= (others => '0'); rs <= (others => '0');
is_32bit <= '0';
count_right <= '0';
wait for clk_period;
assert result = x"0000000000000040"
report "bad cntlzd 0 = " & to_hstring(result);
count_right <= '1';
wait for clk_period;
assert result = x"0000000000000040"
report "bad cnttzd 0 = " & to_hstring(result);
is_32bit <= '1';
count_right <= '0';
wait for clk_period;
assert result = x"0000000000000020"
report "bad cntlzw 0 = " & to_hstring(result);
count_right <= '1';
wait for clk_period;
assert result = x"0000000000000020"
report "bad cnttzw 0 = " & to_hstring(result);

report "test cntlzd/w";
count_right <= '0';
for j in 0 to 100 loop
r := rnd.RandSlv(64);
r(63) := '1';
for i in 0 to 63 loop
rs <= r;
is_32bit <= '0'; is_32bit <= '0';
count_right <= '0';
wait for clk_period; wait for clk_period;
assert to_integer(unsigned(result)) = i assert result = x"0000000000000040"
report "bad cntlzd " & to_hstring(rs) & " -> " & to_hstring(result); report "bad cntlzd 0 = " & to_hstring(result);
rs <= r(31 downto 0) & r(63 downto 32); count_right <= '1';
is_32bit <= '1';
wait for clk_period; wait for clk_period;
if i < 32 then assert result = x"0000000000000040"
assert to_integer(unsigned(result)) = i report "bad cnttzd 0 = " & to_hstring(result);
report "bad cntlzw " & to_hstring(rs) & " -> " & to_hstring(result);
else
assert to_integer(unsigned(result)) = 32
report "bad cntlzw " & to_hstring(rs) & " -> " & to_hstring(result);
end if;
r := '0' & r(63 downto 1);
end loop;
end loop;

report "test cnttzd/w";
count_right <= '1';
for j in 0 to 100 loop
r := rnd.RandSlv(64);
r(0) := '1';
for i in 0 to 63 loop
rs <= r;
is_32bit <= '0';
wait for clk_period;
assert to_integer(unsigned(result)) = i
report "bad cnttzd " & to_hstring(rs) & " -> " & to_hstring(result);
is_32bit <= '1'; is_32bit <= '1';
count_right <= '0';
wait for clk_period;
assert result = x"0000000000000020"
report "bad cntlzw 0 = " & to_hstring(result);
count_right <= '1';
wait for clk_period; wait for clk_period;
if i < 32 then assert result = x"0000000000000020"
assert to_integer(unsigned(result)) = i report "bad cnttzw 0 = " & to_hstring(result);
report "bad cnttzw " & to_hstring(rs) & " -> " & to_hstring(result);
else elsif run("Test cntlzd/w") then
assert to_integer(unsigned(result)) = 32 count_right <= '0';
report "bad cnttzw " & to_hstring(rs) & " -> " & to_hstring(result); for j in 0 to 100 loop
end if; r := rnd.RandSlv(64);
r := r(62 downto 0) & '0'; r(63) := '1';
end loop; for i in 0 to 63 loop
rs <= r;
is_32bit <= '0';
wait for clk_period;
assert to_integer(unsigned(result)) = i
report "bad cntlzd " & to_hstring(rs) & " -> " & to_hstring(result);
rs <= r(31 downto 0) & r(63 downto 32);
is_32bit <= '1';
wait for clk_period;
if i < 32 then
assert to_integer(unsigned(result)) = i
report "bad cntlzw " & to_hstring(rs) & " -> " & to_hstring(result);
else
assert to_integer(unsigned(result)) = 32
report "bad cntlzw " & to_hstring(rs) & " -> " & to_hstring(result);
end if;
r := '0' & r(63 downto 1);
end loop;
end loop;

elsif run("Test cnttzd/w") then
count_right <= '1';
for j in 0 to 100 loop
r := rnd.RandSlv(64);
r(0) := '1';
for i in 0 to 63 loop
rs <= r;
is_32bit <= '0';
wait for clk_period;
assert to_integer(unsigned(result)) = i
report "bad cnttzd " & to_hstring(rs) & " -> " & to_hstring(result);
is_32bit <= '1';
wait for clk_period;
if i < 32 then
assert to_integer(unsigned(result)) = i
report "bad cnttzw " & to_hstring(rs) & " -> " & to_hstring(result);
else
assert to_integer(unsigned(result)) = 32
report "bad cnttzw " & to_hstring(rs) & " -> " & to_hstring(result);
end if;
r := r(62 downto 0) & '0';
end loop;
end loop;
end if;
end loop; end loop;


test_runner_cleanup(runner); test_runner_cleanup(runner);

@ -49,513 +49,485 @@ begin


test_runner_setup(runner, runner_cfg); test_runner_setup(runner, runner_cfg);


rst <= '1'; while test_suite loop
wait for clk_period; rst <= '1';
rst <= '0';

d1.valid <= '1';
d1.dividend <= x"0000000010001000";
d1.divisor <= x"0000000000001111";
d1.is_signed <= '0';
d1.is_32bit <= '0';
d1.is_extended <= '0';
d1.is_modulus <= '0';
d1.neg_result <= '0';

wait for clk_period;
assert d2.valid = '0';

d1.valid <= '0';

for j in 0 to 66 loop
wait for clk_period; wait for clk_period;
if d2.valid = '1' then rst <= '0';
exit;
end if;
end loop;


assert d2.valid = '1'; d1.is_signed <= '0';
assert d2.write_reg_data = x"000000000000f001" report "result " & to_hstring(d2.write_reg_data); d1.neg_result <= '0';
d1.is_extended <= '0';
d1.is_32bit <= '0';
d1.is_modulus <= '0';
d1.valid <= '0';


wait for clk_period; if run("Test interface") then
assert d2.valid = '0' report "valid"; d1.valid <= '1';
d1.dividend <= x"0000000010001000";
d1.divisor <= x"0000000000001111";


d1.valid <= '1'; wait for clk_period;
assert d2.valid = '0';


wait for clk_period; d1.valid <= '0';
assert d2.valid = '0' report "valid";


d1.valid <= '0'; for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;


for j in 0 to 66 loop assert d2.valid = '1';
wait for clk_period; assert d2.write_reg_data = x"000000000000f001" report "result " & to_hstring(d2.write_reg_data);
if d2.valid = '1' then
exit;
end if;
end loop;


assert d2.valid = '1'; wait for clk_period;
assert d2.write_reg_data = x"000000000000f001" report "result " & to_hstring(d2.write_reg_data); assert d2.valid = '0' report "valid";


wait for clk_period; d1.valid <= '1';
assert d2.valid = '0';


-- test divd wait for clk_period;
report "test divd"; assert d2.valid = '0' report "valid";
divd_loop : for dlength in 1 to 8 loop
for vlength in 1 to dlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));


d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra)); d1.valid <= '0';
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63) xor rb(63);
d1.valid <= '1';


for j in 0 to 66 loop
wait for clk_period; wait for clk_period;

if d2.valid = '1' then
d1.valid <= '0'; exit;
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" and (ra /= x"8000000000000000" or rb /= x"ffffffffffffffff") then
behave_rt := ppc_divd(ra, rb);
end if; end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divd expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop; end loop;
end loop;
end loop;


-- test divdu assert d2.valid = '1';
report "test divdu"; assert d2.write_reg_data = x"000000000000f001" report "result " & to_hstring(d2.write_reg_data);
divdu_loop : for dlength in 1 to 8 loop
for vlength in 1 to dlength loop wait for clk_period;
for i in 0 to 100 loop assert d2.valid = '0';
ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64)); elsif run("Test divd") then

divd_loop : for dlength in 1 to 8 loop
d1.dividend <= ra; for vlength in 1 to dlength loop
d1.divisor <= rb; for i in 0 to 100 loop
d1.is_signed <= '0'; ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
d1.neg_result <= '0'; rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));
d1.valid <= '1';

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
wait for clk_period; d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));

d1.is_signed <= '1';
d1.valid <= '0'; d1.neg_result <= ra(63) xor rb(63);
for j in 0 to 66 loop d1.valid <= '1';
wait for clk_period;
if d2.valid = '1' then wait for clk_period;
exit;
end if; d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" and (ra /= x"8000000000000000" or rb /= x"ffffffffffffffff") then
behave_rt := ppc_divd(ra, rb);
end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divd expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := ppc_divdu(ra, rb);
end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divdu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop; end loop;
end loop;
end loop;

-- test divde
report "test divde";
divde_loop : for vlength in 1 to 8 loop
for dlength in 1 to vlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63) xor rb(63);
d1.is_extended <= '1';
d1.valid <= '1';

wait for clk_period;


d1.valid <= '0'; elsif run("Test divdu") then
for j in 0 to 66 loop divdu_loop : for dlength in 1 to 8 loop
wait for clk_period; for vlength in 1 to dlength loop
if d2.valid = '1' then for i in 0 to 100 loop
exit; ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
end if; rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := ppc_divdu(ra, rb);
end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divdu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
d128 := ra & x"0000000000000000";
q128 := std_ulogic_vector(signed(d128) / signed(rb));
if q128(127 downto 63) = x"0000000000000000" & '0' or
q128(127 downto 63) = x"ffffffffffffffff" & '1' then
behave_rt := q128(63 downto 0);
end if;
end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divde expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end loop; end loop;
end loop;
end loop;

-- test divdeu
report "test divdeu";
divdeu_loop : for vlength in 1 to 8 loop
for dlength in 1 to vlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.is_signed <= '0';
d1.neg_result <= '0';
d1.is_extended <= '1';
d1.valid <= '1';

wait for clk_period;


d1.valid <= '0'; elsif run("Test divde") then
for j in 0 to 66 loop divde_loop : for vlength in 1 to 8 loop
wait for clk_period; for dlength in 1 to vlength loop
if d2.valid = '1' then for i in 0 to 100 loop
exit; ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
end if; rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63) xor rb(63);
d1.is_extended <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
d128 := ra & x"0000000000000000";
q128 := std_ulogic_vector(signed(d128) / signed(rb));
if q128(127 downto 63) = x"0000000000000000" & '0' or
q128(127 downto 63) = x"ffffffffffffffff" & '1' then
behave_rt := q128(63 downto 0);
end if;
end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divde expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if unsigned(rb) > unsigned(ra) then
d128 := ra & x"0000000000000000";
q128 := std_ulogic_vector(unsigned(d128) / unsigned(rb));
behave_rt := q128(63 downto 0);
end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divdeu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end loop; end loop;
end loop;
end loop;

-- test divw
report "test divw";
divw_loop : for dlength in 1 to 4 loop
for vlength in 1 to dlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63) xor rb(63);
d1.is_extended <= '0';
d1.is_32bit <= '1';
d1.valid <= '1';

wait for clk_period;


d1.valid <= '0'; elsif run("Test divdeu") then
for j in 0 to 66 loop divdeu_loop : for vlength in 1 to 8 loop
wait for clk_period; for dlength in 1 to vlength loop
if d2.valid = '1' then for i in 0 to 100 loop
exit; ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
end if; rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.is_extended <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if unsigned(rb) > unsigned(ra) then
d128 := ra & x"0000000000000000";
q128 := std_ulogic_vector(unsigned(d128) / unsigned(rb));
behave_rt := q128(63 downto 0);
end if;
assert to_hstring(behave_rt) = to_hstring(d2.write_reg_data)
report "bad divdeu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" and (ra /= x"ffffffff80000000" or rb /= x"ffffffffffffffff") then
behave_rt := ppc_divw(ra, rb);
end if;
assert behave_rt = d2.write_reg_data
report "bad divw expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop; end loop;
end loop;
end loop;

-- test divwu
report "test divwu";
divwu_loop : for dlength in 1 to 4 loop
for vlength in 1 to dlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.is_signed <= '0';
d1.neg_result <= '0';
d1.is_extended <= '0';
d1.is_32bit <= '1';
d1.valid <= '1';


wait for clk_period; elsif run("Test divw") then

divw_loop : for dlength in 1 to 4 loop
d1.valid <= '0'; for vlength in 1 to dlength loop
for j in 0 to 66 loop for i in 0 to 100 loop
wait for clk_period; ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
if d2.valid = '1' then rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));
exit;
end if; d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63) xor rb(63);
d1.is_32bit <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" and (ra /= x"ffffffff80000000" or rb /= x"ffffffffffffffff") then
behave_rt := ppc_divw(ra, rb);
end if;
assert behave_rt = d2.write_reg_data
report "bad divw expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := ppc_divwu(ra, rb);
end if;
assert behave_rt = d2.write_reg_data
report "bad divwu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop; end loop;
end loop;
end loop;


-- test divwe elsif run("Test divwu") then
report "test divwe"; divwu_loop : for dlength in 1 to 4 loop
divwe_loop : for vlength in 1 to 4 loop for vlength in 1 to dlength loop
for dlength in 1 to vlength loop for i in 0 to 100 loop
for i in 0 to 100 loop ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 32)) & x"00000000"; rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));
rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra)); d1.divisor <= rb;
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb)); d1.is_32bit <= '1';
d1.is_signed <= '1'; d1.valid <= '1';
d1.neg_result <= ra(63) xor rb(63);
d1.is_extended <= '0'; wait for clk_period;
d1.is_32bit <= '1';
d1.valid <= '1'; d1.valid <= '0';

for j in 0 to 66 loop
wait for clk_period; wait for clk_period;

if d2.valid = '1' then
d1.valid <= '0'; exit;
for j in 0 to 66 loop end if;
wait for clk_period; end loop;
if d2.valid = '1' then assert d2.valid = '1';
exit;
end if; behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := ppc_divwu(ra, rb);
end if;
assert behave_rt = d2.write_reg_data
report "bad divwu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
q64 := std_ulogic_vector(signed(ra) / signed(rb));
if q64(63 downto 31) = x"00000000" & '0' or
q64(63 downto 31) = x"ffffffff" & '1' then
behave_rt := x"00000000" & q64(31 downto 0);
end if;
assert behave_rt = d2.write_reg_data
report "bad divwe expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end if;
end loop; end loop;
end loop;
end loop;


-- test divweu elsif run("Test divwe") then
report "test divweu"; divwe_loop : for vlength in 1 to 4 loop
divweu_loop : for vlength in 1 to 4 loop for dlength in 1 to vlength loop
for dlength in 1 to vlength loop for i in 0 to 100 loop
for i in 0 to 100 loop ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 32)) & x"00000000";
ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 32)) & x"00000000"; rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));
rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.dividend <= ra; d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.divisor <= rb; d1.is_signed <= '1';
d1.is_signed <= '0'; d1.neg_result <= ra(63) xor rb(63);
d1.neg_result <= '0'; d1.is_32bit <= '1';
d1.is_extended <= '0'; d1.valid <= '1';
d1.is_32bit <= '1';
d1.valid <= '1'; wait for clk_period;


wait for clk_period; d1.valid <= '0';

for j in 0 to 66 loop
d1.valid <= '0'; wait for clk_period;
for j in 0 to 66 loop if d2.valid = '1' then
wait for clk_period; exit;
if d2.valid = '1' then end if;
exit; end loop;
end if; assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
q64 := std_ulogic_vector(signed(ra) / signed(rb));
if q64(63 downto 31) = x"00000000" & '0' or
q64(63 downto 31) = x"ffffffff" & '1' then
behave_rt := x"00000000" & q64(31 downto 0);
end if;
assert behave_rt = d2.write_reg_data
report "bad divwe expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end if;
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if unsigned(rb(31 downto 0)) > unsigned(ra(63 downto 32)) then
behave_rt := std_ulogic_vector(unsigned(ra) / unsigned(rb));
end if;
assert behave_rt = d2.write_reg_data
report "bad divweu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end loop; end loop;
end loop;
end loop;

-- test modsd
report "test modsd";
modsd_loop : for dlength in 1 to 8 loop
for vlength in 1 to dlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63);
d1.is_extended <= '0';
d1.is_32bit <= '0';
d1.is_modulus <= '1';
d1.valid <= '1';


wait for clk_period; elsif run("Test divweu") then

divweu_loop : for vlength in 1 to 4 loop
d1.valid <= '0'; for dlength in 1 to vlength loop
for j in 0 to 66 loop for i in 0 to 100 loop
wait for clk_period; ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 32)) & x"00000000";
if d2.valid = '1' then rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));
exit;
end if; d1.dividend <= ra;
d1.divisor <= rb;
d1.is_32bit <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if unsigned(rb(31 downto 0)) > unsigned(ra(63 downto 32)) then
behave_rt := std_ulogic_vector(unsigned(ra) / unsigned(rb));
end if;
assert behave_rt = d2.write_reg_data
report "bad divweu expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data) & " for ra = " & to_hstring(ra) & " rb = " & to_hstring(rb);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := std_ulogic_vector(signed(ra) rem signed(rb));
end if;
assert behave_rt = d2.write_reg_data
report "bad modsd expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop; end loop;
end loop;
end loop;

-- test modud
report "test modud";
modud_loop : for dlength in 1 to 8 loop
for vlength in 1 to dlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.is_signed <= '0';
d1.neg_result <= '0';
d1.is_extended <= '0';
d1.is_32bit <= '0';
d1.is_modulus <= '1';
d1.valid <= '1';

wait for clk_period;


d1.valid <= '0'; elsif run("Test modsd") then
for j in 0 to 66 loop modsd_loop : for dlength in 1 to 8 loop
wait for clk_period; for vlength in 1 to dlength loop
if d2.valid = '1' then for i in 0 to 100 loop
exit; ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
end if; rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63);
d1.is_modulus <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := std_ulogic_vector(signed(ra) rem signed(rb));
end if;
assert behave_rt = d2.write_reg_data
report "bad modsd expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := std_ulogic_vector(unsigned(ra) rem unsigned(rb));
end if;
assert behave_rt = d2.write_reg_data
report "bad modud expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop; end loop;
end loop;
end loop;

-- test modsw
report "test modsw";
modsw_loop : for dlength in 1 to 4 loop
for vlength in 1 to dlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63);
d1.is_extended <= '0';
d1.is_32bit <= '1';
d1.is_modulus <= '1';
d1.valid <= '1';

wait for clk_period;


d1.valid <= '0'; elsif run("Test modud") then
for j in 0 to 66 loop modud_loop : for dlength in 1 to 8 loop
wait for clk_period; for vlength in 1 to dlength loop
if d2.valid = '1' then for i in 0 to 100 loop
exit; ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
end if; rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.is_modulus <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := std_ulogic_vector(unsigned(ra) rem unsigned(rb));
end if;
assert behave_rt = d2.write_reg_data
report "bad modud expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop; end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
rem32 := std_ulogic_vector(signed(ra(31 downto 0)) rem signed(rb(31 downto 0)));
if rem32(31) = '0' then
behave_rt := x"00000000" & rem32;
else
behave_rt := x"ffffffff" & rem32;
end if;
end if;
assert behave_rt = d2.write_reg_data
report "bad modsw expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop; end loop;
end loop;
end loop;

-- test moduw
report "test moduw";
moduw_loop : for dlength in 1 to 4 loop
for vlength in 1 to dlength loop
for i in 0 to 100 loop
ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.is_signed <= '0';
d1.neg_result <= '0';
d1.is_extended <= '0';
d1.is_32bit <= '1';
d1.is_modulus <= '1';
d1.valid <= '1';

wait for clk_period;


d1.valid <= '0'; elsif run("Test modsw") then
for j in 0 to 66 loop modsw_loop : for dlength in 1 to 4 loop
wait for clk_period; for vlength in 1 to dlength loop
if d2.valid = '1' then for i in 0 to 100 loop
exit; ra := std_ulogic_vector(resize(signed(rnd.RandSlv(dlength * 8)), 64));
end if; rb := std_ulogic_vector(resize(signed(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra when ra(63) = '0' else std_ulogic_vector(- signed(ra));
d1.divisor <= rb when rb(63) = '0' else std_ulogic_vector(- signed(rb));
d1.is_signed <= '1';
d1.neg_result <= ra(63);
d1.is_32bit <= '1';
d1.is_modulus <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
rem32 := std_ulogic_vector(signed(ra(31 downto 0)) rem signed(rb(31 downto 0)));
if rem32(31) = '0' then
behave_rt := x"00000000" & rem32;
else
behave_rt := x"ffffffff" & rem32;
end if;
end if;
assert behave_rt = d2.write_reg_data
report "bad modsw expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop; end loop;
assert d2.valid = '1'; end loop;


behave_rt := (others => '0'); elsif run("Test moduw") then
if rb /= x"0000000000000000" then moduw_loop : for dlength in 1 to 4 loop
behave_rt := x"00000000" & std_ulogic_vector(unsigned(ra(31 downto 0)) rem unsigned(rb(31 downto 0))); for vlength in 1 to dlength loop
end if; for i in 0 to 100 loop
assert behave_rt(31 downto 0) = d2.write_reg_data(31 downto 0) ra := std_ulogic_vector(resize(unsigned(rnd.RandSlv(dlength * 8)), 64));
report "bad moduw expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data); rb := std_ulogic_vector(resize(unsigned(rnd.RandSlv(vlength * 8)), 64));

d1.dividend <= ra;
d1.divisor <= rb;
d1.is_32bit <= '1';
d1.is_modulus <= '1';
d1.valid <= '1';

wait for clk_period;

d1.valid <= '0';
for j in 0 to 66 loop
wait for clk_period;
if d2.valid = '1' then
exit;
end if;
end loop;
assert d2.valid = '1';

behave_rt := (others => '0');
if rb /= x"0000000000000000" then
behave_rt := x"00000000" & std_ulogic_vector(unsigned(ra(31 downto 0)) rem unsigned(rb(31 downto 0)));
end if;
assert behave_rt(31 downto 0) = d2.write_reg_data(31 downto 0)
report "bad moduw expected " & to_hstring(behave_rt) & " got " & to_hstring(d2.write_reg_data);
end loop;
end loop;
end loop; end loop;
end loop; end if;
end loop; end loop;


test_runner_cleanup(runner); test_runner_cleanup(runner);

@ -58,228 +58,232 @@ begin


test_runner_setup(runner, runner_cfg); test_runner_setup(runner, runner_cfg);


wait for clk_period; while test_suite loop
if run("Test interface") then
wait for clk_period;


m1.valid <= '1'; m1.valid <= '1';
m1.data1 <= x"0000000000001000"; m1.data1 <= x"0000000000001000";
m1.data2 <= x"0000000000001111"; m1.data2 <= x"0000000000001111";


wait for clk_period; wait for clk_period;
assert m2.valid = '0'; assert m2.valid = '0';


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period; wait for clk_period;
assert m2.valid = '0'; assert m2.valid = '0';


wait for clk_period; wait for clk_period;
assert m2.valid = '0'; assert m2.valid = '0';


wait for clk_period; wait for clk_period;
assert m2.valid = '1'; assert m2.valid = '1';
assert m2.result = x"00000000000000000000000001111000"; assert m2.result = x"00000000000000000000000001111000";


wait for clk_period; wait for clk_period;
assert m2.valid = '0'; assert m2.valid = '0';


m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;
assert m2.valid = '0'; assert m2.valid = '0';


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);
assert m2.valid = '1'; assert m2.valid = '1';
assert m2.result = x"00000000000000000000000001111000"; assert m2.result = x"00000000000000000000000001111000";


-- test mulld elsif run("Test mulld") then
mulld_loop : for i in 0 to 1000 loop mulld_loop : for i in 0 to 1000 loop
ra := rnd.RandSlv(ra'length); ra := rnd.RandSlv(ra'length);
rb := rnd.RandSlv(rb'length); rb := rnd.RandSlv(rb'length);


behave_rt := ppc_mulld(ra, rb); behave_rt := ppc_mulld(ra, rb);


m1.data1 <= absval(ra); m1.data1 <= absval(ra);
m1.data2 <= absval(rb); m1.data2 <= absval(rb);
sign := ra(63) xor rb(63); sign := ra(63) xor rb(63);
m1.not_result <= sign; m1.not_result <= sign;
m1.addend <= (others => sign); m1.addend <= (others => sign);
m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);


assert m2.valid = '1'; assert m2.valid = '1';


assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 0)) assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 0))
report "bad mulld expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(63 downto 0)); report "bad mulld expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(63 downto 0));
end loop; end loop;


-- test mulhdu elsif run("Test mulhdu") then
mulhdu_loop : for i in 0 to 1000 loop mulhdu_loop : for i in 0 to 1000 loop
ra := rnd.RandSlv(ra'length); ra := rnd.RandSlv(ra'length);
rb := rnd.RandSlv(rb'length); rb := rnd.RandSlv(rb'length);


behave_rt := ppc_mulhdu(ra, rb); behave_rt := ppc_mulhdu(ra, rb);


m1.data1 <= ra; m1.data1 <= ra;
m1.data2 <= rb; m1.data2 <= rb;
m1.not_result <= '0'; m1.not_result <= '0';
m1.addend <= (others => '0'); m1.addend <= (others => '0');
m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);


assert m2.valid = '1'; assert m2.valid = '1';


assert to_hstring(behave_rt) = to_hstring(m2.result(127 downto 64)) assert to_hstring(behave_rt) = to_hstring(m2.result(127 downto 64))
report "bad mulhdu expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(127 downto 64)); report "bad mulhdu expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(127 downto 64));
end loop; end loop;


-- test mulhd elsif run("Test mulhd") then
mulhd_loop : for i in 0 to 1000 loop mulhd_loop : for i in 0 to 1000 loop
ra := rnd.RandSlv(ra'length); ra := rnd.RandSlv(ra'length);
rb := rnd.RandSlv(rb'length); rb := rnd.RandSlv(rb'length);


behave_rt := ppc_mulhd(ra, rb); behave_rt := ppc_mulhd(ra, rb);


m1.data1 <= absval(ra); m1.data1 <= absval(ra);
m1.data2 <= absval(rb); m1.data2 <= absval(rb);
sign := ra(63) xor rb(63); sign := ra(63) xor rb(63);
m1.not_result <= sign; m1.not_result <= sign;
m1.addend <= (others => sign); m1.addend <= (others => sign);
m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);


assert m2.valid = '1'; assert m2.valid = '1';


assert to_hstring(behave_rt) = to_hstring(m2.result(127 downto 64)) assert to_hstring(behave_rt) = to_hstring(m2.result(127 downto 64))
report "bad mulhd expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(127 downto 64)); report "bad mulhd expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(127 downto 64));
end loop; end loop;


-- test mullw elsif run("Test mullw") then
mullw_loop : for i in 0 to 1000 loop mullw_loop : for i in 0 to 1000 loop
ra := rnd.RandSlv(ra'length); ra := rnd.RandSlv(ra'length);
rb := rnd.RandSlv(rb'length); rb := rnd.RandSlv(rb'length);


behave_rt := ppc_mullw(ra, rb); behave_rt := ppc_mullw(ra, rb);


m1.data1 <= (others => '0'); m1.data1 <= (others => '0');
m1.data1(31 downto 0) <= absval(ra(31 downto 0)); m1.data1(31 downto 0) <= absval(ra(31 downto 0));
m1.data2 <= (others => '0'); m1.data2 <= (others => '0');
m1.data2(31 downto 0) <= absval(rb(31 downto 0)); m1.data2(31 downto 0) <= absval(rb(31 downto 0));
sign := ra(31) xor rb(31); sign := ra(31) xor rb(31);
m1.not_result <= sign; m1.not_result <= sign;
m1.addend <= (others => sign); m1.addend <= (others => sign);
m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);


assert m2.valid = '1'; assert m2.valid = '1';


assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 0)) assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 0))
report "bad mullw expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(63 downto 0)); report "bad mullw expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(63 downto 0));
end loop; end loop;


-- test mulhw elsif run("Test mulhw") then
mulhw_loop : for i in 0 to 1000 loop mulhw_loop : for i in 0 to 1000 loop
ra := rnd.RandSlv(ra'length); ra := rnd.RandSlv(ra'length);
rb := rnd.RandSlv(rb'length); rb := rnd.RandSlv(rb'length);


behave_rt := ppc_mulhw(ra, rb); behave_rt := ppc_mulhw(ra, rb);


m1.data1 <= (others => '0'); m1.data1 <= (others => '0');
m1.data1(31 downto 0) <= absval(ra(31 downto 0)); m1.data1(31 downto 0) <= absval(ra(31 downto 0));
m1.data2 <= (others => '0'); m1.data2 <= (others => '0');
m1.data2(31 downto 0) <= absval(rb(31 downto 0)); m1.data2(31 downto 0) <= absval(rb(31 downto 0));
sign := ra(31) xor rb(31); sign := ra(31) xor rb(31);
m1.not_result <= sign; m1.not_result <= sign;
m1.addend <= (others => sign); m1.addend <= (others => sign);
m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);


assert m2.valid = '1'; assert m2.valid = '1';


assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32)) assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32))
report "bad mulhw expected " & to_hstring(behave_rt) & " got " & report "bad mulhw expected " & to_hstring(behave_rt) & " got " &
to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32)); to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32));
end loop; end loop;


-- test mulhwu elsif run("Test mulhwu") then
mulhwu_loop : for i in 0 to 1000 loop mulhwu_loop : for i in 0 to 1000 loop
ra := rnd.RandSlv(ra'length); ra := rnd.RandSlv(ra'length);
rb := rnd.RandSlv(rb'length); rb := rnd.RandSlv(rb'length);


behave_rt := ppc_mulhwu(ra, rb); behave_rt := ppc_mulhwu(ra, rb);


m1.data1 <= (others => '0'); m1.data1 <= (others => '0');
m1.data1(31 downto 0) <= ra(31 downto 0); m1.data1(31 downto 0) <= ra(31 downto 0);
m1.data2 <= (others => '0'); m1.data2 <= (others => '0');
m1.data2(31 downto 0) <= rb(31 downto 0); m1.data2(31 downto 0) <= rb(31 downto 0);
m1.not_result <= '0'; m1.not_result <= '0';
m1.addend <= (others => '0'); m1.addend <= (others => '0');
m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);


assert m2.valid = '1'; assert m2.valid = '1';


assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32)) assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32))
report "bad mulhwu expected " & to_hstring(behave_rt) & " got " & report "bad mulhwu expected " & to_hstring(behave_rt) & " got " &
to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32)); to_hstring(m2.result(63 downto 32) & m2.result(63 downto 32));
end loop; end loop;


-- test mulli elsif run("Test mulli") then
mulli_loop : for i in 0 to 1000 loop mulli_loop : for i in 0 to 1000 loop
ra := rnd.RandSlv(ra'length); ra := rnd.RandSlv(ra'length);
si := rnd.RandSlv(si'length); si := rnd.RandSlv(si'length);


behave_rt := ppc_mulli(ra, si); behave_rt := ppc_mulli(ra, si);


m1.data1 <= absval(ra); m1.data1 <= absval(ra);
m1.data2 <= (others => '0'); m1.data2 <= (others => '0');
m1.data2(15 downto 0) <= absval(si); m1.data2(15 downto 0) <= absval(si);
sign := ra(63) xor si(15); sign := ra(63) xor si(15);
m1.not_result <= sign; m1.not_result <= sign;
m1.addend <= (others => sign); m1.addend <= (others => sign);
m1.valid <= '1'; m1.valid <= '1';


wait for clk_period; wait for clk_period;


m1.valid <= '0'; m1.valid <= '0';


wait for clk_period * (pipeline_depth-1); wait for clk_period * (pipeline_depth-1);


assert m2.valid = '1'; assert m2.valid = '1';


assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 0)) assert to_hstring(behave_rt) = to_hstring(m2.result(63 downto 0))
report "bad mulli expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(63 downto 0)); report "bad mulli expected " & to_hstring(behave_rt) & " got " & to_hstring(m2.result(63 downto 0));
end loop;
end if;
end loop; end loop;


test_runner_cleanup(runner); test_runner_cleanup(runner);

@ -53,255 +53,244 @@ begin


test_runner_setup(runner, runner_cfg); test_runner_setup(runner, runner_cfg);


-- rlwinm, rlwnm while test_suite loop
report "test rlw[i]nm"; if run("Test rlw[i]nm") then
ra <= (others => '0'); ra <= (others => '0');
is_32bit <= '1'; is_32bit <= '1';
right_shift <= '0'; right_shift <= '0';
arith <= '0'; arith <= '0';
clear_left <= '1'; clear_left <= '1';
clear_right <= '1'; clear_right <= '1';
extsw <= '0'; extsw <= '0';
rlwnm_loop : for i in 0 to 1000 loop rlwnm_loop : for i in 0 to 1000 loop
rs <= rnd.RandSlv(64); rs <= rnd.RandSlv(64);
shift <= rnd.RandSlv(7); shift <= rnd.RandSlv(7);
insn <= x"00000" & '0' & rnd.RandSlv(10) & '0'; insn <= x"00000" & '0' & rnd.RandSlv(10) & '0';
wait for clk_period; wait for clk_period;
behave_ra := ppc_rlwinm(rs, shift(4 downto 0), insn_mb32(insn), insn_me32(insn)); behave_ra := ppc_rlwinm(rs, shift(4 downto 0), insn_mb32(insn), insn_me32(insn));
assert behave_ra = result assert behave_ra = result
report "bad rlwnm expected " & to_hstring(behave_ra) & " got " & to_hstring(result); report "bad rlwnm expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
end loop; end loop;


-- rlwimi elsif run("Test rlwimi") then
report "test rlwimi"; is_32bit <= '1';
is_32bit <= '1'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '1';
clear_left <= '1'; clear_right <= '1';
clear_right <= '1'; rlwimi_loop : for i in 0 to 1000 loop
rlwimi_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); ra <= rnd.RandSlv(64);
ra <= rnd.RandSlv(64); shift <= "00" & rnd.RandSlv(5);
shift <= "00" & rnd.RandSlv(5); insn <= x"00000" & '0' & rnd.RandSlv(10) & '0';
insn <= x"00000" & '0' & rnd.RandSlv(10) & '0'; wait for clk_period;
wait for clk_period; behave_ra := ppc_rlwimi(ra, rs, shift(4 downto 0), insn_mb32(insn), insn_me32(insn));
behave_ra := ppc_rlwimi(ra, rs, shift(4 downto 0), insn_mb32(insn), insn_me32(insn)); assert behave_ra = result
assert behave_ra = result report "bad rlwimi expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad rlwimi expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- rldicl, rldcl elsif run("Test rld[i]cl") then
report "test rld[i]cl"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '0';
is_32bit <= '0'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '1';
clear_left <= '1'; clear_right <= '0';
clear_right <= '0'; rldicl_loop : for i in 0 to 1000 loop
rldicl_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= rnd.RandSlv(7);
shift <= rnd.RandSlv(7); insn <= x"00000" & '0' & rnd.RandSlv(10) & '0';
insn <= x"00000" & '0' & rnd.RandSlv(10) & '0'; wait for clk_period;
wait for clk_period; behave_ra := ppc_rldicl(rs, shift(5 downto 0), insn_mb(insn));
behave_ra := ppc_rldicl(rs, shift(5 downto 0), insn_mb(insn)); assert behave_ra = result
assert behave_ra = result report "bad rldicl expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad rldicl expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- rldicr, rldcr elsif run("Test rld[i]cr") then
report "test rld[i]cr"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '0';
is_32bit <= '0'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '0';
clear_left <= '0'; clear_right <= '1';
clear_right <= '1'; rldicr_loop : for i in 0 to 1000 loop
rldicr_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= rnd.RandSlv(7);
shift <= rnd.RandSlv(7); insn <= x"00000" & '0' & rnd.RandSlv(10) & '0';
insn <= x"00000" & '0' & rnd.RandSlv(10) & '0'; wait for clk_period;
wait for clk_period; behave_ra := ppc_rldicr(rs, shift(5 downto 0), insn_me(insn));
behave_ra := ppc_rldicr(rs, shift(5 downto 0), insn_me(insn)); --report "rs = " & to_hstring(rs);
--report "rs = " & to_hstring(rs); --report "ra = " & to_hstring(ra);
--report "ra = " & to_hstring(ra); --report "shift = " & to_hstring(shift);
--report "shift = " & to_hstring(shift); --report "insn me = " & to_hstring(insn_me(insn));
--report "insn me = " & to_hstring(insn_me(insn)); --report "result = " & to_hstring(result);
--report "result = " & to_hstring(result); assert behave_ra = result
assert behave_ra = result report "bad rldicr expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad rldicr expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- rldic elsif run("Test rldic") then
report "test rldic"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '0';
is_32bit <= '0'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '1';
clear_left <= '1'; clear_right <= '1';
clear_right <= '1'; rldic_loop : for i in 0 to 1000 loop
rldic_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= '0' & rnd.RandSlv(6);
shift <= '0' & rnd.RandSlv(6); insn <= x"00000" & '0' & rnd.RandSlv(10) & '0';
insn <= x"00000" & '0' & rnd.RandSlv(10) & '0'; wait for clk_period;
wait for clk_period; behave_ra := ppc_rldic(rs, shift(5 downto 0), insn_mb(insn));
behave_ra := ppc_rldic(rs, shift(5 downto 0), insn_mb(insn)); assert behave_ra = result
assert behave_ra = result report "bad rldic expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad rldic expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- rldimi elsif run("Test rldimi") then
report "test rldimi"; is_32bit <= '0';
is_32bit <= '0'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '1';
clear_left <= '1'; clear_right <= '1';
clear_right <= '1'; rldimi_loop : for i in 0 to 1000 loop
rldimi_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); ra <= rnd.RandSlv(64);
ra <= rnd.RandSlv(64); shift <= '0' & rnd.RandSlv(6);
shift <= '0' & rnd.RandSlv(6); insn <= x"00000" & '0' & rnd.RandSlv(10) & '0';
insn <= x"00000" & '0' & rnd.RandSlv(10) & '0'; wait for clk_period;
wait for clk_period; behave_ra := ppc_rldimi(ra, rs, shift(5 downto 0), insn_mb(insn));
behave_ra := ppc_rldimi(ra, rs, shift(5 downto 0), insn_mb(insn)); assert behave_ra = result
assert behave_ra = result report "bad rldimi expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad rldimi expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- slw elsif run("Test slw") then
report "test slw"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '1';
is_32bit <= '1'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '0';
clear_left <= '0'; clear_right <= '0';
clear_right <= '0'; slw_loop : for i in 0 to 1000 loop
slw_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= rnd.RandSlv(7);
shift <= rnd.RandSlv(7); wait for clk_period;
wait for clk_period; behave_ra := ppc_slw(rs, std_ulogic_vector(resize(unsigned(shift), 64)));
behave_ra := ppc_slw(rs, std_ulogic_vector(resize(unsigned(shift), 64))); assert behave_ra = result
assert behave_ra = result report "bad slw expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad slw expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- sld elsif run("Test sld") then
report "test sld"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '0';
is_32bit <= '0'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '0';
clear_left <= '0'; clear_right <= '0';
clear_right <= '0'; sld_loop : for i in 0 to 1000 loop
sld_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= rnd.RandSlv(7);
shift <= rnd.RandSlv(7); wait for clk_period;
wait for clk_period; behave_ra := ppc_sld(rs, std_ulogic_vector(resize(unsigned(shift), 64)));
behave_ra := ppc_sld(rs, std_ulogic_vector(resize(unsigned(shift), 64))); assert behave_ra = result
assert behave_ra = result report "bad sld expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad sld expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- srw elsif run("Test srw") then
report "test srw"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '1';
is_32bit <= '1'; right_shift <= '1';
right_shift <= '1'; arith <= '0';
arith <= '0'; clear_left <= '0';
clear_left <= '0'; clear_right <= '0';
clear_right <= '0'; srw_loop : for i in 0 to 1000 loop
srw_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= rnd.RandSlv(7);
shift <= rnd.RandSlv(7); wait for clk_period;
wait for clk_period; behave_ra := ppc_srw(rs, std_ulogic_vector(resize(unsigned(shift), 64)));
behave_ra := ppc_srw(rs, std_ulogic_vector(resize(unsigned(shift), 64))); assert behave_ra = result
assert behave_ra = result report "bad srw expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad srw expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- srd elsif run("Test srd") then
report "test srd"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '0';
is_32bit <= '0'; right_shift <= '1';
right_shift <= '1'; arith <= '0';
arith <= '0'; clear_left <= '0';
clear_left <= '0'; clear_right <= '0';
clear_right <= '0'; srd_loop : for i in 0 to 1000 loop
srd_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= rnd.RandSlv(7);
shift <= rnd.RandSlv(7); wait for clk_period;
wait for clk_period; behave_ra := ppc_srd(rs, std_ulogic_vector(resize(unsigned(shift), 64)));
behave_ra := ppc_srd(rs, std_ulogic_vector(resize(unsigned(shift), 64))); assert behave_ra = result
assert behave_ra = result report "bad srd expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad srd expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end loop;


-- sraw[i] elsif run("Test sraw[i]") then
report "test sraw[i]"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '1';
is_32bit <= '1'; right_shift <= '1';
right_shift <= '1'; arith <= '1';
arith <= '1'; clear_left <= '0';
clear_left <= '0'; clear_right <= '0';
clear_right <= '0'; sraw_loop : for i in 0 to 1000 loop
sraw_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= '0' & rnd.RandSlv(6);
shift <= '0' & rnd.RandSlv(6); wait for clk_period;
wait for clk_period; behave_ca_ra := ppc_sraw(rs, std_ulogic_vector(resize(unsigned(shift), 64)));
behave_ca_ra := ppc_sraw(rs, std_ulogic_vector(resize(unsigned(shift), 64))); --report "rs = " & to_hstring(rs);
--report "rs = " & to_hstring(rs); --report "ra = " & to_hstring(ra);
--report "ra = " & to_hstring(ra); --report "shift = " & to_hstring(shift);
--report "shift = " & to_hstring(shift); --report "result = " & to_hstring(carry_out & result);
--report "result = " & to_hstring(carry_out & result); assert behave_ca_ra(63 downto 0) = result and behave_ca_ra(64) = carry_out
assert behave_ca_ra(63 downto 0) = result and behave_ca_ra(64) = carry_out report "bad sraw expected " & to_hstring(behave_ca_ra) & " got " & to_hstring(carry_out & result);
report "bad sraw expected " & to_hstring(behave_ca_ra) & " got " & to_hstring(carry_out & result); end loop;
end loop;


-- srad[i] elsif run("Test srad[i]") then
report "test srad[i]"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '0';
is_32bit <= '0'; right_shift <= '1';
right_shift <= '1'; arith <= '1';
arith <= '1'; clear_left <= '0';
clear_left <= '0'; clear_right <= '0';
clear_right <= '0'; srad_loop : for i in 0 to 1000 loop
srad_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= rnd.RandSlv(7);
shift <= rnd.RandSlv(7); wait for clk_period;
wait for clk_period; behave_ca_ra := ppc_srad(rs, std_ulogic_vector(resize(unsigned(shift), 64)));
behave_ca_ra := ppc_srad(rs, std_ulogic_vector(resize(unsigned(shift), 64))); --report "rs = " & to_hstring(rs);
--report "rs = " & to_hstring(rs); --report "ra = " & to_hstring(ra);
--report "ra = " & to_hstring(ra); --report "shift = " & to_hstring(shift);
--report "shift = " & to_hstring(shift); --report "result = " & to_hstring(carry_out & result);
--report "result = " & to_hstring(carry_out & result); assert behave_ca_ra(63 downto 0) = result and behave_ca_ra(64) = carry_out
assert behave_ca_ra(63 downto 0) = result and behave_ca_ra(64) = carry_out report "bad srad expected " & to_hstring(behave_ca_ra) & " got " & to_hstring(carry_out & result);
report "bad srad expected " & to_hstring(behave_ca_ra) & " got " & to_hstring(carry_out & result); end loop;
end loop;


-- extswsli elsif run("Test extswsli") then
report "test extswsli"; ra <= (others => '0');
ra <= (others => '0'); is_32bit <= '0';
is_32bit <= '0'; right_shift <= '0';
right_shift <= '0'; arith <= '0';
arith <= '0'; clear_left <= '0';
clear_left <= '0'; clear_right <= '0';
clear_right <= '0'; extsw <= '1';
extsw <= '1'; extswsli_loop : for i in 0 to 1000 loop
extswsli_loop : for i in 0 to 1000 loop rs <= rnd.RandSlv(64);
rs <= rnd.RandSlv(64); shift <= '0' & rnd.RandSlv(6);
shift <= '0' & rnd.RandSlv(6); wait for clk_period;
wait for clk_period; behave_ra := rs;
behave_ra := rs; behave_ra(63 downto 32) := (others => rs(31));
behave_ra(63 downto 32) := (others => rs(31)); behave_ra := std_ulogic_vector(shift_left(unsigned(behave_ra),
behave_ra := std_ulogic_vector(shift_left(unsigned(behave_ra), to_integer(unsigned(shift))));
to_integer(unsigned(shift)))); --report "rs = " & to_hstring(rs);
--report "rs = " & to_hstring(rs); --report "ra = " & to_hstring(ra);
--report "ra = " & to_hstring(ra); --report "shift = " & to_hstring(shift);
--report "shift = " & to_hstring(shift); --report "result = " & to_hstring(carry_out & result);
--report "result = " & to_hstring(carry_out & result); assert behave_ra = result
assert behave_ra = result report "bad extswsli expected " & to_hstring(behave_ra) & " got " & to_hstring(result);
report "bad extswsli expected " & to_hstring(behave_ra) & " got " & to_hstring(result); end loop;
end if;
end loop; end loop;

test_runner_cleanup(runner); test_runner_cleanup(runner);
end process; end process;
end behave; end behave;

Loading…
Cancel
Save