控制器设计 精品.docx

上传人:b****2 文档编号:24112688 上传时间:2023-05-24 格式:DOCX 页数:18 大小:84.99KB
下载 相关 举报
控制器设计 精品.docx_第1页
第1页 / 共18页
控制器设计 精品.docx_第2页
第2页 / 共18页
控制器设计 精品.docx_第3页
第3页 / 共18页
控制器设计 精品.docx_第4页
第4页 / 共18页
控制器设计 精品.docx_第5页
第5页 / 共18页
点击查看更多>>
下载资源
资源描述

控制器设计 精品.docx

《控制器设计 精品.docx》由会员分享,可在线阅读,更多相关《控制器设计 精品.docx(18页珍藏版)》请在冰豆网上搜索。

控制器设计 精品.docx

控制器设计精品

实验报告

实验课程:

计算机组成原理I

实验日期:

20XX年11月15日,交报告日期:

20XX年12月2日

同组学生

姓名

学号

20XX07063

20XX07061

一、实验课题

按照题目要求设计计算机控制器的基本逻辑(不包括微操作信号产生电路),决定外部的端口(名称、有效电平)和内部各元件的连接,画出系统框图和逻辑图,设计仿真数据,用VHDL编程和仿真。

实验内容:

用层次结构设计的方法设计控制器的指令部件。

下层元件的设计已经在实验3中完成。

包括:

程序计数器、指令寄存器、数据寄存器、地址寄存器、指令译码器等。

本实验只需要做顶层设计。

顶层设计

功能要求:

具有控制器的部分基本功能,能够控制取指令操作、控制访存取数据操作、控制访存存数据操作、指令译码,等。

取指令机器周期:

把程序计数器的内容送到地址总线,延迟一段时间后把从存储器中读出的指令(通过数据总线读入),送到指令寄存器;每取一个指令字程序计数器加1。

取数据机器周期:

把地址寄存器的内容送到地址总线,延迟一段时间后把从存储器中读出的数据(通过数据总线)送到数据寄存器。

存数据机器周期:

把地址寄存器的内容送到地址总线,把数据寄存器中的数据送到数据总线,延迟一段时间后结束。

指令译码:

假设操作码在指令字的最高3位。

提示1:

控制器内部数据通路,可以是总线结构,也可以是直接连接结构。

提示2:

控制器与系统总线的连接方法,有两种结构可以考虑:

①程序计数器、指令寄存器、数据寄存器、地址寄存器都与系统总线有直接连接。

②只有数据寄存器和地址寄存器与系统总线连接。

程序计数器和指令寄存器不与系统总线连接。

程序计数器内容必须先送到地址寄存器,然后才能到地址总线。

从存储器中读出的指令必须先送到数据寄存器,然后才能到指令寄存器。

仿真

设计仿真波形数据,模拟取指令、访存取数据、访存存数据等操作。

要考虑到所有可能的情况。

在实验报告中必须清楚说明仿真波形数据是怎样设计的。

 

二、逻辑设计

 

控制器系统框图

 

端口说明:

Loadq,loadd:

数据寄存器的同步置数端口

Loada:

地址寄存器的同步置数端口

Loadi:

指令寄存器的同步置数端口

zq,zd;数据寄存器的三态控制端口

Clk:

时钟信号

Zpc:

程序计数器的三态控制端口

Za:

地址寄存器的三态控制端口

ld:

程序计数器的同步置数端口

r:

程序计数器的同步清零端口

et:

程序计数器的加1控制端口

cot:

cot(0),cot

(1)分别控制数据寄存器和程序计数器向地址寄存器和指令寄存器的数据传送

qd:

数据的双向输入输出端口(连接系统数据总线)数据从外部先送到系统总线才可以送到数据寄存器

da:

地址寄存器输出端口(连接系统地址总线)

ic:

经过译码器输出的控制信号

d:

程序计数器的置数端口。

 

控制器逻辑图

 

 

三、VHDL源程序

libraryieee;

useieee.std_logic_1164.all;

useieee.std_logic_arith.all;

--ContolUnit

entitycontrol_unitis

port

--loadd,loadq,loada,loadi同步置数端口高电平有效

--zq,zd三态控制端口,低电平有效

--zpc,za三态控制端口,高电平有效

--clk时钟信号,上升沿有效

--ld程序计数器的预置数端口,低电平有效

--r程序计数器的清零端口,低电平有效

--et控制程序计数器自动加1功能

--qd数据从内存读出数据后送入系统总线的输入端,也是输出端口

--ic译码器的输出端口,即:

控制信号。

--cot是控制数据在寄存器间传输的信号

--cot(0)控制DR到IR的数据流通

--cot

(1)控制程序计数器到AR的数据流通

--d程序计数器的输入端口

loadd,loadq,loada,loadi,zq,zd,clk,ld,r,et,za,zpc:

instd_logic;

cot:

instd_logic_vector(1downto0);

qd:

inoutstd_logic_vector(7downto0);

d:

inunsigned(7downto0);

ic:

outstd_logic_vector(7downto0);

qa:

outstd_logic_vector(7downto0)

);

endcontrol_unit;

