OpenCores
URL https://opencores.org/ocsvn/aemb/aemb/trunk

Subversion Repositories aemb

[/] [aemb/] [trunk/] [rtl/] [verilog/] [aeMB2_intu.v] - Blame information for rev 205

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 158 sybreon
/* $Id: aeMB2_intu.v,v 1.7 2008-05-01 12:00:18 sybreon Exp $
2 118 sybreon
**
3
** AEMB2 EDK 6.2 COMPATIBLE CORE
4
** Copyright (C) 2004-2008 Shawn Tan <shawn.tan@aeste.net>
5
**
6
** This file is part of AEMB.
7
**
8
** AEMB is free software: you can redistribute it and/or modify it
9
** under the terms of the GNU Lesser General Public License as
10
** published by the Free Software Foundation, either version 3 of the
11
** License, or (at your option) any later version.
12
**
13
** AEMB is distributed in the hope that it will be useful, but WITHOUT
14
** ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
15
** or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General
16
** Public License for more details.
17
**
18
** You should have received a copy of the GNU Lesser General Public
19
** License along with AEMB. If not, see <http:**www.gnu.org/licenses/>.
20
*/
21
/**
22
 * One Cycle Integer Unit
23
 * @file aeMB2_intu.v
24
 
25
 * This implements a single cycle integer unit. It performs all basic
26
   arithmetic, shift, and logic operations.
27
 
28
 */
29
 
30
module aeMB2_intu (/*AUTOARG*/
31
   // Outputs
32
   mem_ex, bpc_ex, alu_ex, alu_mx, msr_ex, sfr_mx,
33
   // Inputs
34
   opc_of, opa_of, opb_of, opd_of, imm_of, rd_of, ra_of, gclk, grst,
35
   dena, gpha
36
   );
37
   parameter AEMB_DWB = 32;
38
   parameter AEMB_IWB = 32;
39
   parameter AEMB_HTX = 1;
40
 
41
   output [31:2] mem_ex;
42
   output [31:2] bpc_ex;
43
 
44
   output [31:0] alu_ex,
45
                 alu_mx;
46 205 sybreon
 
47 150 sybreon
   //input [2:0]         mux_of;   
48 118 sybreon
   input [5:0]    opc_of;
49
   input [31:0]  opa_of;
50
   input [31:0]  opb_of;
51
   input [31:0]  opd_of;
52
   input [15:0]  imm_of;
53
   input [4:0]    rd_of,
54
                 ra_of;
55 204 sybreon
   output [9:0]  msr_ex;
56 118 sybreon
   output [31:0] sfr_mx;
57
 
58
   // SYS signals
59
   input         gclk,
60
                 grst,
61
                 dena,
62
                 gpha;
63
 
64
   /*AUTOREG*/
65
   // Beginning of automatic regs (for this module's undeclared outputs)
66
   reg [31:0]            alu_ex;
67
   reg [31:0]            alu_mx;
68
   reg [31:2]           bpc_ex;
69
   reg [31:2]           mem_ex;
70
   reg [31:0]            sfr_mx;
71
   // End of automatics
72
 
73 150 sybreon
   localparam [2:0]      MUX_SFR = 3'o7,
74
                        MUX_BSF = 3'o6,
75
                        MUX_MUL = 3'o5,
76
                        MUX_MEM = 3'o4,
77
 
78
                        MUX_RPC = 3'o2,
79
                        MUX_ALU = 3'o1,
80
                        MUX_NOP = 3'o0;
81
 
82 118 sybreon
   reg                  rMSR_C,
83 204 sybreon
                        rMSR_EE,
84
                        rMSR_EIP,
85 118 sybreon
                        rMSR_CC,
86
                        rMSR_MTX,
87 150 sybreon
                        rMSR_DTE,
88
                        rMSR_ITE,
89 118 sybreon
                        rMSR_BIP,
90
                        rMSR_IE,
91
                        rMSR_BE;
92 134 sybreon
 
93 150 sybreon
   // Infer a ADD with carry cell because ADDSUB cannot be inferred
94
   // across technologies.
95 118 sybreon
 
96
   reg [31:0]            add_ex;
97
   reg                  add_c;
98 131 sybreon
 
99 125 sybreon
   wire [31:0]           wADD;
100
   wire                 wADC;
101 118 sybreon
 
102 150 sybreon
   wire                 fCCC = !opc_of[5] & opc_of[1]; // & !opc_of[4]
103
   wire                 fSUB = !opc_of[5] & opc_of[0]; // & !opc_of[4]
104 158 sybreon
   wire                 fCMP = !opc_of[3] & imm_of[1]; // unsigned only
