您好,欢迎来到尚车旅游网。
搜索
您的当前位置:首页计算机组成原理实验报告单周期cpu的设计与实现

计算机组成原理实验报告单周期cpu的设计与实现

来源:尚车旅游网
电子科技大学计算机科学与工程学院

标 准 实 验 报 告

(实验)课程名称: 计算机组成原理实验

电 子 科 技 大 学

电子科技大学教务处制表实 验 报 告

学生姓名: 郫县尼克杨 学 号: 2014 指导教师:陈虹 实验地点: 主楼A2-411 实验时间:12周-15周 一、 实验室名称:

主楼A2-411 二、 实验项目名称:

单周期CPU的设计与实现。 三、 实验学时:

8学时 四、 实验原理:

(一) 概述

单周期(Single Cycle)CPU是指CPU从取出1条指令到执行完该指令只需1个时钟

1个时钟周期

Clock

指令0 指令1 指令2 指令4 指令5 周期。

一条指令的执行过程包括:取指令→分析指令→取操作数→执行指令→保存结果。对于单周期CPU来说,这些执行步骤均在一个时钟周期内完成。

(二) 单周期cpu总体电路

本实验所设计的单周期CPU的总体电路结构如下。

(三) MIPS指令格式化

MIPS指令系统结构有MIPS-32和MIPS-两种。本实验的MIPS指令选用MIPS-32。以下所说的MIPS指令均指MIPS-32。

MIPS的指令格式为32位。下图给出MIPS指令的3种格式。

31 R型指令

31 I型指令

31 J型指令

26 221 216 15 11 16 5 0 op rs rt rd sa func 26 221 216 15 op rs rt 26 2op 0 immediate 0 address

本实验只选取了9条典型的MIPS指令来描述CPU逻辑电路的设计方法。下图列出了本实验的所涉及到的9条MIPS指令。 五、 实验目的

1、掌握单周期CPU的工作原理、实现方法及其组成部件的原理和设计方法,如控制器、

运算器等。?

2、认识和掌握指令与CPU的关系、指令的执行过程。?

3、熟练使用硬件描述语言Verilog、EDA工具软件进行软件设计与仿真,以培养学生的分析和设计CPU的能力。 六、 实验内容

(一)拟定本实验的指令系统,指令应包含R型指令、I型指令和J型指令,指令数为9条。

(二)CPU各功能模块的设计与实现。

(三)对设计的各个模块的仿真测试。

(四)整个CPU的封装与测试。 七、 实验器材(设备、元器件):

(一)安装了Xilinx ISE Design Suite 13.4的PC机一台

(二)FPGA开发板:Anvyl Spartan6/XC6SLX45

(三)计算机与FPGA开发板通过JTAG(Joint Test Action Group)接口连接,其连接方式如图所示。 八、 实验步骤

一个CPU主要由ALU(运算器)、控制器、寄存器堆、取指部件及其它基本功能部件等构成。?

在本实验中基本功能部件主要有:32位2选1多路选择器、5位2选1多路选择器、32位寄存器堆、ALU等。

(一)新建工程(New Project)

启动ISE Design Suite 13.4软件,然后选择菜单File→New Project,弹出New Project Wizard对话框,在对话框中输入工程名CPU,并指定工作路径D:\\Single_Cycle_CPU。

(二)基本功能器件的设计与实现

(1)多路选择器的设计与实现

a.5位2选1多路选择器(MUX5_2_1)的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:MUX5_2_1,然后输入其实现代码:

MODULE MUX5_2_1(

INPUT [4:0] A,

INPUT [4:0] B,

INPUT SEL,

OUTPUT [4:0] O

);

ASSIGN O = SEL ? B : A;

ENDMODULE

在ISE集成开发环境中,对模块MUX5_2_1进行综合(Synthesize),综合结果如图所示:

在ISE集成开发环境中,对模块MUX5_2_1进行仿真(Simulation)。输入如下测式代码:

MODULE MUX5_2_1_T;

// INPUTS REG [4:0] A; REG [4:0] B; REG SEL; // OUTPUTS WIRE [4:0] C;

