Commit flag setter for issue.
[firearm.git] / Issue.v
1 `include "ARM_Constants.v"
2
3 module Issue(
4         input clk,
5         input Nrst,
6         
7         input stall,    /* pipeline control */
8         input flush,
9         
10         input inbubble, /* stage inputs */
11         input [31:0] insn,
12         input [31:0] inpc,
13         
14         output reg outbubble,   /* stage outputs */
15         output reg [31:0] outpc
16         /* other */
17         );
18         
19         always @(posedge clk)
20         begin
21                 outbubble <= inbubble;
22                 outpc <= inpc;
23         end
24
25 `ifdef COPY_PASTA_FODDER
26         /* from page 2 of ARM7TDMIvE2.pdf */
27         casex (insn)
28         32'b????000000??????????????1001????:   /* Multiply -- must come before ALU, because it pattern matches a specific case of ALU */
29 //      32'b????00001???????????????1001????:   /* Multiply long */
30         32'b????00010?001111????000000000000:   /* MRS (Transfer PSR to register) */
31         32'b????00010?101001111100000000????:   /* MSR (Transfer register to PSR) */
32         32'b????00?10?1010001111????????????:   /* MSR (Transfer register or immediate to PSR, flag bits only) */
33         32'b????00??????????????????????????:   /* ALU */
34         32'b????00010?00????????00001001????:   /* Atomic swap */
35         32'b????000100101111111111110001????:   /* Branch */
36         32'b????000??0??????????00001??1????:   /* Halfword transfer - register offset */
37         32'b????000??1??????????00001??1????:   /* Halfword transfer - register offset */
38         32'b????011????????????????????1????:   /* Undefined. I hate ARM */
39         32'b????01??????????????????????????:   /* Single data transfer */
40         32'b????100?????????????????????????:   /* Block data transfer */
41         32'b????101?????????????????????????:   /* Branch */
42         32'b????110?????????????????????????:   /* Coprocessor data transfer */
43         32'b????1110???????????????????0????:   /* Coprocessor data op */
44         32'b????1110???????????????????1????:   /* Coprocessor register transfer */
45         32'b????1111????????????????????????:   /* SWI */
46         default:                                /* X everything else out */
47         endcase
48 `endif
49
50         /* Flag setting */
51         reg use_cpsr;
52         reg [15:0] use_regs;
53         reg def_cpsr;
54         reg [15:0] def_regs;
55         
56         function [15:0] idxbit;
57                 input [3:0] r;
58                 if (r == 15)
59                         idxbit = 0;
60                 else
61                         idxbit = (16'b1) << r;
62         endfunction
63         
64         wire [3:0] rn = insn[19:16];
65         wire [3:0] rd = insn[15:12];
66         wire [3:0] rs = insn[11:8];
67         wire [3:0] rm = insn[3:0];
68         wire [3:0] cond = insn[31:28];
69         
70         wire [3:0] rd_mul = insn[19:16];
71         wire [3:0] rn_mul = insn[15:12];
72         wire [3:0] rs_mul = insn[11:8];
73         
74         wire [3:0] alu_opc = insn[24:21];
75         
76         function alu_is_logical;
77                 input [3:0] op;
78                 
79                 case (op)
80                 `ALU_AND,`ALU_EOR,`ALU_TST,`ALU_TEQ,`ALU_ORR,`ALU_MOV,`ALU_BIC,`ALU_MVN: alu_is_logical = 1;
81                 default: alu_is_logical = 0;
82                 endcase
83         endfunction
84         
85         function alu_flags_only;
86                 input [3:0] op;
87                 
88                 case (op)
89                 `ALU_TST,`ALU_TEQ,`ALU_CMP,`ALU_CMN: alu_flags_only = 1;
90                 default: alu_flags_only = 0;
91                 endcase
92         endfunction
93         
94         function shift_requires_carry;
95                 input [7:0] shift;
96                 
97                 case(shift[1:0])
98                 `SHIFT_LSL: shift_requires_carry = (shift[7:2] == 0);
99                 `SHIFT_LSR: shift_requires_carry = 0;
100                 `SHIFT_ASR: shift_requires_carry = 0;
101                 `SHIFT_ROR: shift_requires_carry = (shift[7:2] == 0);
102                 endcase
103         endfunction
104         
105         always @(*)
106                 casez (insn)
107                 32'b????000000??????????????1001????:   /* Multiply -- must come before ALU, because it pattern matches a specific case of ALU */
108                 begin
109                         use_cpsr = `COND_MATTERS(cond);
110                         use_regs = (insn[21] /* accum */ ? idxbit(rn_mul) : 0) | idxbit(rs_mul) | idxbit(rm);
111                         def_cpsr = insn[20] /* setcc */;
112                         def_regs = idxbit(rd_mul);
113                 end
114 //              32'b????00001???????????????1001????:   /* Multiply long */
115                 32'b????00010?001111????000000000000:   /* MRS (Transfer PSR to register) */
116                 begin
117                         use_cpsr = `COND_MATTERS(cond) || (insn[22] == 0) /* Source = CPSR */;
118                         use_regs = 0;
119                         def_cpsr = 0;
120                         def_regs = idxbit(rd);
121                 end
122                 32'b????00010?101001111100000000????:   /* MSR (Transfer register to PSR) */
123                 begin
124                         use_cpsr = `COND_MATTERS(cond);
125                         use_regs = idxbit(rm);
126                         def_cpsr = 1;
127                         def_regs = 0;
128                 end
129                 32'b????00?10?1010001111????????????:   /* MSR (Transfer register or immediate to PSR, flag bits only) */
130                 begin
131                         use_cpsr = `COND_MATTERS(cond);
132                         use_regs = insn[25] ? 0 : idxbit(rm);
133                         def_cpsr = 1;
134                         def_regs = 0;
135                 end
136                 32'b????00??????????????????????????:   /* ALU */
137                 begin
138                         use_cpsr = `COND_MATTERS(cond) | (!insn[25] /* I */ && shift_requires_carry(insn[11:4]));
139                         use_regs =
140                                 (insn[25] /* I */ ? 0 :
141                                         (insn[4] /* shift by reg */ ?
142                                                 (idxbit(rs) | idxbit(rm)) :
143                                                 (idxbit(rm)))) |
144                                 (((alu_opc != `ALU_MOV) && (alu_opc != `ALU_MVN)) ? idxbit(rn) : 0);
145                         def_cpsr = insn[20] /* S */ | alu_is_logical(alu_opc);
146                         def_regs = alu_flags_only(alu_opc) ? 0 : idxbit(rd);
147                 end
148                 32'b????00010?00????????00001001????:   /* Atomic swap */
149                 begin
150                         use_cpsr = `COND_MATTERS(cond);
151                         use_regs = idxbit(rn) | idxbit(rm);
152                         def_cpsr = 0;
153                         def_regs = idxbit(rd);
154                 end
155                 32'b????000100101111111111110001????:   /* Branch */
156                 begin
157                         use_cpsr = `COND_MATTERS(cond);
158                         use_regs = idxbit(rm);
159                         def_cpsr = 0;   // don't care, we'll never get there
160                         def_regs = 0;
161                 end
162                 32'b????000??0??????????00001??1????:   /* Halfword transfer - register offset */
163                 begin
164                         use_cpsr = `COND_MATTERS(cond);
165                         use_regs = idxbit(rn) | idxbit(rm) | (insn[20] /* L */ ? 0 : idxbit(rd));
166                         def_cpsr = 0;
167                         def_regs = insn[20] /* L */ ? idxbit(rd) : 0;
168                 end
169                 32'b????000??1??????????00001??1????:   /* Halfword transfer - immediate offset */
170                 begin
171                         use_cpsr = `COND_MATTERS(cond);
172                         use_regs = idxbit(rn) | (insn[20] /* L */ ? 0 : idxbit(rd));
173                         def_cpsr = 0;
174                         def_regs = insn[20] /* L */ ? idxbit(rd) : 0;
175                 end
176                 32'b????011????????????????????1????:   /* Undefined. I hate ARM */
177                 begin   
178                         use_cpsr = 0;
179                         use_regs = 0;
180                         def_cpsr = 0;
181                         def_regs = 0;
182                 end
183                 32'b????100?????????????????????????:   /* Block data transfer */
184                 begin
185                         use_cpsr = `COND_MATTERS(cond);
186                         use_regs = idxbit(rn) | (insn[20] /* L */ ? 0 : insn[15:0]);
187                         def_cpsr = insn[22];    /* This is a superset of all cases, anyway. */
188                         def_regs = (insn[21] /* W */ ? idxbit(rn) : 0) | (insn[20] /* L */ ? insn[15:0] : 0);
189                 end
190                 32'b????101?????????????????????????:   /* Branch */
191                 begin
192                         use_cpsr = `COND_MATTERS(cond);
193                         use_regs = 0;
194                         def_cpsr = 0;
195                         def_regs = 0;
196                 end
197                 32'b????110?????????????????????????:   /* Coprocessor data transfer */
198                 begin
199                         use_cpsr = `COND_MATTERS(cond);
200                         use_regs = idxbit(rn);
201                         def_cpsr = 0;
202                         def_regs = insn[21] /* W */ ? idxbit(rn) : 0;
203                 end
204                 32'b????1110???????????????????0????:   /* Coprocessor data op */
205                 begin
206                         use_cpsr = `COND_MATTERS(cond);
207                         use_regs = 0;
208                         def_cpsr = 0;
209                         def_regs = 0;
210                 end
211                 32'b????1110???????????????????1????:   /* Coprocessor register transfer */
212                 begin
213                         use_cpsr = `COND_MATTERS(cond);
214                         use_regs = insn[20] /* L */ ? 0 : idxbit(rd);
215                         def_cpsr = 0;
216                         def_regs = insn[20] /* L */ ? idxbit(rd) : 0;
217                 end
218                 32'b????1111????????????????????????:   /* SWI */
219                 begin
220                         use_cpsr = `COND_MATTERS(cond);
221                         use_regs = 0;
222                         def_cpsr = 0;
223                         def_regs = 0;
224                 end
225                 default:                                /* X everything else out */
226                 begin
227                         use_cpsr = 1'bx;
228                         use_regs = 16'bxxxxxxxxxxxxxxxx;
229                         def_cpsr = 1'bx;
230                         def_regs = 16'bxxxxxxxxxxxxxxxx;
231                 end
232                 endcase
233 endmodule
This page took 0.030243 seconds and 4 git commands to generate.