105
   wire                 wCMP = (fCMP) ? !wADC : wADD[31]; // cmpu adjust
106 118 sybreon
 
107 131 sybreon
   wire [31:0]           wOPA = (fSUB) ? ~opa_of : opa_of;
108 118 sybreon
   wire                 wOPC = (fCCC) ? rMSR_CC : fSUB;
109
 
110 150 sybreon
   assign               {wADC, wADD} = (opb_of + wOPA) + wOPC; // add carry
111 118 sybreon
 
112 150 sybreon
   always @(/*AUTOSENSE*/wADC or wADD or wCMP) begin
113
      {add_c, add_ex} <= #1 {wADC, wCMP, wADD[30:0]}; // add with carry
114 118 sybreon
   end
115
 
116
   // SHIFT/LOGIC/MOVE
117
   reg [31:0]            slm_ex;
118
 
119
   always @(/*AUTOSENSE*/imm_of or opa_of or opb_of or opc_of
120
            or rMSR_CC)
121
     case (opc_of[2:0])
122
       // LOGIC
123
       3'o0: slm_ex <= #1 opa_of | opb_of;
124
       3'o1: slm_ex <= #1 opa_of & opb_of;
125
       3'o2: slm_ex <= #1 opa_of ^ opb_of;
126
       3'o3: slm_ex <= #1 opa_of & ~opb_of;
127
       // SHIFT/SEXT
128
       3'o4: case ({imm_of[6:5],imm_of[0]})
129
               3'o1: slm_ex <= #1 {opa_of[31],opa_of[31:1]}; // SRA
130
               3'o3: slm_ex <= #1 {rMSR_CC,opa_of[31:1]}; // SRC
131
               3'o5: slm_ex <= #1 {1'b0,opa_of[31:1]}; // SRL
132
               3'o6: slm_ex <= #1 {{(24){opa_of[7]}}, opa_of[7:0]}; // SEXT8
133
               3'o7: slm_ex <= #1  {{(16){opa_of[15]}}, opa_of[15:0]}; // SEXT16
134 125 sybreon
               default: slm_ex <= #1 32'hX;
135 118 sybreon
             endcase // case ({imm_of[6:5],imm_of[0]})
136
       // MFS/MTS/MSET/MCLR
137
       //3'o5: slm_ex <= #1 sfr_of;       
138
       // BRL (PC from SFR)
139
       //3'o6: slm_ex <= #1 sfr_of;
140
       default: slm_ex <= #1 32'hX;
141
     endcase // case (opc_of[2:0])
142
 
143
   // ALU RESULT
144
   always @(posedge gclk)
145
     if (grst) begin
146
        /*AUTORESET*/
147
        // Beginning of autoreset for uninitialized flops
148
        alu_ex <= 32'h0;
149
        alu_mx <= 32'h0;
150 131 sybreon
        bpc_ex <= 30'h0;
151 118 sybreon
        mem_ex <= 30'h0;
152
        // End of automatics
153
     end else if (dena) begin
154
        alu_mx <= #1 alu_ex;
155
        alu_ex <= #1 (opc_of[5]) ? slm_ex : add_ex;
156 134 sybreon
        mem_ex <= #1 wADD[AEMB_DWB-1:2]; // LXX/SXX     
157 131 sybreon
        bpc_ex <= #1
158
                  (!opc_of[0] & ra_of[3]) ? // check for BRA
159
                  opb_of[AEMB_IWB-1:2] : // BRA only
160 134 sybreon
                  wADD[AEMB_IWB-1:2]; // RTD/BCC/BR
161 118 sybreon
     end
162
 
163
   // MSR SECTION
164
 
165
   /*
166
    MSR REGISTER
167
 
168
    We should keep common configuration bits in the lower 16-bits of
169
    the MSR in order to avoid using the IMMI instruction.
170
 
171
    MSR bits
172
    31 - CC (carry copy)
173
    30 - HTE (hardware thread enabled)
174
    29 - PHA (current phase)
175
 
176 150 sybreon
    7  - DTE (data cache enable)
177
    5  - ITE (instruction cache enable)
178 125 sybreon
    4  - MTX (hardware mutex bit)
179
    3  - BIP (break in progress)
180
    2  - C (carry flag)
181
    1  - IE (interrupt enable)
182
 
183 118 sybreon
    */
184
 
185
   assign msr_ex = {
186 204 sybreon
                    rMSR_EIP,
187
                    rMSR_EE,
188 150 sybreon
                    rMSR_DTE,
189 118 sybreon
                    1'b0,
190 150 sybreon
                    rMSR_ITE,
191 118 sybreon
                    rMSR_MTX,
192
                    rMSR_BIP,
193
                    rMSR_C,
194
                    rMSR_IE,
195
                    rMSR_BE
196
                    };