// INSTANTIATE THE UNIT UNDER TEST (UUT) MUX5_2_1 UUT (

.A(A), .B(B), .SEL(SEL),

);

.C(C)

INITIAL BEGIN

// INITIALIZE INPUTS A = 0; B = 0;

SEL = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

A = 5'B10100;

B = 0;

SEL = 1;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

A = 1;

B = 5'B10000;

SEL = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

A = 5'B00000;

B = 5'B11000;

SEL = 1;

// ADD STIMULUS HERE

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

b.32位2选1多路选择器的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:MUX32_2_1,然后输入其实现代码:

MODULE MUX32_2_1(

INPUT [31:0]A ,

INPUT [31:0]B,

INPUT SEL,

OUTPUT [31:0] O

);

ASSIGN O= SEL?B:A;

ENDMODULE

在ISE集成开发环境中,对模块MUX32_2_1进行综合(Synthesize),综合结果如图

所示:

在ISE集成开发环境中,对模块MUX32_2_1进行仿真(Simulation)。首先输入如下测式代码:

MODULE MUX32_2_1_T;

// INPUTS

REG [31:0] A;

REG [31:0] B;

REG SEL;

// OUTPUTS

WIRE [31:0] O;

// INSTANTIATE THE UNIT UNDER TEST (UUT) MUX32_2_1 UUT (

.A(A), .B(B), .SEL(SEL), .O(O)

);

INITIAL BEGIN

A=0; B=0;

SEL=0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

A=32'H00000001; B=32'H00000000;

SEL=1;

#100;

A=32'H00000101; B=32'H00000010;

SEL =0;

// ADD STIMULUS HERE

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

(2)符号扩展(Sign_Extender)的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:Sign_Extender,然后输入其实现代码:

MODULE SIGN_EXTENDER(

INPUT [15:0] D,

OUTPUT [31:0] O

);

ASSIGN O = (D[15:15] == 1'B0) ? {16'B0, D[15:0]} : {16'B1, D[15:0]};

ENDMODULE

在ISE集成开发环境中,对模块Sign_Extender进行综合(Synthesize),综合结果如图所示。

在ISE集成开发环境中,对模块MUX32_2_1进行仿真(Simulation)。首先输入如下测式代码:

MODULE SIGN_EXTENDER_T;

// INPUTS

REG [15:0] D;

// OUTPUTS

WIRE [31:0] O;

// INSTANTIATE THE UNIT UNDER TEST (UUT) SIGN_EXTENDER UUT (

.D(D), .O(O)

);

INITIAL BEGIN

// INITIALIZE INPUTS

D = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

// ADD STIMULUS HERE

D = 16'H0011;

#100;

D = 16'H1011;

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

(3)32位寄存器堆(RegFile)的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:RegFile,然后输入其实现代码:

MODULE REGFILE(

INPUT [4:0] RN1, RN2, WN,

INPUT WRITE,

INPUT [31:0] WD,

OUTPUT [31:0] A, B,

INPUT CLOCK

);

REG [31:0] REGISTER[1:31];

ASSIGN A = (RN1 == 0) ? 0 : REGISTER[RN1];

ASSIGN B = (RN2 == 0) ? 0 : REGISTER[RN2];

ALWAYS @ (POSEDGE CLOCK) BEGIN

IF (WRITE && WN != 0)

REGISTER[WN] <= WD;

END

ENDMODULE

在ISE集成开发环境中,对模块RegFile进行综合(Synthesize),综合结果如图所示。

在ISE集成开发环境中,对模块RegFile进行仿真(Simulation)。输入如下测式代码:

MODULE REGFILE_T;

// INPUTS

REG [4:0] RN1;

REG [4:0] RN2;

REG [4:0] WN;

REG WRITE;

REG [31:0] WD;

REG CLOCK;

// OUTPUTS

WIRE [31:0] A;

WIRE [31:0] B;

// INSTANTIATE THE UNIT UNDER TEST (UUT) REGFILE UUT (

.RN1(RN1), .RN2(RN2),