architecturebehaveofcontrol_unitis

--数据总线和地址总线

--signalABUS:

std_logic_vector(7downto0);

--signalDBUS:

std_logic_vector(7downto0);

--引用地址寄存器

ponentaddress_register

port

--load同步并行置数

--z三态输出z=1isvalidesignal

--d输入

--q输出

load,z,clk:

instd_logic;

d:

instd_logic_vector(7downto0);

q:

outstd_logic_vector(7downto0)

);

endponent;

--引用数据寄存器

ponentdata_register

port

--clk时钟信号

--zq控制q端口的三态

--zd控制d端口的三态

--load1,load2同步并行置数.loadd控制d,loadq控制q

--d输入输出双向端口

--q输入输出端口

clk,zd,zq,loadd,loadq:

instd_logic;

d:

inoutstd_logic_vector(7downto0);

q:

inoutstd_logic_vector(7downto0)

);

endponent;

--引用译码器

ponentdecode

port

A:

instd_logic_vector(2downto0);--输入

Y:

outstd_logic_vector(7downto0)--输出

);

endponent;

--引用程序计数器

ponenteight_count

port

--et控制自动加1的端口

--clk时钟信号

--c进位输出

--z三态们z=1

--ld预制数控制端ld=0

--r同步清零端r=0有效

et,clk,z,ld,r:

instd_logic;

c:

outstd_logic;

d:

inunsigned(7downto0);

q:

outunsigned(7downto0)

);

endponent;

--引用指令寄存器

ponentinstruction_register

port

clk,load:

instd_logic;

d:

instd_logic_vector(7downto0);

q:

outstd_logic_vector(7downto0)

);

endponent;

--在程序计数器和地址寄存器之间的内部信号

signalpcdr:

std_logic_vector(7downto0);

signalUSpcdr:

unsigned(7downto0);

--在数据寄存器到指令寄存器之间的内部信号

signaldrir:

std_logic_vector(7downto0);

signaldeir:

std_logic_vector(7downto0);

---暂存信号

signalt1:

std_logic_vector(7downto0);

signalt2:

std_logic_vector(7downto0);

signalt3:

std_logic_vector(7downto0);

begin

P1:

process(cot)

begin

ifcot

(1)='0'then

t1<=(others=>('Z'));

elset1<=pcdr;

endif;

ifcot(0)='0'then

t2<=(others=>('Z'));

elset2<=drir;

endif;

endprocess;

--实例化程序计数器,

PC:

eight_countportmap

(clk=>clk,z=>zpc,et=>et,d=>d,ld=>ld,r=>r,q=>USpcdr);

--convertunsigneddatatostd_logic_vector;

pcdr<=conv_std_logic_vector(USpcdr,8);

--t1<=cot

(1)andpcdr;

--实例化地址寄存器

AR:

address_registerportmap

(clk=>clk,z=>za,load=>loada,d=>t1,q=>qa);

--实例化数据寄存器

DR:

data_registerportmap

(clk=>clk,zq=>zq,zd=>zd,loadd=>loadd,loadq=>loadq,q=>qd,d=>drir);

--实例化指令寄存器

IR:

instruction_registerportmap

(clk=>clk,load=>loadi,d=>t2,q=>deir);

--实例化译码器

DE:

decodeportmap

(A=>deir(7downto5),Y=>ic);

endbehave;

--address_register

libraryieee;

useieee.std_logic_1164.all;

entityaddress_registeris

port

--load同步并行置数

--z三态输出z=1isvalidesignal

--d输入

--q输出

load,z,clk:

instd_logic;

d:

instd_logic_vector(7downto0);

q:

outstd_logic_vector(7downto0)

);

endaddress_register;

architecturebehaveofaddress_registeris

signaliq:

std_logic_vector(7downto0);

begin

process(clk,z,load)

begin

ifrising_edge(clk)andload='1'then

iq<=d;

endif;

ifz='1'then

q<=(others=>'Z');

else

q<=iq;

endif;

endprocess;

endbehave;

 

--dataregister

libraryieee;

useieee.std_logic_1164.all;

entitydata_registeris

port

--clk时钟信号

--zq控制q端口的三态

--zd控制d端口的三态

--load1,load2同步并行置数.loadd控制d,loadq控制q

--d输入输出双向端口

--q输入输出端口

clk,zd,zq,loadd,loadq:

instd_logic;

d:

inoutstd_logic_vector(7downto0);

q:

inoutstd_logic_vector(7downto0)

);

enddata_register;

architecturebehaveofdata_registeris

signaliq:

std_logic_vector(7downto0);

begin

process(clk,zd,zq,loadd,loadq)

begin

ifrising_edge(clk)then

ifloadd='1'andzd='0'then--因为d是双向端口,当d作为输入端口时,

--d作为输出端口时应该是高阻态,否则会产生线与

iq<=d;

d<=(others=>'Z');

endif;

ifloadq='1'andzq='0'then

iq<=q;

q<=(others=>'Z');

endif;

endif;

ifzd='0'then--三态门关闭

d<=(others=>'Z');

elsed<=iq;

endif;

ifzq='0'then--三态门关闭