197
 
198
   // MSRSET/MSRCLR (small ALU)
199 204 sybreon
   wire [9:0] wRES = (ra_of[0]) ?
200
              (msr_ex[9:0]) & ~imm_of[9:0] : // MSRCLR
201
              (msr_ex[9:0]) | imm_of[9:0]; // MSRSET      
202 118 sybreon
 
203
   // 0 - Break
204
   // 1 - Interrupt
205
   // 2 - Exception
206
   // 3 - Reserved
207 204 sybreon
 
208
   // break
209
   wire       fRTBD = (opc_of == 6'o55) & rd_of[1];
210
   wire       fBRKB = ((opc_of == 6'o46) | (opc_of == 6'o56)) & (ra_of[4:0] == 5'hC);
211
 
212
   // interrupt
213 150 sybreon
   wire       fRTID = (opc_of == 6'o55) & rd_of[0];
214
   wire       fBRKI = (opc_of == 6'o56) & (ra_of[4:0] == 5'hD);
215 204 sybreon
 
216
   // exception
217
   wire       fRTED = (opc_of == 6'o55) & rd_of[2];
218
   wire       fBRKE = (opc_of == 6'o56) & (ra_of[4:0] == 5'hE);
219 125 sybreon
 
220 150 sybreon
   wire       fMOV = (opc_of == 6'o45);
221
   wire       fMTS = fMOV & &imm_of[15:14];
222
   wire       fMOP = fMOV & ~|imm_of[15:14];
223 118 sybreon
 
224 150 sybreon
   reg [31:0] sfr_ex;
225
 
226 118 sybreon
   always @(posedge gclk)
227
     if (grst) begin
228
        /*AUTORESET*/
229
        // Beginning of autoreset for uninitialized flops
230
        rMSR_BE <= 1'h0;
231
        rMSR_BIP <= 1'h0;
232 150 sybreon
        rMSR_DTE <= 1'h0;
233 205 sybreon
        rMSR_EE <= 1'h0;
234
        rMSR_EIP <= 1'h0;
235 118 sybreon
        rMSR_IE <= 1'h0;
236 150 sybreon
        rMSR_ITE <= 1'h0;
237 118 sybreon
        rMSR_MTX <= 1'h0;
238
        sfr_ex <= 32'h0;
239
        sfr_mx <= 32'h0;
240
        // End of automatics
241
     end else if (dena) begin // if (grst)
242
        sfr_mx <= #1 sfr_ex;
243
        sfr_ex <= #1
244
                  {rMSR_CC,
245
                   AEMB_HTX[0],
246 126 sybreon
                   gpha,
247 118 sybreon
                   21'd0,
248 150 sybreon
                   rMSR_DTE,
249 118 sybreon
                   1'b0,
250 150 sybreon
                   rMSR_ITE,
251 118 sybreon
                   rMSR_MTX,
252
                   rMSR_BIP,
253
                   rMSR_CC,
254
                   rMSR_IE,
255
                   rMSR_BE
256
                   };
257 158 sybreon
 
258 150 sybreon
        rMSR_DTE <= #1
259 118 sybreon
                   (fMTS) ? opa_of[7] :
260
                   (fMOP) ? wRES[7] :
261 150 sybreon
                   rMSR_DTE;
262 134 sybreon
 
263 150 sybreon
        rMSR_ITE <= #1
264 118 sybreon
                   (fMTS) ? opa_of[5] :
265
                   (fMOP) ? wRES[5] :
266 150 sybreon
                   rMSR_ITE;
267 118 sybreon
 
268
        rMSR_MTX <= #1
269
                   (fMTS) ? opa_of[4] :
270
                   (fMOP) ? wRES[4] :
271
                   rMSR_MTX;
272
 
273
        rMSR_BE <= #1
274
                   (fMTS) ? opa_of[0] :
275
                   (fMOP) ? wRES[0] :
276
                   rMSR_BE;
277
 
278 158 sybreon
        rMSR_IE <= #1
279
                   (fBRKI) ? 1'b0 :
280
                   (fRTID) ? 1'b1 :
281
                   (fMTS) ? opa_of[1] :
282
                   (fMOP) ? wRES[1] :
283
                   rMSR_IE;
284
 
285
        rMSR_BIP <= #1
286
                    (fBRKB) ? 1'b1 :
287
                    (fRTBD) ? 1'b0 :
288
                    (fMTS) ? opa_of[3] :
289
                    (fMOP) ? wRES[3] :
290
                    rMSR_BIP;
291 204 sybreon
 
292
        rMSR_EE <= #1
293
                   (fBRKE) ? 1'b0 :
294
                   (fRTED) ? 1'b1 :
295
                   (fMTS) ? opa_of[8] :
296
                   (fMOP) ? wRES[8] :
297
                   rMSR_EE;
298
 
299
        rMSR_EIP <= #1
300
                    (fBRKE) ? 1'b1 :
301
                    (fRTED) ? 1'b0 :
302
                    (fMTS) ? opa_of[9] :
303
                    (fMOP) ? wRES[9] :
304
                    rMSR_EIP;
305
 
306 158 sybreon
        /*
307
 
308 134 sybreon
        case ({fMTS, fMOP})
309 150 sybreon
          2'o2: {rMSR_DTE,
310
                 rMSR_ITE,
311 134 sybreon
                 rMSR_MTX,
312
                 rMSR_BE} <= #1 {opa_of[7],
313
                                 opa_of[5],
314
                                 opa_of[4],
315
                                 opa_of[0]};
316 150 sybreon
          2'o1: {rMSR_DTE,
317
                 rMSR_ITE,
318 134 sybreon
                 rMSR_MTX,
319
                 rMSR_BE} <= #1 {wRES[7],
320
                                 wRES[5],
321
                                 wRES[4],
322
                                 wRES[0]};
323 150 sybreon
          default: {rMSR_DTE,
324
                    rMSR_ITE,
325 134 sybreon
                    rMSR_MTX,
326 150 sybreon
                    rMSR_BE} <= #1 {rMSR_DTE,
327
                                    rMSR_ITE,
328 134 sybreon
                                    rMSR_MTX,
329
                                    rMSR_BE};
330
        endcase // case ({fMTS, fMOP})
331
 
332
        case ({fMTS, fMOP})
333
          2'o2: {rMSR_BIP,
334
                 rMSR_IE} <= #1 {opa_of[3],
335
                                 opa_of[1]};
336
          2'o1: {rMSR_BIP,
337
                 rMSR_IE} <= #1 {wRES[3],
338
                                 wRES[1]};
339
          default: begin
340
             rMSR_BIP <= #1 (fBRKB | fRTBD) ? !rMSR_BIP : rMSR_BIP;
341
             rMSR_IE <= #1 (fBRKI | fRTID) ? !rMSR_IE : rMSR_IE;
342
          end
343
        endcase // case ({fMTS, fMOP})
344 158 sybreon
         */
345 125 sybreon
     end // if (dena)
346 118 sybreon
 
347
   // BARREL C
348 158 sybreon
   wire fADDSUB = !opc_of[5] & !opc_of[4] & !opc_of[2];
349
   // (opc_of[5:2] == 4'h0) | (opc_of[5:2] == 4'h2);
350
   wire fSHIFT  = (opc_of == 6'o44) & &imm_of[6:5];
351 125 sybreon
 
352 118 sybreon
   always @(posedge gclk)
353
     if (grst) begin
354
        /*AUTORESET*/
355
     end else if (dena) begin
356
     end
357 125 sybreon
 
358 118 sybreon
   always @(posedge gclk)
359
     if (grst) begin
360
        /*AUTORESET*/
361
        // Beginning of autoreset for uninitialized flops
362
        rMSR_C <= 1'h0;
363 131 sybreon
        rMSR_CC <= 1'h0;
364 118 sybreon
        // End of automatics
365
     end else if (dena) begin
366 131 sybreon
        rMSR_CC <= #1 rMSR_C;
367 158 sybreon
 
368 118 sybreon
        rMSR_C <= #1
369
                  (fMTS) ? opa_of[2] :
370
                  (fMOP) ? wRES[2] :
371
                  (fSHIFT) ? opa_of[0] : // SRA/SRL/SRC
372
                  (fADDSUB) ? add_c : // ADD/SUB/ADDC/SUBC
373
                  rMSR_CC;
374 158 sybreon
 
375
        /*
376
        case ({fMTS,fMOP,fSHIFT,fADDSUB})
377
          4'h8: rMSR_C <= #1 opa_of[2];
378
          4'h4: rMSR_C <= #1 wRES[2];
379
          4'h2: rMSR_C <= #1 opa_of[0];
380
          4'h1: rMSR_C <= #1 add_c;
381
          default: rMSR_C <= #1 rMSR_CC;
382
        endcase // case ({fMTS,fMOP,fSHIFT,fADDSUB})
383
        */
384 118 sybreon
     end
385
 
386
endmodule // aeMB2_intu
387
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.