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

Subversion Repositories edge

[/] [edge/] [trunk/] [HW/] [Verilog/] [controller.v] - Blame information for rev 2

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 heshamelma
//////////////////////////////////////////////////////////////////
2
//                                                              //
3
//  Instruction decoder at decode stage for Edge core           //
4
//                                                              //
5
//  This file is part of the Edge project                       //
6
//  http://www.opencores.org/project,edge                       //
7
//                                                              //
8
//  Description                                                 //
9
//  Instruction decoder receives MIPS instruction and emits the //
10
//  appropriate control signal for each unit in the pipeline.   //
11
//                                                              //
12
//  Author(s):                                                  //
13
//      - Hesham AL-Matary, heshamelmatary@gmail.com            //
14
//                                                              //
15
//////////////////////////////////////////////////////////////////
16
//                                                              //
17
// Copyright (C) 2014 Authors and OPENCORES.ORG                 //
18
//                                                              //
19
// This source file may be used and distributed without         //
20
// restriction provided that this copyright statement is not    //
21
// removed from the file and that any derivative work contains  //
22
// the original copyright notice and the associated disclaimer. //
23
//                                                              //
24
// This source file is free software; you can redistribute it   //
25
// and/or modify it under the terms of the GNU Lesser General   //
26
// Public License as published by the Free Software Foundation; //
27
// either version 2.1 of the License, or (at your option) any   //
28
// later version.                                               //
29
//                                                              //
30
// This source is distributed in the hope that it will be       //
31
// useful, but WITHOUT ANY WARRANTY; without even the implied   //
32
// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR      //
33
// PURPOSE.  See the GNU Lesser General Public License for more //
34
// details.                                                     //
35
//                                                              //
36
// You should have received a copy of the GNU Lesser General    //
37
// Public License along with this source; if not, download it   //
38
// from http://www.opencores.org/lgpl.shtml                     //
39
//                                                              //
40
//////////////////////////////////////////////////////////////////
41
 
42
/* OPCODE defines INST[31:26] */
43
`define RTYPE_OPCODE 6'b000000 // 0
44
 
45
/* Immediates */
46
`define ADDI_OPCODE   6'b001000 // 8
47
`define ADDIU_OPCODE  6'b001001 // 9
48
`define SLTI_OPCODE   6'b001010 // 10
49
`define SLTIU_OPCODE  6'b001011 // 11
50
`define ANDI_OPCODE   6'b001100 // 12
51
`define ORI_OPCODE    6'b001101 // 13
52
`define XORI_OPCODE   6'b001110 // 14
53
 
54
/* loads */
55
`define LUI_OPCODE  6'b001111 // 15
56
`define CP0_OPCODE  6'b010000 // 16 mfc0, mtc0
57
`define MUL_OPCODE  6'b011100 // 28
58
`define LB_OPCODE   6'b100000 // 32
59
`define LH_OPCODE   6'b100001 // 33
60
`define LW_OPCODE   6'b100011 // 35
61
`define LBU_OPCODE  6'b100100 // 36
62
`define LHU_OPCODE  6'b100101 // 37
63
 