.WN(WN), .WRITE(WRITE), .WD(WD), .A(A), .B(B), .CLOCK(CLOCK)

);

INITIAL BEGIN

// INITIALIZE INPUTS RN1 = 0; RN2 = 0; WN = 0; WRITE = 0; WD = 0; CLOCK = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH

#100;

RN1 = 5'B00001;

RN2 = 5'B00001; WN = 5'B00001; WRITE = 1; WD = 0; CLOCK = 0; #100; CLOCK = 1; #50;

WD = 32'HBBBBBBBB; #50; CLOCK = 0; #100; CLOCK = 1; #100

CLOCK = 0; // ADD STIMULUS HERE

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

(4)运算器(ALU)设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:ALU,然后输入其实现代码:

MODULE ALU(

INPUT [31:0] A, B,

INPUT [2:0] ALU_OPERATION,

OUTPUT [31:0] RESULT,

OUTPUT ZERO

);

ASSIGN RESULT = (ALU_OPERATION == 3'B000) ? A + B :

(ALU_OPERATION == 3'B100) ? A - B :

(ALU_OPERATION == 3'B001) ? A & B :

(ALU_OPERATION == 3'B101) ? A | B :

(ALU_OPERATION == 3'B010) ? A ^ B :

(ALU_OPERATION == 3'B110) ? {B[15:0], 16'H0} :

32'HXXXXXXXX;

ASSIGN ZERO = ~|RESULT;

ENDMODULE

在ISE集成开发环境中,对模块ALU进行综合(Synthesize),综合结果如图所示:

在ISE集成开发环境中,对模块ALU进行仿真(Simulation)。输入如下测式代码:

MODULE ALU_TB;

// INPUTS

REG [31:0] A;

REG [31:0] B;

REG [2:0] ALU_OPERATION;

// OUTPUTS

WIRE [31:0] RESULT;

WIRE ZERO;

// INSTANTIATE THE UNIT UNDER TEST (UUT) ALU UUT (

.A(A), .B(B),

.ALU_OPERATION(ALU_OPERATION), .RESULT(RESULT), .ZERO(ZERO)

);

INITIAL BEGIN

// INITIALIZE INPUTS A = 0; B = 0;

ALU_OPERATION = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

A = 1;

B = 1;

ALU_OPERATION = 0; // ADD STIMULUS HERE #100 A = 2; B = 2;

ALU_OPERATION = 4; #100 A = 1; B = 1;

ALU_OPERATION = 1; #100 A = 1; B = 1;

ALU_OPERATION = 5; #100

A = 1; B = 1;

ALU_OPERATION = 2;

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

(5)控制器(Controller)的设计与实现

为了简化设计,控制器由控制单元Control和控制单元ALUop组成,控制器结构如下所示。

a. Control的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:Control,然后输入其实现代码:

MODULE CONTROL(

INPUT [5:0] OP,

OUTPUT REGDST,

OUTPUT REGWRITE,

OUTPUT ALUSRC,

OUTPUT MEMWRITE,

OUTPUT MEMREAD,

OUTPUT MEMTOREG,

OUTPUT BRANCH,

OUTPUT [1:0] ALUCTR

);

WIRE I_RT=~|OP;

WIRE I_LW=OP[5] & ~OP[3];

WIRE I_SW=OP[5] & OP[3];

WIRE I_BEQ =OP[2] & ~OP[1];

WIRE I_LUI=OP[3] & OP[2];

ASSIGN REGDST = I_RT;

ASSIGN REGWRITE=I_RT|I_LW|I_LUI;

ASSIGN ALUSRC =I_LW|I_SW |I_LUI;

ASSIGN MEMWRITE =I_SW;

ASSIGN MEMREAD=I_LW;

ASSIGN MEMTOREG= I_LW;

ASSIGN BRANCH=I_BEQ;

ASSIGN ALUCTR[1]= I_RT|I_LUI;

ASSIGN ALUCTR[0]=I_BEQ|I_LUI;

ENDMODULE

在ISE集成开发环境中,对模块Control进行综合(Synthesize), 综合结果如图:

在ISE集成开发环境中,对模块Control进行仿真(Simulation)。首先输入如下测式代码:

MODULE CONTROL_TB;

// INPUTS REG [5:0] OP; // OUTPUTS WIRE REGDST; WIRE REGWRITE; WIRE ALUSRC;

WIRE MEMWRITE; WIRE MEMREAD; WIRE MEMTOREG; WIRE BRANCH; WIRE [1:0] ALUCTR;

// INSTANTIATE THE UNIT UNDER TEST (UUT) CONTROL UUT (

.OP(OP), .REGDST(REGDST), .REGWRITE(REGWRITE), .ALUSRC(ALUSRC), .MEMWRITE(MEMWRITE), .MEMREAD(MEMREAD), .MEMTOREG(MEMTOREG), .BRANCH(BRANCH), .ALUCTR(ALUCTR)

);

INITIAL BEGIN

// INITIALIZE INPUTS

OP = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

OP = 6'B000000;

#100;

OP = 6'B100011;

#100;

OP = 6'B101011;

#100;

OP = 6'B000100;

#100;

OP = 6'B001111;

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

b. ALUop的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:ALUop,然后输入其实现代码:

MODULE ALUOP(

INPUT [5:0] FUNC,

INPUT [1:0] ALUCTR,

OUTPUT [2:0] ALU_OP

);

WIRE I_RT = ALUCTR[1] & ~ALUCTR[0];

ASSIGN ALU_OP[2]=(I_RT&((~FUNC[2]&FUNC[1])|(FUNC[2] &FUNC[0]))) | ALUCTR[0];

ASSIGN ALU_OP[1]=(I_RT &FUNC[2] &FUNC[1])| (ALUCTR[1]& ALUCTR[0]);

ASSIGN ALU_OP[0]=(I_RT &FUNC[2] &~FUNC[1]);

ENDMODULE

在ISE集成开发环境中,对模块ALUop进行综合(Synthesize), 综合结果如图:

在ISE集成开发环境中,对模块ALUop进行仿真(Simulation)。首先输入如下测式

代码:

MODULE ALU_TB;

// INPUTS

REG [31:0] A;

REG [31:0] B;

REG [2:0] ALU_OPERATION;

// OUTPUTS

WIRE [31:0] RESULT;

WIRE ZERO;

// INSTANTIATE THE UNIT UNDER TEST (UUT) ALU UUT (

.A(A), .B(B),

.ALU_OPERATION(ALU_OPERATION), .RESULT(RESULT), .ZERO(ZERO)

);

INITIAL BEGIN

// INITIALIZE INPUTS A = 0; B = 0;

ALU_OPERATION = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

A = 1;

B = 1;

ALU_OPERATION = 0; // ADD STIMULUS HERE #100 A = 2; B = 2;

ALU_OPERATION = 4;

#100 A = 1; B = 1;

ALU_OPERATION = 1; #100 A = 1; B = 1;

ALU_OPERATION = 5; #100 A = 1; B = 1;

ALU_OPERATION = 2;

END

ENDMODULE

然后进行仿真,仿真结果如图所:

c. 将Control与ALUop封装成Controller

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:Controller,然后输入其实现代码:

MODULE CONTROLLER(

INPUT [5:0] OP, INPUT [5:0] FUNC, OUTPUT REGDST, OUTPUT REGWRITE, OUTPUT ALUSRC, OUTPUT MEMWRITE, OUTPUT MEMREAD, OUTPUT MEMTOREG, OUTPUT BRANCH, OUTPUT [2:0] ALU_OP

);

WIRE [1:0] ALUCTR;

CONTROL U0 (OP, REGDST, REGWRITE, ALUSRC, MEMWRITE, MEMREAD, MEMTOREG, BRANCH,

ALUCTR);

ALUOP U1 (FUNC, ALUCTR, ALU_OP);

ENDMODULE

在ISE集成开发环境中,对模块Controller进行综合(Synthesize),综合结果如图:

在ISE集成开发环境中,对模块Controller进行仿真(Simulation)。首先输入如下测式代码:

MODULE CONTROLLER_TB;

// INPUTS

REG [5:0] OP;

REG [5:0] FUNC;

// OUTPUTS

WIRE REGDST;

WIRE REGWRITE;

WIRE ALUSRC;

WIRE MEMWRITE;

WIRE MEMREAD;

WIRE MEMTOREG;

WIRE BRANCH;

WIRE [2:0] ALU_OP;

// INSTANTIATE THE UNIT UNDER TEST (UUT) CONTROLLER UUT (

.OP(OP), .FUNC(FUNC), .REGDST(REGDST), .REGWRITE(REGWRITE), .ALUSRC(ALUSRC), .MEMWRITE(MEMWRITE), .MEMREAD(MEMREAD), .MEMTOREG(MEMTOREG), .BRANCH(BRANCH), .ALU_OP(ALU_OP)

);

INITIAL BEGIN

// INITIALIZE INPUTS

OP = 0;

FUNC = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

OP =6'B100011;

#100

OP=6'B101011;

#100

OP=6'B000100;

#100

OP=6'B001111;

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

(6)取指电路的设计与实现

取指电路需完成ADD32、PC寄存器、多路选择器和左移两位模块,从而实现该取指电路。

a.ADD32的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:ADD32,然后输入其实现代码:

MODULE ADD32(

INPUT [31:0] A, B,

OUTPUT [31:0] C

);

ASSIGN C = A + B;

ENDMODULE

在ISE集成开发环境中,对模块Controller进行综合(Synthesize),综合结果如图:

b.左移两位模块(Left_2_Shifter)的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:Left_2_Shifter,然后输入其实现代码:

MODULE LEFT_2_SHIFTER(

INPUT [31:0] D,

OUTPUT [31:0] O

);

ASSIGN O = {D[29:0], 2'B00};

ENDMODULE

在ISE集成开发环境中,对模块Controller进行综合(Synthesize),综合结果如图:

c.综合取指电路(Fetch)的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:Fetch,然后输入其实现代码:

MODULE FETCH(

INPUT RESET,

INPUT CLOCK,

INPUT [31:0] B_ADDR,

INPUT Z, B,

OUTPUT [31:0] ADDR

);

REG [31:0] PC;

WIRE [31:0] U0_O;

WIRE [31:0] U1_C;

WIRE [31:0] U2_C;

WIRE [31:0] NEXT_PC;

WIRE SEL = Z & B;

LEFT_2_SHIFTER U0 (B_ADDR, U0_O); ADD32 U1 (PC, 4, U1_C); ADD32 U2 (U1_C, U0_O, U2_C);

MUX32_2_1 M1 (U1_C, U2_C, SEL, NEXT_PC);

ASSIGN ADDR = PC;

ALWAYS @ (POSEDGE CLOCK OR NEGEDGE RESET) BEGIN

IF (RESET == 0)

PC = 0;

ELSE

PC = NEXT_PC;

END

ENDMODULE

在ISE集成开发环境中,对模块Fetch进行综合(Synthesize),综合结果如图:

在ISE集成开发环境中,对模块Fetch进行仿真(Simulation)。首先输入如下测式代码:

MODULE FETCH_T;

// INPUTS

REG CLOCK;

REG RESET;

REG [31:0] B_ADDR;

REG B;

REG Z;

// OUTPUTS

WIRE [31:0] INST;

WIRE [31:0] O_ADDR;

WIRE [31:0] O_SUM;

WIRE [31:0] O_SUM1;

// INSTANTIATE THE UNIT UNDER TEST (UUT) FETCH UUT (

.CLOCK(CLOCK), .RESET(RESET), .B_ADDR(B_ADDR), .B(B), .Z(Z), .INST(INST), .O_ADDR(O_ADDR), .O_SUM(O_SUM), .O_SUM1(O_SUM1)

);

INITIAL BEGIN

// INITIALIZE INPUTS

CLOCK = 0;

RESET = 0;

B_ADDR = 0;

B = 0;

Z = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

CLOCK=1;

#100;

CLOCK=0;

#100;

CLOCK=1;

#100;

CLOCK=0;

#100;

CLOCK=1;

#100;

CLOCK=0;

#100;

CLOCK=1;

#100; Z=1; B=1;

B_ADDR=32'H4;

CLOCK=0;

#100;

CLOCK=1;

#100;

CLOCK=0;

B=0; Z=0; #100;

CLOCK=1;

#100;

CLOCK=0;

#100;

CLOCK=1;

B_ADDR=32'B0;

#100;

CLOCK=0;

#100;

RESET=1;

CLOCK=1;

#100;

CLOCK=0;

#100;

CLOCK=1;

#100;

CLOCK=0;

// ADD STIMULUS HERE // ADD STIMULUS HERE

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

(7)数据通路Data_Flow的设计与实现

除去指令存储器Instruction ROM、数据存储器DATA MEM,将剩余的电路封装成一个单周期的CPU数据通路(Data_Flow)模块。

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:Data_Flow,然后输入其实现代码:

MODULE DATA_FLOW(

INPUT RESET,

INPUT CLOCK,

INPUT [31:0] INST,

INPUT [31:0] DATA,

OUTPUT MEMWRITE,

OUTPUT MEMREAD,

OUTPUT [31:0] RESULT,

OUTPUT [31:0] B_DATA,

OUTPUT [31:0] NEXTPC

);

WIRE [31:0] B_ADDR;

WIRE Z, B;

WIRE REGDST;

WIRE REGWRITE;

WIRE ALUSRC;

WIRE MEMTOREG;

WIRE [2:0] ALU_OP;

WIRE [31:0] ALU_A, ALU_B;

WIRE [4:0] WN;

WIRE [31:0] WD;

FETCH U0 (RESET, CLOCK, B_ADDR, Z, B, NEXTPC);

CONTROLLER U1 (INST[31:26], INST[5:0], REGDST, REGWRITE, ALUSRC,

MEMWRITE, MEMREAD, MEMTOREG, B, ALU_OP);

ALU U2 (ALU_A, ALU_B, ALU_OP, RESULT, Z);

REGFILE U3 (INST[25:21], INST[20:16], WN, REGWRITE, WD, ALU_A, B_DATA, CLOCK); MUX5_2_1 U4 (INST[20:16], INST[15:11], REGDST, WN); MUX32_2_1 U5 (B_DATA, B_ADDR, ALUSRC, ALU_B); SIGN_EXTENDER U6 (INST[15:0], B_ADDR); MUX32_2_1 U7 (NEXTPC, DATA, MEMTOREG, WD);

ENDMODULE

在ISE集成开发环境中,对模块Controller进行综合(Synthesize),综合结果如图:

在ISE集成开发环境中,对模块Data_Flow进行仿真(Simulation)。首先输入如下测式代码:

MODULE DATA_FLOW_TB;

// INPUTS

REG RESET;

REG CLOCK;

REG [31:0] INST;

REG [31:0] DATA;

// OUTPUTS

WIRE MEMWRITE;

WIRE MEMREAD;

WIRE [31:0] RESULT;

WIRE [31:0] B_DATA;

WIRE [31:0] NEXTPC;

// INSTANTIATE THE UNIT UNDER TEST (UUT) DATA_FLOW UUT (

.RESET(RESET), .CLOCK(CLOCK), .INST(INST), .DATA(DATA), .MEMWRITE(MEMWRITE), .MEMREAD(MEMREAD), .RESULT(RESULT), .B_DATA(B_DATA), .NEXTPC(NEXTPC)

);