q<=(others=>'Z');

elseq<=iq;

endif;

endprocess;

endbehave;

--Decode

libraryieee;

useieee.std_logic_1164.all;

entitydecodeis

port

A:

instd_logic_vector(2downto0);--输入

Y:

outstd_logic_vector(7downto0)--输出

);

enddecode;

architecturede_behaveofdecodeis

signals:

std_logic;

begin

process(A)

begin

caseAis

when"000"=>Y<="11111110";

when"001"=>Y<="11111101";

when"010"=>Y<="11111011";

when"011"=>Y<="11110111";

when"100"=>Y<="11101111";

when"101"=>Y<="11011111";

when"110"=>Y<="10111111";

when"111"=>Y<="01111111";

endcase;

endprocess;

endde_behave;

--eight_count

libraryieee;

useieee.std_logic_1164.all;

useieee.std_logic_arith.all;

entityeight_countis

port

--et控制自动加1的端口

--clk时钟信号

--c进位输出

--z三态们z=1

--ld预制数控制端ld=0

--r同步清零端r=0有效

et,clk,z,ld,r:

instd_logic;

c:

outstd_logic;

d:

inunsigned(7downto0);

q:

outunsigned(7downto0)

);

endeight_count;

architecturebehaveofeight_countis

signaliq:

unsigned(7downto0);

begin

process(clk,et,z,ld,r)

begin

ifrising_edge(clk)then

ifr='0'then--同步清零

iq<=(others=>'0');

elsifld='0'theniq<=d;--预制数

elsifet='1'theniq<=iq+1;--计数

endif;

endif;

ifiq=255thenc<='1';--计数到255,产生进位

elsec<='0';

endif;

q<=iq;

ifz='1'then--三态们关闭

c<='Z';

q<=(others=>'Z');

endif;

endprocess;

endbehave;

libraryieee;

useieee.std_logic_1164.all;

entityinstruction_registeris

port

clk,load:

instd_logic;

d:

instd_logic_vector(7downto0);

q:

outstd_logic_vector(7downto0)

);

endinstruction_register;

architecturebehaveofinstruction_registeris

signalsave:

std_logic_vector(7downto0);

begin

process(clk,load)

begin

ifrising_edge(clk)andload='1'then

save<=d;

endif;

q<=save;

endprocess;

endbehave;

四、仿真设计

由于元器件的仿真在实验3中已经做过,所以此处不再进行元器件的仿真。

首先令clk每隔10纳秒翻转一次。

et=1(有效),ld=1(无效),r=1(无效)

这是程序计数器处于工作状态。

取指令:

在第三个时钟上升沿时,zpc=0,(程序计数器三态门打开),loada=1(地址寄存器同步控制端有效),za=0(地址寄存器三态门打开),Cot

(1)=1(让pc输出的数据传入地址寄存器),这是输出应该是00000010,因为程序计数器刚好计数三个。

访存取指令:

下一个时钟上升沿时.

qd=11111111,zq=0,zd=1,loadq=1,loadd=0.za=1,zpc=1,loada=0,loadi=1,cot(0)=1

下一个时钟上升沿时:

zd=1(数据寄存器的三态门打开),loadi=1(指令寄存器的同步置数端口有效),cot=’01’(让数据寄存器里的数据传入指令寄存器)。

结果ic输出的应该是qd的高三位对应的指令控制信号011111111.

访存存数据:

下一个时钟上升沿:

Zq=1,其它信号都处于无效状态。

这是数据寄存器的三态门打开,数据送到系统总线,然后存入存储器。

输出的应该是先前存入的数据11111111

验证cot的有效性:

下二个时钟上升沿:

za=0,zpc=0,loada=1,cot分别等于00和10以验证控制数据传入的信号的有效性。

五、结果分析讨论

从图中可以看出,当没有置数之前,ic的值是111111110,,那是因为软件默认传入A端口的值是000,从qa的第一变化开始出也可以看出,za=0三态门打开的时候在时钟上升沿来到之前qa由ZZZZZZZZ变为00000000中也可以得到佐证。

时钟上升沿来到的时候,za的三态门是打开的,于是就把其中的地址输出,00000010,,正好是第三次时钟上升沿应该有的数据。

然后,从qd植入数据11111111,虽然数据寄存器到总线的三态门是关闭的qd输入却是置入的数据,这是正确的。

因为输入输出端口是一个端口,在此时此刻就应该显示qd置入的数据。

然后把数据寄存器中保存的指令,传入指令寄存器,得到输出结果01111111。

这真是译码器中的111对应的输出。

然后zq的三态门打开,数据寄存器中的数据送到系统总线,显示的是上一次置入的数据。

此系统总线上的数据可以送到存储器中。

然后验证cot的有效性,从图中的可以看出,两次时钟上升沿中,第一次由于cot处于无效状态qa的输出是高组态(虽然三态门已经打开),而后一次,由于cot处于有效状态,qa输出的是第九次时钟上升沿的数据00001000

这一副图也是验证cot有效性的。

但它是验证数据寄存器和指令寄存器之间的cot的有效性的。

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 外语学习 > 韩语学习

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1