计算机组成原理实验报告
操作:取指令、rt←rs < ext.imm16(sign_extend) 、PC←NPC(PC+4)操作:取指令、rt←rs < ext.imm16(sign_extend) 、PC←NPC(PC+4)操作:取指令、rt←rs+imm16(sign_extend) 、PC←NPC(PC+4)操作:取指令、rt←rs+imm16(sign_extend) 、PC←NPC(PC+4)操作:取指令、r
计算机组成原理实验报告
一、 实验内容
在本次实验中,将使用Verilog HDL实现31条MIPS指令的CPU的设计、前仿真、后仿真和下板调试运行。
二、 数据通路
(一)单独数据通路:
1 ADD
格式:ADD rd, rs, rt
操作:取指令,rd←rs+rt, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


2 ADDU
格式:ADDU rd, rs, rt
操作:取指令,rd←rs+rt, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


3 SUB
格式:SUB rd, rs, rt
操作:取指令,rd←rs-rt, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


4 SUBU
格式:SUBU rd, rs, rt
操作:取指令,rd←rs-rt, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


5 AND
格式:AND rd, rs, rt
操作:取指令,rd←rs & rt, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


6 OR
格式:OR rd, rs, rt
操作:取指令,rd←rs | rt, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


7 XOR
格式:XOR rd, rs, rt
操作:取指令,rd←rs ^ rt, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


8 NOR
格式:NOR rd, rs, rt
操作:取指令,rd←~(rs | rt), PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


9 SLT
格式:SLT rd, rs, rt
操作:取指令,rd← rs < rt , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


10 SLTU
格式:SLTU rd, rs, rt
操作:取指令,rd← rs < rt , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


11 SLL
格式:SLL rd, rt, sa
操作:取指令, rd←rt << sa , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU, Ext5
输入输出关系:


12 SRL
格式:SRL rd, rt, sa
操作:取指令, rd←rt >> sa (logical) , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU, Ext5
输入输出关系:


13 SRA
格式:SRA rd, rt, sa
操作:取指令, rd←rt >> sa (arithmetic) , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU, Ext5
输入输出关系:


14 SLLV
格式:SLLV rd, rt, rs,
操作:取指令, rd←rt << rs , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


15 SRLV
格式:SRLV rd, rt,rs
操作:取指令, rd←rt >> rs (logical) , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


16 SRAV
格式:SRAV rd, rt,rs
操作:取指令, rd←rt >> rs (arithmetic) , PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile, ALU
输入输出关系:


17 JR
格式:JR rs
操作:取指令, PC←rs, PC←NPC(PC+4)
所需部件:PC, NPC, IMEM, Regfile
输入输出关系:


18 ADDI
格式:ADDI rt, rs, imm16
操作:取指令、rt←rs+imm16(sign_extend) 、PC←NPC(PC+4)
所需部件::PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:



19 ADDIU
格式:ADDIU rt, rs, imm16
操作:取指令、rt←rs+imm16(sign_extend) 、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:


20 ANDI
格式:ANDI rt, rs, imm16
操作:取指令、rt←rs&imm16(zero_extend) 、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:


21 ORI
格式:ORI rt, rs, imm16
操作:取指令、rt←rs|imm16(zero_extend) 、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:


22 XORI
格式:XORI rt, rs, imm16
操作:取指令、rt←rs^imm16(zero_extend) 、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:


23 LW
格式:LW rt, offset(base)
操作:取指令、rt←memory[rs + offset]、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、ALU、Ext16、DMEM
输入输出关系:


24 SW
格式:SW rt, offset(base)
操作:取指令、memory[base + offset]←rt、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、ALU、Ext16、DMEM
输入输出关系:


25 BEQ
格式:BEQ rs, rt, offset
操作: if (rs=rt)PC←NPC + Sign_ext(offset||02)
else PC← NPC(PC+4)
所需部件:PC、NPC、IMEM、Regfile、ALU、Ext18、ADD
输入输出关系:


26 BNE
格式:BNE rs, rt, offset
操作:if (rs≠rt)PC←NPC + Sign_ext(offset||02)
else PC← NPC(PC+4)
所需部件:PC、NPC、IMEM、Regfile、ALU、Ext18、ADD
输入输出关系:


27 SLTI
格式:SLTI rt, rs, imm16
操作:取指令、rt←rs < ext.imm16(sign_extend) 、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:


28 SLTIU
格式:SLTIU rt, rs, imm16
操作:取指令、rt←rs < ext.imm16(sign_extend) 、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:


29 LUI
格式:LUI rt, imm16
操作:取指令、rt←imm16||016 、PC←NPC(PC+4)
所需部件:PC、NPC、IMEM、Rregfile、ALU、Ext16
输入输出关系:


30 J
格式:J target
操作:取指令、PC ← PC31-28||instr_index||02 , PC←NPC(PC+4)
所需部件:PC、NPC、IMEM
输入输出关系:


31 JAL
格式:JAL target
操作:取指令、 R[31] ← PC + 8,PC ← PC31-28||instr_index||02 , PC←PC+4
所需部件::PC、NPC、IMEM
输入输出关系:


(二)整个数据通路

(三)部件表:
31条指令CPU所需部件及数据通路图


三、 模块建模
3.1 顶层模块sccomp_dataflow,调用cpu,imem和dram
module sccomp_dataflow(
input clk_in,
input reset,
output [31:0] inst,
output [31:0] pc
);
wire [31:0] imm;
wire [31:0] Rt;
wire [31:0] alu_r;
wire cs;
wire dm_w;
wire dm_r;
wire [31:0] ram_out;
assign inst=imm;
imem imem(((pc- 32'h00400000)/4),imm);
//imem im(pc,inst)
//IMEM imem(1,((pc- 32'h00400000)/4),imm);
cpu sccpu(clk_in,reset,imm,ram_out, //input
Rt,alu_r,pc,cs,dm_w,dm_r); //output
DMEM dram(
.clk(clk_in),
.CS(cs), //enable control signal
.DM_W(dm_w), //write
.DM_R(dm_r), //read
.Addr((alu_r[9:0]-32'h10010000)/4),
.Data_in(Rt),
.Data_out(ram_out)
);
endmodule
3.2 cpu模块 发送控制信号
module cpu(
input clk_in,
input reset,
input [31:0]imem,//
input [31:0] ram_out,
output [31:0] Rt,
output [31:0] alu_r,
output [31:0] pc,
output cs, //dmem control signal
output dm_w, //dmem write
output dm_r//dmem read
);
wire [31:0]npc;
wire M3,M3_2,M4,M4_2, M2,M5,M1,M1_2,M6,M7; //mux2
wire ALUC3,ALUC2,ALUC1,ALUC0;
wire RF_W; //regfiles write
wire RL_CLK; //regfiles clk
wire [3:0]ALUC;//alu control
wire [31:0] PC;
wire [31:0] mux_out_1;
wire [31:0] mux_out_1_2;
wire [31:0] mux_out_2;
wire [31:0] mux_out_3;
wire [31:0] mux_out_3_2;
wire [31:0] mux_in_4;
wire [31:0] mux_out_4;
wire [31:0] mux_out_4_2;
wire [31:0] mux_out_5;
wire [31:0] Rs; //Rs
wire [31:0] ext18_sign;
wire [4:0] rdc;
wire [4:0] rsc;
wire [4:0] rtc;
wire [31:0] ext16;
wire [31:0] ext16_sign;
wire ext16_sin_judge;
wire zero;
wire carry;
wire negative;
wire overflow;
assign pc = PC;
//assign RDC_T = rdc;
assign mux_out_2_T=mux_out_2;
wire _add, _addu, _sub, _subu, _and, _or, _xor, _nor;
wire _slt, _sltu, _sll, _srl, _sra, _sllv, _srlv, _srav, _jr;
wire _addi, _addiu, _andi, _ori, _xori, _lw, _sw;
wire _beq, _bne, _slti, _sltiu, _lui, _j, _jal;
//1~17
assign _add = (imem[31:26]==6'b000000&&imem[5:0]==6'b100000)?1'b1:1'b0;
assign _addu = (imem[31:26]==6'b000000&&imem[5:0]==6'b100001)?1'b1:1'b0;
assign _sub = (imem[31:26]==6'b000000&&imem[5:0]==6'b100010)?1'b1:1'b0;
assign _subu = (imem[31:26]==6'b000000&&imem[5:0]==6'b100011)?1'b1:1'b0;
assign _and = (imem[31:26]==6'b000000&&imem[5:0]==6'b100100)?1'b1:1'b0;
assign _or = (imem[31:26]==6'b000000&&imem[5:0]==6'b100101)?1'b1:1'b0;
assign _xor = (imem[31:26]==6'b000000&&imem[5:0]==6'b100110)?1'b1:1'b0;
assign _nor = (imem[31:26]==6'b000000&&imem[5:0]==6'b100111)?1'b1:1'b0;
assign _slt = (imem[31:26]==6'b000000&&imem[5:0]==6'b101010)?1'b1:1'b0;
assign _sltu = (imem[31:26]==6'b000000&&imem[5:0]==6'b101011)?1'b1:1'b0;
assign _sll = (imem[31:26]==6'b000000&&imem[5:0]==6'b000000)?1'b1:1'b0;
assign _srl = (imem[31:26]==6'b000000&&imem[5:0]==6'b000010)?1'b1:1'b0;
assign _sra = (imem[31:26]==6'b000000&&imem[5:0]==6'b000011)?1'b1:1'b0;
assign _sllv = (imem[31:26]==6'b000000&&imem[5:0]==6'b000100)?1'b1:1'b0;
assign _srlv = (imem[31:26]==6'b000000&&imem[5:0]==6'b000110)?1'b1:1'b0;
assign _srav = (imem[31:26]==6'b000000&&imem[5:0]==6'b000111)?1'b1:1'b0;
assign _jr = (imem[31:26]==6'b000000&&imem[5:0]==6'b001000)?1'b1:1'b0;
//18~29
assign _addi = (imem[31:26]==6'b001000)?1'b1:1'b0;
assign _addiu = (imem[31:26]==6'b001001)?1'b1:1'b0;
assign _andi = (imem[31:26]==6'b001100)?1'b1:1'b0;
assign _ori = (imem[31:26]==6'b001101)?1'b1:1'b0;
assign _xori = (imem[31:26]==6'b001110)?1'b1:1'b0;
assign _lw = (imem[31:26]==6'b100011)?1'b1:1'b0;
assign _sw = (imem[31:26]==6'b101011)?1'b1:1'b0;
assign _beq = (imem[31:26]==6'b000100)?1'b1:1'b0;
assign _bne = (imem[31:26]==6'b000101)?1'b1:1'b0;
assign _slti = (imem[31:26]==6'b001010)?1'b1:1'b0;
assign _sltiu = (imem[31:26]==6'b001011)?1'b1:1'b0;
assign _lui = (imem[31:26]==6'b001111)?1'b1:1'b0;
//30 31
assign _j = (imem[31:26]==6'b000010)?1'b1:1'b0;
assign _jal = (imem[31:26]==6'b000011)?1'b1:1'b0;
wire exception;
wire [4:0] cause;
wire wdata;
assign wdata = Rt;
wire [31:0] rdata;
wire [31:0] status;
wire [31:0] exc_addr; //un
//Control signal expression
assign M3 = _sll || _srl || _sra ;
assign M3_2 = _jal ;
assign M4 = _addi || _addiu || _andi || _ori || _xori || _slti || _sltiu || _lui || _lw || _sw ;
assign M4_2 = _jal ;
assign M6 =_addi||_addiu||_andi||_ori||_xori|||_slti||_sltiu||_lui||_lw;//||_mfc0;
assign M7 =_jal;
assign ALUC[3] = _slt || _sltu ||_sllv || _srlv || _srav || _sll || _srl || _sra || _slti || _sltiu || _lui ;
assign ALUC[2] = _and || _or ||_xor || _nor || _sllv || _srlv || _srav || _sll || _srl || _sra || _andi || _ori || _xori ;
assign ALUC[1] = _add || _sub ||_xor || _nor || _slt || _sltu || _sllv || _sll || _addi || _xori || _slti || _sltiu ;
assign ALUC[0] = _sub || _subu ||_or || _nor || _slt || _srlv || _srl || _ori || _slti || _beq || _bne ;//||_teq;//cp0 teq
assign M2 = !_lw;
assign rdc = M6?imem[20:16]:(M7?5'd31:imem[15:11]);
assign RF_W= (!_sw)&&(!_beq)&&(!_bne)&&(!_j)&&(!_jr);
assign RL_CLK= ((!_sw)&&(!_beq)&&(!_bne)&&(!_j)&&(!_jal)&&(!_jr))&&clk_in;
assign M5 = (_beq&&zero) || (_bne&&(!zero)) ;
assign M1 = (!_j)&&(!_jal) ;
assign M1_2 = _jr ;
assign cs = _lw || _sw;
assign dm_r = _lw;
assign dm_w = _sw;
assign ext16_sin_judge = _addi || _addiu || _slti||_sltiu || _lw; //sign_ext
assign ext18_sign = {{14{imem[15]}},{imem[15:0],2'h0}};
assign npc = PC + 4;
assign ext16_sign = {{16{imem[15]}},imem[15:0]};//
assign ext16 = {16'h0,imem[15:0]};
assign mux_in_4 = ext16_sin_judge?ext16_sign:ext16;
assign rsc = imem[25:21];
assign rtc = imem[20:16];
assign mux_out_1=M1?mux_out_5:{PC[31:28],imem[25:0],2'b00}; //mux1
assign mux_out_1_2=M1_2?Rs:mux_out_1; //mux1_2
assign mux_out_2=M2?alu_r:ram_out; //mux2
assign mux_out_3=M3?{27'b0,imem[10:6]}:Rs;
assign mux_out_3_2=M3_2?PC:mux_out_3;
assign mux_out_4=M4?mux_in_4:Rt;
assign mux_out_4_2=M4_2?32'd4:mux_out_4;
assign mux_out_5=M5?ext18_sign+npc:npc;
pcreg PCreg(
.clk(clk_in),
.rst(reset),
.ena(1),
//.wena(1),
.data_in(mux_out_1_2),
.data_out(PC)
);
regfile cpu_ref(
.clk(clk_in),
.rst(reset),
.ena(1),
.we(RF_W),
.raddr1(rsc), //rsc
.raddr2(rtc),//rtc
.waddr(rdc), //rdc 5bits
.wdata(mux_out_2), //rd
.rdata1(Rs), //rs
.rdata2(Rt) //rt
);
ALU alu(
.a(mux_out_3_2),
.b(mux_out_4_2),
.aluc(ALUC),
.r(alu_r),
.zero(zero),
.carry(carry),
.negative(negative),
.overflow(overflow)
);
endmodule
3.3 dmem模块
module DMEM(
input clk,
input CS, //enable control signal
input DM_W, //write
input DM_R, //read
input [9:0] Addr,
input [31:0] Data_in,
output [31:0] Data_out
);
reg [31:0] num [0:31];
assign Data_out=CS? (DM_R? num[Addr]: 32'h00000000):32'bzzzz_zzzz_zzzz_zzzz_zzzz_zzzz_zzzz_zzzz;
always@(negedge clk or negedge CS)
begin
if(CS&&DM_W)num[Addr]<=Data_in;
end
endmodule
3.4 ALU负责完成各类计算
module ALU(
input [31:0] a, //OP1
input [31:0] b, //OP2
input [3:0] aluc, //controller
output [31:0] r, //result
output zero,
output carry,
output negative,
output overflow);
parameter Addu = 4'b0000; //r=a+b unsigned
parameter Add = 4'b0010; //r=a+b signed
parameter Subu = 4'b0001; //r=a-b unsigned
parameter Sub = 4'b0011; //r=a-b signed
parameter And = 4'b0100; //r=a&b
parameter Or = 4'b0101; //r=a|b
parameter Xor = 4'b0110; //r=a^b
parameter Nor = 4'b0111; //r=~(a|b)
parameter Lui1 = 4'b1000; //r={b[15:0],16'b0}
parameter Lui2 = 4'b1001; //r={b[15:0],16'b0}
parameter Slt = 4'b1011; //r=(a-b<0)?1:0 signed
parameter Sltu = 4'b1010; //r=(a-b<0)?1:0 unsigned
parameter Sra = 4'b1100; //r=b>>>a
parameter Sll = 4'b1110; //r=b<<a
parameter Srl = 4'b1101; //r=b>>a
parameter bits=31;
parameter ENABLE=1,DISABLE=0;
reg [32:0] result;
wire signed [31:0] sa=a,sb=b;
always@(*)begin
case(aluc)
Addu: begin
result=a+b;
end
Subu: begin
result=a-b;
end
Add: begin
result=sa+sb;
end
Sub: begin
result=sa-sb;
end
Sra: begin
if(a==0) {result[31:0],result[32]}={b,1'b0};
else {result[31:0],result[32]}=sb>>>(a-1);
end
Srl: begin
if(a==0) {result[31:0],result[32]}={b,1'b0};
else {result[31:0],result[32]}=b>>(a-1);
end
Sll: begin
result=b<<a;
end
And: begin
result=a&b;
end
Or: begin
result=a|b;
end
Xor: begin
result=a^b;
end
Nor: begin
result=~(a|b);
end
Sltu: begin
result=a<b?1:0;
end
Slt: begin
result=sa<sb?1:0;
end
Lui1,Lui2: result = {b[15:0], 16'b0};
default:
result=a+b;
endcase
end
assign r=result[31:0];
assign carry = result[32];
assign zero=(r==32'b0)?1:0;
assign negative=result[31];
assign overflow=result[32];
endmodule
3.5 regfiles模块
module regfile(
input clk,
input rst,
input ena,
input we,
input [4:0] raddr1,
input [4:0] raddr2,
input [4:0] waddr,
input [31:0] wdata,
output wire [31:0] rdata1,
output wire [31:0] rdata2
);
reg [31:0]array_reg[31:0];
assign rdata1 = ena?array_reg[raddr1]:32'bz;
assign rdata2 = ena?array_reg[raddr2]:32'bz;
always @(negedge clk or posedge rst)
//always @(posedge clk or posedge rst)
begin
if (rst) begin
array_reg[0] <= 32'h0;
array_reg[1] <= 32'h0;
array_reg[2] <= 32'h0;
array_reg[3] <= 32'h0;
array_reg[4] <= 32'h0;
array_reg[5] <= 32'h0;
array_reg[6] <= 32'h0;
array_reg[7] <= 32'h0;
array_reg[8] <= 32'h0;
array_reg[9] <= 32'h0;
array_reg[10] <= 32'h0;
array_reg[11] <= 32'h0;
array_reg[12] <= 32'h0;
array_reg[13] <= 32'h0;
array_reg[14] <= 32'h0;
array_reg[15] <= 32'h0;
array_reg[16] <= 32'h0;
array_reg[17] <= 32'h0;
array_reg[18] <= 32'h0;
array_reg[19] <= 32'h0;
array_reg[20] <= 32'h0;
array_reg[21] <= 32'h0;
array_reg[22] <= 32'h0;
array_reg[23] <= 32'h0;
array_reg[24] <= 32'h0;
array_reg[25] <= 32'h0;
array_reg[26] <= 32'h0;
array_reg[27] <= 32'h0;
array_reg[28] <= 32'h0;
array_reg[29] <= 32'h0;
array_reg[30] <= 32'h0;
array_reg[31] <= 32'h0;
end
else if ((ena&we)&& (waddr != 0))
array_reg[waddr] <= wdata;
end
endmodule
3.6 pc寄存器
module pcreg(clk,rst,ena,data_in,data_out);
input clk;
input rst;
input ena;
input [31:0]data_in;
output reg[31:0]data_out;
wire [31:0]data;
always@(*)
begin
if(ena==1)
data_out=data;
else
data_out=data_out;
end
Asynchronous_D_FF DFF0(.CLK(clk),.D(data_in[0]),.RST_n(rst),.Q1(data[0]));
Asynchronous_D_FF DFF1(.CLK(clk),.D(data_in[1]),.RST_n(rst),.Q1(data[1]));
Asynchronous_D_FF DFF2(.CLK(clk),.D(data_in[2]),.RST_n(rst),.Q1(data[2]));
Asynchronous_D_FF DFF3(.CLK(clk),.D(data_in[3]),.RST_n(rst),.Q1(data[3]));
Asynchronous_D_FF DFF4(.CLK(clk),.D(data_in[4]),.RST_n(rst),.Q1(data[4]));
Asynchronous_D_FF DFF5(.CLK(clk),.D(data_in[5]),.RST_n(rst),.Q1(data[5]));
Asynchronous_D_FF DFF6(.CLK(clk),.D(data_in[6]),.RST_n(rst),.Q1(data[6]));
Asynchronous_D_FF DFF7(.CLK(clk),.D(data_in[7]),.RST_n(rst),.Q1(data[7]));
Asynchronous_D_FF DFF8(.CLK(clk),.D(data_in[8]),.RST_n(rst),.Q1(data[8]));
Asynchronous_D_FF DFF9(.CLK(clk),.D(data_in[9]),.RST_n(rst),.Q1(data[9]));
Asynchronous_D_FF DFF10(.CLK(clk),.D(data_in[10]),.RST_n(rst),.Q1(data[10]));
Asynchronous_D_FF DFF11(.CLK(clk),.D(data_in[11]),.RST_n(rst),.Q1(data[11]));
Asynchronous_D_FF DFF12(.CLK(clk),.D(data_in[12]),.RST_n(rst),.Q1(data[12]));
Asynchronous_D_FF DFF13(.CLK(clk),.D(data_in[13]),.RST_n(rst),.Q1(data[13]));
Asynchronous_D_FF DFF14(.CLK(clk),.D(data_in[14]),.RST_n(rst),.Q1(data[14]));
Asynchronous_D_FF DFF15(.CLK(clk),.D(data_in[15]),.RST_n(rst),.Q1(data[15]));
Asynchronous_D_FF DFF16(.CLK(clk),.D(data_in[16]),.RST_n(rst),.Q1(data[16]));
Asynchronous_D_FF DFF17(.CLK(clk),.D(data_in[17]),.RST_n(rst),.Q1(data[17]));
Asynchronous_D_FF DFF18(.CLK(clk),.D(data_in[18]),.RST_n(rst),.Q1(data[18]));
Asynchronous_D_FF DFF19(.CLK(clk),.D(data_in[19]),.RST_n(rst),.Q1(data[19]));
Asynchronous_D_FF DFF20(.CLK(clk),.D(data_in[20]),.RST_n(rst),.Q1(data[20]));
Asynchronous_D_FF DFF21(.CLK(clk),.D(data_in[21]),.RST_n(rst),.Q1(data[21]));
Asynchronous_D_FF1 DFF22(.CLK(clk),.D(data_in[22]),.RST_n(rst),.Q1(data[22]));//reset==1
Asynchronous_D_FF DFF23(.CLK(clk),.D(data_in[23]),.RST_n(rst),.Q1(data[23]));
Asynchronous_D_FF DFF24(.CLK(clk),.D(data_in[24]),.RST_n(rst),.Q1(data[24]));
Asynchronous_D_FF DFF25(.CLK(clk),.D(data_in[25]),.RST_n(rst),.Q1(data[25]));
Asynchronous_D_FF DFF26(.CLK(clk),.D(data_in[26]),.RST_n(rst),.Q1(data[26]));
Asynchronous_D_FF DFF27(.CLK(clk),.D(data_in[27]),.RST_n(rst),.Q1(data[27]));
Asynchronous_D_FF DFF28(.CLK(clk),.D(data_in[28]),.RST_n(rst),.Q1(data[28]));
Asynchronous_D_FF DFF29(.CLK(clk),.D(data_in[29]),.RST_n(rst),.Q1(data[29]));
Asynchronous_D_FF DFF30(.CLK(clk),.D(data_in[30]),.RST_n(rst),.Q1(data[30]));
Asynchronous_D_FF DFF31(.CLK(clk),.D(data_in[31]),.RST_n(rst),.Q1(data[31]));
Endmodule
四、测试模块建模
cpu_tb
module CPU_tb();
reg clk;
reg rst;
wire [31:0] inst;
wire [31:0] pc;
//integer file_output;
//integer counter = 0;
sccomp_dataflow uut(.clk_in(clk),.reset(rst),.inst(inst),.pc(pc)//,.addr(addr)
);
initial
begin
// file_output = $fopen("E:/result.txt");
clk = 0;
rst = 1;
#5;
rst = 0;
end
always
begin
#10;
clk = ~clk;
//if (clk == 1'b0)
//begin
//if (counter == 1500)
//begin
//$fclose(file_output);
//end
//#4
// counter = counter + 1;
// if (counter > 600)
// begin
//$fdisplay(file_output,"pc:%h",pc-32'h00400000);
// $fdisplay(file_output,"pc:%h",pc);
// $fdisplay(file_output,"instr:%h",uut.inst);
//$fdisplay(file_output,"regfile0: %h",uut.sccpu.cpu_ref.array_reg[0]);
//$fdisplay(file_output,"regfile1: %h",uut.sccpu.cpu_ref.array_reg[1]);
//$fdisplay(file_output,"regfile2: %h",uut.sccpu.cpu_ref.array_reg[2]);
//$fdisplay(file_output,"regfile3: %h",uut.sccpu.cpu_ref.array_reg[3]);
//$fdisplay(file_output,"regfile4: %h",uut.sccpu.cpu_ref.array_reg[4]);
//$fdisplay(file_output,"regfile5: %h",uut.sccpu.cpu_ref.array_reg[5]);
//$fdisplay(file_output,"regfile6: %h",uut.sccpu.cpu_ref.array_reg[6]);
//$fdisplay(file_output,"regfile7: %h",uut.sccpu.cpu_ref.array_reg[7]);
//$fdisplay(file_output,"regfile8: %h",uut.sccpu.cpu_ref.array_reg[8]);
//$fdisplay(file_output,"regfile9: %h",uut.sccpu.cpu_ref.array_reg[9]);
//$fdisplay(file_output,"regfile10: %h",uut.sccpu.cpu_ref.array_reg[10]);
//$fdisplay(file_output,"regfile11: %h",uut.sccpu.cpu_ref.array_reg[11]);
//$fdisplay(file_output,"regfile12: %h",uut.sccpu.cpu_ref.array_reg[12]);
//$fdisplay(file_output,"regfile13: %h",uut.sccpu.cpu_ref.array_reg[13]);
//$fdisplay(file_output,"regfile14: %h",uut.sccpu.cpu_ref.array_reg[14]);
//$fdisplay(file_output,"regfile15: %h",uut.sccpu.cpu_ref.array_reg[15]);
//$fdisplay(file_output,"regfile16: %h",uut.sccpu.cpu_ref.array_reg[16]);
//$fdisplay(file_output,"regfile17: %h",uut.sccpu.cpu_ref.array_reg[17]);
//$fdisplay(file_output,"regfile18: %h",uut.sccpu.cpu_ref.array_reg[18]);
//$fdisplay(file_output,"regfile19: %h",uut.sccpu.cpu_ref.array_reg[19]);
//$fdisplay(file_output,"regfile20: %h",uut.sccpu.cpu_ref.array_reg[20]);
//$fdisplay(file_output,"regfile21: %h",uut.sccpu.cpu_ref.array_reg[21]);
//$fdisplay(file_output,"regfile22: %h",uut.sccpu.cpu_ref.array_reg[22]);
//$fdisplay(file_output,"regfile23: %h",uut.sccpu.cpu_ref.array_reg[23]);
//$fdisplay(file_output,"regfile24: %h",uut.sccpu.cpu_ref.array_reg[24]);
//$fdisplay(file_output,"regfile25: %h",uut.sccpu.cpu_ref.array_reg[25]);
//$fdisplay(file_output,"regfile26: %h",uut.sccpu.cpu_ref.array_reg[26]);
//$fdisplay(file_output,"regfile27: %h",uut.sccpu.cpu_ref.array_reg[27]);
//$fdisplay(file_output,"regfile28: %h",uut.sccpu.cpu_ref.array_reg[28]);
//$fdisplay(file_output,"regfile29: %h",uut.sccpu.cpu_ref.array_reg[29]);
//$fdisplay(file_output,"regfile30: %h",uut.sccpu.cpu_ref.array_reg[30]);
//$fdisplay(file_output,"regfile31: %h",uut.sccpu.cpu_ref.array_reg[31]);
// end
//end
end
endmodule
在测试时,只需要修改cpu_tb以及IMEM的相应文件路径即可
module IMEM(
input IM_R, //read
input [9:0] Addr,
output reg [31:0] data_out
);
reg [31:0] mem[1023:0];
initial begin
$readmemh("E:/31test/intrs/_4_jr.txt",mem);
end
always @ (*)
begin
if(!IM_R)
begin
data_out <= 32'hzzzz_zzzz;
end
else // read data
data_out <= mem[Addr];
end
endmodule
使用$readmemh初始化IMEM,读取相应的指令,进行测试
五、实验结果
5.1前仿真测试



5.2后仿真测试



5.3 下板测试
Inst:

PC:
魔乐社区(Modelers.cn) 是一个中立、公益的人工智能社区,提供人工智能工具、模型、数据的托管、展示与应用协同服务,为人工智能开发及爱好者搭建开放的学习交流平台。社区通过理事会方式运作,由全产业链共同建设、共同运营、共同享有,推动国产AI生态繁荣发展。
更多推荐


所有评论(0)