INITIAL BEGIN

// INITIALIZE INPUTS RESET = 0; CLOCK = 0; INST = 0; DATA = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100; RESET = 1; //#100;

INST = 32'H00002820;//R型,ADD,0号0号寄存器内容相加保存到5号寄存

器,执行后MW,MR应为零,B_DATA应为零

#100; CLOCK = 1; #100; CLOCK = 0; #100;

单元内容

INST = 32'H8CB10000;//I,LW,5号与立即数符号扩展相加作为地址,将内存

DATA

送到9号寄存器,执行:

#100; CLOCK = 1; #100; CLOCK = 0; #100

INST = 32'HACA00000;//I,SW,5号与立即数符号扩展相加作为地址,将0号

寄存器的内容送到内存单元,执行:

应为0,MW应为1,B_DATA应为0号寄存器内容0

//MR

#100; CLOCK = 1; #100; RESET = 0; // ADD STIMULUS HERE

END

ENDMODULE

然后进行仿真,仿真结果如图所示:

(8)Instruction ROM的设计与实现

假定一个只有32个32位单元的指令存储器,由于只读无需写入,所以可以设置为简化的32个wire型变量,每个变量可被赋值为一条指令。

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:Inst_ROM,然后输入其实现代码:

MODULE INST_ROM(

INPUT [31:0] ADDRESS,

OUTPUT [31:0] INST

);