64
`define SB_OPCODE   6'b101000 // 40
65
`define SH_OPCODE   6'b101001 // 41
66
`define SW_OPCODE   6'b101011 // 43
67
 
68
`define BLTZ_OPCODE 6'b000001 // 1
69
`define BGEZ_OPCODE 6'b000001 // 1
70
`define JMP_OPCODE  6'b000010 // 2
71
`define JAL_OPCODE  6'b000011 // 3
72
`define BEQ_OPCODE  6'b000100 // 4
73
`define BNE_OPCODE  6'b000101 // 5
74
`define BLEZ_OPCODE 6'b000110 // 6
75
`define BGTZ_OPCODE 6'b000111 // 7
76
 
77
/* FUNCT defines INST[5:0] */
78
`define SLL_FUNCT   6'b000000 // 0 
79
`define SRL_FUNCT   6'b000010 // 2
80
`define SRA_FUNCT   6'b000011 // 3
81
`define SLLV_FUNCT  6'b000100 // 4
82
`define SRLV_FUNCT  6'b000110 // 6
83
`define SRAV_FUNCT  6'b000111 // 7
84
`define JR_FUNCT    6'b001000 // 8
85
`define JALR_FUNCT  6'b001001 // 9
86
`define SYSCALL_FUNCT 6'b001100 // 12
87
`define BREAK_FUNCT 6'b001101 // 13
88
`define MFHI_FUNCT  6'b010000 // 16
89
`define MTHI_FUNCT  6'b010001 // 17
90
`define MFLO_FUNCT  6'b010010 // 18
91
`define MTLO_FUNCT  6'b010011 // 19
92
`define MULT_FUNCT  6'b011000 // 24
93
`define MULTU_FUNCT 6'b011001 // 25
94
`define DIV_FUNCT   6'b011010 // 26
95
`define DIVU_FUNCT  6'b011011 // 27
96
`define ADD_FUNCT   6'b100000 // 32
97
`define ADDU_FUNCT  6'b100001 // 33
98
`define SUB_FUNCT   6'b100010 // 34
99
`define SUBU_FUNCT  6'b100011 // 35
100
`define AND_FUNCT   6'b100100 // 36
101
`define OR_FUNCT    6'b100101 // 37
102
`define XOR_FUNCT   6'b100110 // 38
103
`define SLT_FUNCT   6'b101010 // 42
104
`define SLTU_FUNCT  6'b101011 // 43
105
 
106
/* Memory Reference sizes */
107
`define BYTE_REF  2'b01
108
`define HW_REF    2'b10
109
`define W_REF     2'b11
110
 
111
module controller
112
(
113
  input[5:0] opcode,
114
  input[5:0] func,
115
  input[31:0] Instruction,
116
 
117
  output reg RegWrite,
118
  output reg[1:0] WBResultSelect,
119
  output reg MemWrite,
120
  output reg Branch,
121
  output reg Jump,
122
  output reg JumpR, /* Jump to address in Register */
123
  output [3:0] ALUControl,
124
  output reg ALUSrcB,
125
  output reg RegDst,
126
  output reg UpperImm_out,
127
  output reg [2:0] BHW, /* byte or halfword or word ? */
128
  output reg ImmSorU_out, /* Signed or Unsgined Immediate ? */
129
  output reg ALUComp_out, /*  One complement of ALU output (useful for inst
130
like nor */
131
  output ShiftAmtVar_out, /* Whether shift amount comes from instruction
132
or register */
133
  output [1:0] Shift_type_out, /* Choose shifter type from [Right | LEFT]
134
[Logical | Arithmetic] */
135
  output reg Shifter_or_ALU_out, /* Choose Result between ALUoutput and
136
Shifter output */
137
  output reg[1:0] MulDivRF, /* Choose input to hi/lo registers from Mul, Div,
138
or RF */
139
  output reg hiEN, /* Enable(load) hi register */
140
  output reg loEN,       /* Enable(load) lo register */
141
  output reg link, /* if link == 1 > Put pc+4 into ra */
142
  output reg undefinedEx, /* Undefined instruction Excption */
143
  output reg syscallEx, /* System call excpetion */
144
  output reg breakEx, /* Break expetion */
145
  output reg mfc0, /* get value from coprocessor 0 */
146
  output reg mtc0, /* Write enable Co-processor 0 registers */
147
  output reg[1:0] MemRefSize /* Zero of no mem ref, 1 for byte, 2 for hw, 3
148
for w)*/
149
);
150
 
151
reg[3:0] ALUop;
152
 
153
always @*
154
begin
155
  RegWrite = 1'b0;
156
  WBResultSelect <= 2'b00;
157
  MemWrite <= 1'b0;
158
  Branch <= 1'b0;
159
  Jump <= 1'b0;
160
  JumpR <= 1'b0;
161
  ALUSrcB <= 1'b0;
162
  RegDst <= 1'b0;
163
  ALUop <= 4'b0000;
164
  UpperImm_out <= 1'b0;
165
  BHW <= 3'b000;
166
  ImmSorU_out <= 0;
167
  ALUComp_out <= 0;
168
  Shifter_or_ALU_out <= 0;
169
  MulDivRF <= 2'b11; /* Zero hi, lo registers */
170
  hiEN <= 1'b0;
171
  loEN <= 1'b0;
172
  link <= 1'b0;
173
  undefinedEx <= 1'b0;
174
  syscallEx <= 1'b0;
175
  breakEx <= 1'b0;
176
  mfc0 <= 1'b0;
177
  mtc0 <= 1'b0;
178
  MemRefSize = 2'b00; /* No memory reference */
179
 
180
  /* Every new instruction opcode should be added here */
181
 
182
  case (opcode)
183
    `RTYPE_OPCODE: /* R-Type */
