aba54cb514cb1fdde1edd792e4c49ed0e6206323
[hwmod.git] / src / beh_alu_tb.vhd
1 library ieee;
2 use ieee.std_logic_1164.all;
3 use ieee.numeric_std.all;
4 use work.gen_pkg.all;
5
6 entity beh_alu_tb is
7 end entity beh_alu_tb;
8
9 architecture sim of beh_alu_tb is
10         signal sys_clk, sys_res_n, do_calc, calc_done, calc_error : std_logic;
11         signal opcode : alu_ops;
12         signal op1, op2, op3, opM : csigned;
13         signal stop : boolean := false;
14 begin
15         inst : entity work.alu(beh)
16         port map
17         (
18                 sys_clk => sys_clk,
19                 sys_res_n => sys_res_n,
20                 do_calc => do_calc,
21                 calc_done => calc_done,
22                 op1 => op1,
23                 op2 => op2,
24                 op3 => op3,
25                 opM => opM,
26                 opcode => opcode,
27                 calc_error => calc_error
28         );
29
30         process
31         begin
32                 sys_clk <= '0';
33                 wait for 15 ns;
34                 sys_clk <= '1';
35                 wait for 15 ns;
36                 if stop = true then
37                         wait;
38                 end if;
39         end process;
40
41         process
42                 type alu_testv is record
43                         o1 : cinteger;
44                         o : alu_ops;
45                         o2 : cinteger;
46                         om : cinteger;
47                         expected : cinteger;
48                         errcase : boolean;
49                 end record alu_testv;
50
51                 -- ggf. groesse des arrays erhoehen
52                 type alu_testv_array is array (natural range 0 to 65) of alu_testv;
53
54                 variable testmatrix : alu_testv_array :=
55                         ( 0 => (-5, ALU_DIV, 3, 2, -1, false),
56                           1 => (7, ALU_ADD, 3, 0, 10, false),
57                           2 => (7, ALU_SUB, 1, 0, 6, false),
58                           3 => (7, ALU_DIV, 1, 0, 7, false),
59                           4 => (7, ALU_DIV, 3, 1, 2, false),
60                           5 => (7, ALU_ADD, 1, 0, 8, false),
61                           6 => (7, ALU_MUL, 3, 0, 21, false),
62                           7 => (-7, ALU_MUL, 3, 0, -21, false),
63                           8 => (268435456, ALU_MUL, -2, 0, -536870912, false),
64                           9 => (268435456, ALU_MUL, 2**5, 0, 0, false), -- um fuenf nach links shiften
65                           10 => (268435456 + 5, ALU_MUL, 2**5, 0, 160, false), -- = 5 * (2^5)
66                           11 => (100, ALU_DIV, 10, 0, 10, false),
67                           12 => (100, ALU_DIV, 51, 49, 1, false),
68                           13 => (100, ALU_DIV, 49, 2, 2, false),
69                           14 => (153156, ALU_DIV, 3543, 807, 43, false),
70                           15 => (-153156, ALU_DIV, 3543, 807, -43, false),
71                           16 => (153156, ALU_DIV, -3543, 807, -43, false),
72                           17 => (-153156, ALU_DIV, -3543, 807, 43, false),
73                           -- add: sign and under-/overflow check
74                           18 => (2147483647, ALU_ADD, -1, 0, 2147483646, false),
75                           19 => (2147483647, ALU_ADD, 1, 0, 0, true),
76                           20 => (-2147483645, ALU_ADD, -100, 0, 0, true),
77                           21 => (7, ALU_ADD, 1, 0, 8, false),
78                           22 => (7, ALU_ADD, -1, 0, 6, false),
79                           23 => (-7, ALU_ADD, 1, 0, -6, false),
80                           24 => (-7, ALU_ADD, -1, 0, -8, false),
81                           -- sub: sign and under-/overflow check
82                           25 => (-7, ALU_SUB, 1, 0, -8, false),
83                           26 => (-7, ALU_SUB, -1, 0, -6, false),
84                           27 => (7, ALU_SUB, 1, 0, 6, false),
85                           28 => (7, ALU_SUB, -1, 0, 8, false),
86                           29 => (-2147483645, ALU_SUB, 1000, 0, 0, true),
87                           30 => (2147483645, ALU_SUB, -1000, 0, 0, true),
88                           31 => (-1000, ALU_SUB, 2147483645, 0, 0, true),
89                           32 => (1000, ALU_SUB, -2147483645, 0, 0, true),
90                           -- mul: sign and under-/overflow check
91                           33 => (3, ALU_MUL, 2, 0, 6, false),
92                           34 => (3, ALU_MUL, -2, 0, -6, false),
93                           35 => (-3, ALU_MUL, 2, 0, -6, false),
94                           36 => (-3, ALU_MUL, -2, 0, 6, false),
95                           37 => (90000, ALU_MUL, 100000, 0, 0, true),
96                           38 => (90000, ALU_MUL, -100000, 0, 0, true),
97                           39 => (-90000, ALU_MUL, 100000, 0, 0, true),
98                           40 => (-90000, ALU_MUL, -100000, 0, 0, true),
99                           -- div: overflow check und division durch null
100                           41 => (-2147483648, ALU_DIV, -1, 0, 0, true),
101                           42 => (-2147483648, ALU_DIV, 0, 0, 0, true),
102                           43 => (-4, ALU_DIV, 2, 0, -2, false),
103                           -- div/mod:
104                           44 => (1234, ALU_DIV, 3, 1, 411, false),
105                           45 => (1, ALU_DIV, 10, 1, 0, false),
106                           46 => (2, ALU_DIV, 10, 2, 0, false),
107                           47 => (3, ALU_DIV, 10, 3, 0, false),
108                           48 => (4, ALU_DIV, 10, 4, 0, false),
109                           49 => (5, ALU_DIV, 10, 5, 0, false),
110                           50 => (6, ALU_DIV, 10, 6, 0, false),
111                           51 => (7, ALU_DIV, 10, 7, 0, false),
112                           52 => (8, ALU_DIV, 10, 8, 0, false),
113                           53 => (9, ALU_DIV, 10, 9, 0, false),
114                           54 => (0, ALU_DIV, 10, 0, 0, false),
115                           55 => (10, ALU_DIV, 10, 0, 1, false),
116                           56 => (5134123, ALU_DIV, 358015, 121913, 14, false),
117                           -- extra
118                           60 => (5, ALU_SUB, -2147483648, 0, 0, true),
119                           others => (0, ALU_ADD, 0, 0, 0, false)
120                         );
121                 variable checkall : boolean := true;
122         begin
123                 -- init & reset
124                 sys_res_n <= '0';
125                 do_calc <= '0';
126                 opcode <= ALU_NOP;
127                 op1 <= (others => '0');
128                 op2 <= (others => '0');
129
130                 icwait(sys_clk, 30);
131                 sys_res_n <= '1';
132
133                 for i in testmatrix'range loop
134                         icwait(sys_clk, 10);
135                         op1 <= to_signed(testmatrix(i).o1,CBITS);
136                         opcode <= testmatrix(i).o;
137                         op2 <= to_signed(testmatrix(i).o2,CBITS);
138
139                         -- berechnung kann los gehen
140                         do_calc <= '1';
141
142                         -- warten auf die alu einheit
143                         wait on calc_done;
144                         icwait(sys_clk, 1);
145
146                         if testmatrix(i).errcase then
147                                 if (calc_error = '0') then
148                                         assert(false) report "sollte ein error sein";
149                                         assert op3 = to_signed(testmatrix(i).expected,CBITS)
150                                                 report "" & cinteger'image(testmatrix(i).o1) & 
151                                                 " " & integer'image(to_integer(signed(opcode))) &
152                                                 " " & cinteger'image(testmatrix(i).o2) &
153                                                 " /= " & integer'image(to_integer(op3)) &
154                                                 " ( " & integer'image(to_integer(opM)) & " ) " &
155                                                 " -- erwartet: " & cinteger'image(testmatrix(i).expected) &
156                                                 " ( " & cinteger'image(testmatrix(i).om) & " ) ";
157                                         checkall := false;
158                                 else
159                                         assert(false) report "testfall war ein error (passt)";
160                                 end if;
161                         else
162                                 assert ((op3 = to_signed(testmatrix(i).expected,CBITS)) and (opM = to_signed(testmatrix(i).om,CBITS)))
163                                         report "" & cinteger'image(testmatrix(i).o1) & 
164                                         " " & integer'image(to_integer(signed(opcode))) &
165                                         " " & cinteger'image(testmatrix(i).o2) &
166                                         " /= " & integer'image(to_integer(op3)) &
167                                         " ( " & integer'image(to_integer(opM)) & " ) " &
168                                         " -- erwartet: " & cinteger'image(testmatrix(i).expected) &
169                                         " ( " & cinteger'image(testmatrix(i).om) & " ) ";
170
171                                 if not((op3 = to_signed(testmatrix(i).expected,CBITS)) and (opM = to_signed(testmatrix(i).om,CBITS))) then
172                                         checkall := false;
173                                 end if;
174                         end if;
175
176                         icwait(sys_clk, 2);
177                         -- ack it!
178                         do_calc <= '0';
179                 end loop;
180
181                 if checkall then
182                         report "alle testfaelle der ALU waren erfolgreich!";
183                 else
184                         report "einige testfaelle schlugen fehl";
185                 end if;
186                 stop <= true;
187                 wait;
188         end process;
189 end architecture sim;