WIRE [31:0] RAM [0:31];

ASSIGN RAM [0] = 32'B000000_00001_00010_00011_00000100000;//AND

ASSIGN RAM [1] = 32'B000000_00001_00010_00011_00000100000;//AND

ASSIGN RAM [2] = 32'B100011_00101_10001_0000000000000000;//LW

ASSIGN RAM [3] = 32'B100011_00101_10010_0000000000000100;//LW

ASSIGN RAM [4] = 32'B000000_10001_10010_10001_00000100000;//AND

ASSIGN RAM [5] = 32'B100011_00101_10010_0000000000001000;//LW

ASSIGN RAM [6] = 32'B000100_10001_10001_0000000000000001;//BEP

ASSIGN RAM [7] = 32'B101011_00101_00000_0000000000001100;//SW

ASSIGN INST = RAM[ADDRESS[6:2]];

ENDMODULE

在ISE集成开发环境中,对模块Inst_ROM进行综合(Synthesize),综合结果如图:

在ISE集成开发环境中,对模块Inst_ROM进行仿真(Simulation)。首先输入如下测式代码:

MODULE INST_ROM_TB;

// INPUTS

REG [31:0] ADDRESS;

// OUTPUTS

WIRE [31:0] INST;

// INSTANTIATE THE UNIT UNDER TEST (UUT) INST_ROM UUT (