184
      begin
185
        RegWrite = 1'b1;
186
        ALUop <= 4'b0010;
187
        RegDst <= 1'b1;
188
 
189
        if (func == `SLL_FUNCT || func == `SRL_FUNCT ||
190
          func == `SRA_FUNCT || func == `SLLV_FUNCT||
191
          func == `SRLV_FUNCT|| func == `SRAV_FUNCT) /* Shift Operation */
192
          Shifter_or_ALU_out <= 1;
193
        if (func == `JR_FUNCT)
194
        begin
195
          JumpR <= 1'b1;
196
          RegWrite = 1'b0;
197
          ALUop <= 4'b0000;
198
        end
199
        if (func == `JALR_FUNCT)
200
        begin
201
          JumpR <= 1'b1;
202
          RegWrite = 1'b1;
203
          ALUop <= 4'b0000;
204
          link <= 1'b1;
205
        end
206
      case(func)
207
        `MTHI_FUNCT :
208
        begin
209
          RegWrite = 1'b0;
210
          hiEN <= 1'b1;
211
          MulDivRF <= 2'b10;
212
        end
213
        `MTLO_FUNCT :
214
        begin
215
          RegWrite = 1'b0;
216
          loEN <= 1'b1;
217
          MulDivRF <= 2'b10;
218
        end
219
        `MULT_FUNCT :
220
        begin
221
          RegWrite = 1'b0;
222
          hiEN <= 1'b1;
223
          loEN <= 1'b1;
224
          MulDivRF <= 2'b00;
225
        end
226
        `MULTU_FUNCT :
227
        begin
228
            RegWrite = 1'b0;
229
          hiEN <= 1'b1;
230
          loEN <= 1'b1;
231
          MulDivRF <= 2'b00;
232
        end
233
        `DIV_FUNCT :
234
        begin
235
            RegWrite = 1'b0;
236
          hiEN <= 1'b1;
237
          loEN <= 1'b1;
238
          MulDivRF <= 2'b01;
239
       end
240
          `DIVU_FUNCT :
241
          begin
242
            RegWrite = 1'b0;
243
            hiEN <= 1'b1;
244
            loEN <= 1'b1;
245
            MulDivRF <= 2'b01;
246
          end
247
          `MFLO_FUNCT:
248
            WBResultSelect <= 2'b10;
249
          `MFHI_FUNCT:
250
            WBResultSelect <= 2'b11;
251
          `SYSCALL_FUNCT:
252
            syscallEx <= 1'b1;
253
          `BREAK_FUNCT:
254
            breakEx <= 1'b1;
255
      endcase
256
 
257
        end
258
      `ADDI_OPCODE:
259
      begin
260
        RegWrite = 1'b1;
261
        ALUSrcB <= 1'b1;
262
      end
263
      `ADDIU_OPCODE:
264
      begin
265
        RegWrite = 1'b1;
266
        ALUSrcB <= 1'b1;
267
      end
268
      `SLTI_OPCODE:
269
      begin
270
        RegWrite = 1'b1;
271
        ALUop <= 4'b100;
272
        ALUSrcB <= 1'b1;
273
      end
274
      `SLTIU_OPCODE:
275
      begin
276
        RegWrite = 1'b1;
277
        ALUop <= 4'b0010;
278
        ALUSrcB <= 1'b1;
279
        ImmSorU_out <= 1'b1;
280
      end
281
      `ANDI_OPCODE:
282
      begin
283
        RegWrite = 1'b1;
284
        ALUop <= 4'b0101;
285
        ALUSrcB <= 1'b1;
286
      end
287
      `ORI_OPCODE:
288
      begin
289
        RegWrite = 1'b1;
290
        ALUop <= 4'b0110;
291
        ALUSrcB <= 1'b1;
292
      end
