Cpu设计

最简单的cpu设计

这里有一个用Verilog HDL语言设计的计算机内核,可以运行简单的程序,我在研究生班教学中作为设计实例完成的。该设计已通过Quartus II软件环境的测试,并已下载到自制的开发实验板上运行。其中,内存是哈佛结构,直接利用Quartus II给出的内存元素组织而成。

程序

//基本输入时钟

//复位控制:reset_n,低电位有效。

//基本输出:o

//程序内存iram,16位,高5位为类指令代码,初始化为imem16.mif。

//数据存储器dram,16位,无数据文件初始化。

lpm存储器的地址信号在读写数据之前应该稳定在1拍。

//指令格式:高5位指令代码,11位地址码,16位立即数(分高低8位)。

模块测试

时钟,

重置_n,

哦,

//调试输出(可选):

opc,

奥马尔,

ojp,

oqw,

奥尔达,

oadd,

oout

);

输入时钟;

输入reset _ n;

output[15:0]o;

output[15:0]oqw;

output [10:0] opc,omar

输出[2:0]ojp;

输出olda、oadd、oout

电线dwren

wire[15:0]q _ w;

wire[15:0]q _ data;

reg [15:0] b,a,ir,da,oo,ddata

reg [10:0] pc,mar

reg[2:0]jp;//节拍

reg dwrit//写控制

//指令:

Reg lda,// fetch:从数据单元取数到da。

Add,// Add: da加到数据单元,结果放入da。

Out,// output:将数据单元的内容输出到输出寄存器。

Sdal,//低位8位立即数:将8位立即数扩展为16位并发送给da。

Sdah,//高8位立即数:将8位立即数作为高8位,与原da的低8位连接,形成16位,放入da中。

str//da发送数据存储单元:

//模拟信号输出:

赋值o = oo

分配opc = pc

赋值omar = mar

赋值ojp = jp

赋值oqw = q _ w;

赋值olda = lda

assign oadd = add

赋值oout = out

赋值dwren = dwrit

//指令存储器:

lpm_rom iram(。地址(个人电脑)。inclock(时钟)。q(q _ w));//程序存储器

def param iram . LPM _ width = 16;

def param iram . LPM _ width ad = 11;

defparam iram.lpm_outdata = "未注册";

def param iram . LPM _ in data = " REGISTERED ";

def param iram . LPM _ address _ control = " REGISTERED ";

def param iram . LPM _ file = " imem 16 . MIF ";//初始化文件并放置程序。

//数据存储:

lpm_ram_dq dram(。数据(ddata)。地址(mar)。我们(dwren)。inclock(时钟)。q(q _ data));def param dram . LPM _ width = 16;

def param dram . LPM _ width ad = 11;

defparam dram.lpm_outdata = "未注册";

def param dram . LPM _ in data = " REGISTERED ";

def param dram . LPM _ address _ control = " REGISTERED ";

always @(正边沿时钟或负边沿复位_n)

开始

如果(!reset_n)

开始

pc & lt= 0;

lda & lt= 0;

添加& lt= 0;

out & lt= 0;

sdal & lt= 0;

sdah & lt= 0;

str & lt= 0;

jp & lt=0;

结束

其他

开始

jp & lt= jp+1;

案例(jp)

0:开始

结束

1:开始

案例(q_w[15:11])

5 ' b 00001:LDA & lt;= 1;//lda:00001

5 ' b 00010:add & lt;= 1;//地址:00010

5 ' b 00011:out & lt;= 1;//out:00011

5 ' b 00100:sdal & lt;= 1;//低8位,用带符号的16位扩展

5 ' b 00101:sdah & lt;= 1;//高8位,与前面的低8位组合形成16位。

5 ' b 00110:str & lt;= 1;//da发送数据单元

结束案例

结束

2:开始

if (lda || add || out || str)

mar & lt= q _ w[10:0];

结束

3:PC & lt;= PC+1;

4:开始

中频(lda)

开始

da & lt= q _ data

jp & lt= 0;

lda & lt= 0;

结束

其他

如果(添加)

开始

b & lt= q _ data

a & lt= da

结束

其他

如果(出局)

开始

oo & lt= q _ data

jp & lt= 0;

out & lt= 0;

结束

其他

如果(sdal)

开始

da & lt= {{8{q_w[7]}},q _ w[7:0]};//扩展为16有符号数。

sdal & lt= 0;

结束

其他

if (sdah)

开始

da[15:0]& lt;= {q_w[7:0],da[7:0]};

sdah & lt= 0;

结束

其他

if(字符串)

开始

ddata & lt= da

dwrit & lt= 1;

结束

结束

5:开始

如果(添加)

开始

da & lt= a+b;

jp & lt= 0;

添加& lt= 0;

结束

其他

if(字符串)

开始

str & lt= 0;

dwrit & lt= 0;

结束

结束

结束案例

结束

结束

末端模块

///////////模拟或执行程序的示例/////////

//assembly//

// sdal 5 2005 //

// sdah 6 2806 //

// str 10 300a //

// sdal 3 2003 //

//添加10 100a //

// str 15 300f //

// out 15 180f //

//将编译后的16十六进制数写入imem16.mif //

//////16结果输出:0608/////////。