.ADDRESS(ADDRESS), .INST(INST)

);

INITIAL BEGIN

// INITIALIZE INPUTS

ADDRESS = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

ADDRESS = 0;

#100;

ADDRESS = 4;

#100;

ADDRESS = 8;

#100;

ADDRESS = 12;

#100;

ADDRESS = 16;

#100;

ADDRESS = 20;

#100;

ADDRESS = 24;

#100;

ADDRESS = 28;

// ADD STIMULUS HERE

END

ENDMODULE

然后进行仿真,仿真结果如图:

(9)Data Mem模块的设计与实现

对于实验而言,32个32位单元的数据存储器已满足需求(实际情况应该是以字节编址)。由于需要保存并写入数据,所以应设置32个reg型变量,要求初始化0、1、2号单元的内容为2、3、5。

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出 的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:data_mem,然后输入其实现代码:

MODULE DATA_MEM(ADDR, READ, WRITE, DATAIN, CLOCK, DATAOUT);

INPUT [31:0] ADDR;

INPUT READ, WRITE; INPUT [31:0] DATAIN; INPUT CLOCK;

OUTPUT [31:0] DATAOUT;

REG [31:0] RAM [0:31];

ASSIGN DATAOUT = READ ? RAM[ADDR[6:2]] : 32'HXXXXXXXX;