293
      `XORI_OPCODE:
294
      begin
295
        RegWrite = 1'b1;
296
        ALUop <= 4'b0111;
297
        ALUSrcB <= 1'b1;
298
      end
299
      `MUL_OPCODE:
300
      begin
301
        RegWrite = 1'b1;
302
        ALUop <= 4'b1000;
303
        RegDst <= 1'b1;
304
      end
305
      `LUI_OPCODE: /* Load upper immediate */
306
      begin
307
        UpperImm_out <= 1'b1;
308
        RegWrite = 1'b1;
309
        ALUSrcB <= 1'b1;
310
      end
311
      `LB_OPCODE: /* load signed byte */
312
      begin
313
        RegWrite = 1'b1;
314
        WBResultSelect <= 2'b01;
315
        ALUSrcB <= 1'b1;
316
        BHW <= 3'b001;
317
        MemRefSize = 2'b01;
318
      end
319
      `LH_OPCODE: /* load signed halfword */
320
      begin
321
        RegWrite = 1'b1;
322
        WBResultSelect <= 2'b01;
323
        ALUSrcB <= 1'b1;
324
        BHW <= 3'b010;
325
        MemRefSize = 2'b10;
326
      end
327
      `LW_OPCODE: /* load word */
328
      begin
329
        RegWrite = 1'b1;
330
        WBResultSelect <= 2'b01;
331
        ALUSrcB <= 1'b1;
332
        MemRefSize = 2'b11;
333
      end
334
      `LBU_OPCODE: /* load unsigned byte */
335
      begin
336
        RegWrite = 1'b1;
337
        WBResultSelect <= 2'b01;
338
        ALUSrcB <= 1'b1;
339
        BHW <= 3'b011;
340
        MemRefSize = 2'b01;
341
      end
342
      `LHU_OPCODE: /* load unsigned byte */
343
      begin
344
        RegWrite = 1'b1;
345
        WBResultSelect <= 2'b01;
346
        ALUSrcB <= 1'b1;
347
        BHW <= 3'b100;
348
        MemRefSize = 2'b10;
349
      end
350
      `SB_OPCODE:
351
      begin
352
        MemWrite <= 1'b1;
353
        ALUSrcB <= 1'b1;
354
        MemRefSize = 2'b01;
355
      end
356
      `SH_OPCODE:
357
      begin
358
        MemWrite <= 1'b1;
359
        ALUSrcB <= 1'b1;
360
        MemRefSize = 2'b10;
361
      end
362
      `SW_OPCODE: /* store */
363
      begin
364
        MemWrite <= 1'b1;
365
        ALUSrcB <= 1'b1;
366
        MemRefSize = 2'b11;
367
      end
368
      `BEQ_OPCODE,
369
      `BNE_OPCODE: /* branch if equale */
370
      begin
371
        Branch <= 1'b1;
372
        ALUop <= 4'b0001;
373
      end
374
      `BLTZ_OPCODE, `BGEZ_OPCODE, `BLEZ_OPCODE, `BGTZ_OPCODE:
375
      begin
376
        Branch <= 1'b1;
377
      end
378
      `JMP_OPCODE:
379
        Jump <= 1'b1;
380
      `JAL_OPCODE:
381
      begin
382
        Jump <= 1'b1;
383
        link <= 1'b1;
384
        RegWrite = 1'b1;
385
      end
386
      `CP0_OPCODE:
387
      begin
388
        if(Instruction[25:21] == 5'd0) //mfc0
389
        begin
390
          mfc0 <= 1'b1;
391
          RegWrite = 1'b1;
392
          RegDst <= 1'b0;
393
        end
394
        else if(Instruction[25:21] == 5'd4) //mtc0
395
        begin
396
          mtc0 <= 1'b1;
397
        end
398
    end
399
      default: /* Undefined instruction exception */
400
      begin
401
        undefinedEx <= 1'b1;
402
      end
403
  endcase
404
end
405
 
406
alu_decoder dec
407
(
408
.ALUop(ALUop),
409
.Funct(func),
410
.ALUControl(ALUControl)
411
);
412
 
413
shifter_decoder shift_dec
414
(
415
.Funct(func),
416
.Shift_type(Shift_type_out),
417
.ShiftAmtVar_out(ShiftAmtVar_out)
418
);
419
 
420
endmodule

powered by: WebSVN 2.1.0

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