ALWAYS @ (POSEDGE CLOCK) BEGIN

RAM[ADDR[6:2]] = WRITE ? DATAIN : 32'HXXXXXXXX; END

INTEGER I;

INITIAL BEGIN

FOR(I = 0;I<32;I = I + 1)

RAM[I] = I;

END

ENDMODULE

在ISE集成开发环境中,对模块data_mem进行综合(Synthesize), 综合结果如图:

(10)MainBoard模块的设计与实现

在ISE集成开发环境中,在工程管理区任意位置单击鼠标右键,在弹出 的菜单中选择New Source命令,创建一个Verilog Module模块,名称为:MainBoard,然后输入其实现代码:

MODULE MAINBOARD(

INPUT CLOCK,RESET,

OUTPUT [31:0] INST,

OUTPUT [31:0] PC,

OUTPUT [31:0] ALUOUT,

OUTPUT [31:0] B_DATA

);

WIRE [31:0] ADDR_FTI;

WIRE [31:0] DATA_DTF;

WIRE MEMWRITE,MEMREAD;

WIRE [31:0] RESULT;

WIRE [31:0] NEXTPC;

DATA_FLOW U0(RESET, CLOCK, INST, DATA_DTF, MEMWRITE, MEMREAD, RESULT, B_DATA,

NEXTPC);

INST_ROM U1(NEXTPC, INST);

DATA_MEM U2(CLOCK, DATA_DTF, B_DATA, RESULT, MEMWRITE, MEMREAD);

ASSIGN PC = NEXTPC;

ASSIGN ALUOUT = RESULT;

ENDMODULE

在ISE集成开发环境中,对模块MIPS_CPU进行综合(Synthesize), 综合结果如图22所示。

在ISE集成开发环境中,对模块Inst_ROM进行仿真(Simulation)。首先输入如下测式代码:

MODULE MAINBOARD_TB;

// INPUTS REG CLOCK; REG RESET;

// OUTPUTS WIRE [31:0] INST; WIRE [31:0] PC; WIRE [31:0] ALUOUT; WIRE [31:0] B_DATA;

// INSTANTIATE THE UNIT UNDER TEST (UUT) MAINBOARD UUT (

.CLOCK(CLOCK), .RESET(RESET), .INST(INST), .PC(PC), .ALUOUT(ALUOUT), .B_DATA(B_DATA)

);

INITIAL BEGIN

// INITIALIZE INPUTS

CLOCK = 0; RESET = 0;

// WAIT 100 NS FOR GLOBAL RESET TO FINISH #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1;

#100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1; #100;

CLOCK = ~CLOCK;

RESET = 1;

END

ENDMODULE

然后进行仿真,仿真结果如图:

在该转移的地方进行了转移,成功。 九、 实验数据及结果分析:

在一个时钟周期内所设计的CPU能够完成一条指令的执行,指令执行结果与预期的结果是一致的。通过仿真可以看到最终顺利实现了每个模块的功能,成功解决了之前出错的PC转移问题,整个CPU按照设计好的指令运行。 十、 实验结论:

单周期CPU在一个时钟周期完成指令的所有执行步骤,简化了CPU的设计,但是这样没有考虑不同部件完成时间上的差异,所以导致CPU各部件的利用率不高,采用多周期流水线CPU可以提高利用率,但是难度也会增大许多。 十一、 总结及心得体会:

我本身对这次实验很兴趣,指导教师陈老师也非常和蔼耐心地指导,所以比较顺利地完成了整个实验。

本次实验完全是完成,没有任何抄袭,包括实验报告的编写,每一段代码都是自己写出来的,每一张图片也都是自己截的图,虽然整个过程花的时间比较多,但确实收获很多,很开心,也希望能得到一个好的成绩。

本次实验让我切实感受到了仿真的好处,计算机仿真在实际生产中的作用,也很好地锻炼了自己的逻辑思维能力,对课堂第四章第五章的内容有了更为深刻的理解。

要合理地将本次实验中“把庞大的部件分割为许多小部件,逐一解决” 的方法运用到对其它问题的解决中。

十二、 对本实验过程及方法、手段的改进建议:

建议增加2个实验学时,同时将要实现的指令增加为十一条,增加运算器溢出信号Overflow、判断溢出的加法运算,以及 J型指令的设计与实现,从而进一步锻炼自己。 报告评分:

指导教师签字:

因篇幅问题不能全部显示,请点此查看更多更全内容

Copyright © 2019- sceh.cn 版权所有 湘ICP备2023017654号-4

违法及侵权请联系:TEL:199 1889 7713 E-MAIL:2724546146@qq.com

本站由北京市万商天勤律师事务所王兴未律师提供法律服务