关于程序计数器PC

16年408真题

18.某计算机主存空间为4GB,字长为32位,按字节编址,采用32位字长指令字格式。若指令
按字边界对齐存放,则程序计数器(PC)和指令寄存器(IR)的位数至少分别是(B)

A.30,30 B. 30,32 C. 32,30 D. 32,32

做了这一道题不禁在想,PC究竟存储的是字地址还是字节地址?依据答案的说法,似乎对此并无硬性要求,即二者均可。因题目描述位“至少”所以按字地址算。

在查阅资料后发现程序计数器PC甚至“不是实际存在的”。

PC应该是存在与理论设计层面的寄存器,不同的指令集都有对PC功能的实现,但可能不止使用一个寄存器,这个或者说这组寄存器也不一定叫PC,甚至叫“程序计数器”这个名字也仅是出于历史原因,更合理的名字似乎应该是IAR。所以对于此问题应当分指令集讨论。

在存储程序概念中,使用一个寄存器来保存当前运行的指令地址是绝对必要的。尽管这个寄存器更为合理的名字可能应该是指令地址寄存器(instruction address register),但是出于历史原因,这个寄存器通常称为程序计数器(program counter),在MIPS体系结构中缩写为PC。jal指令实际上将PC+4保存在寄存器$ra中,从而将链接指向下一条指令,为过程返回做好准备。

——《计算机组成与设计:硬件/软件接口(原书第五版)》P65

对于MIPS指令集来说,PC是真真实实存在的,且存储的是字地址,因此MIPS作为指令字长32位的RISC执行的是PC+4而非PC+1。另外值得注意的是,MIPS中bep指令的偏移量是字地址,所以需要左移两位,MIPS系统结构数据通路中是由执行移位操作的部件的,所以如果有某个指令集的PC存储的是字地址也不是不可实现的。

程序计时 jAVA 程序计时器的位数_寄存器

对于x86这样的CISC来说就要稍微复杂些了,例如8086,是由代码段寄存器CS(Code Segment)和指令指针寄存器IP(Instruction Pointer)组合实现类似PC功能的。8086内部寄存器均为16位,但可利用地址加法器来产生20位地址,具体计算时,要将段寄存器的内容左移4位,然后再与IP的内容相加。此外8086并非用一条指令取一条,而是可以取多条指令放在指令队列缓冲器中。

1)8086的指令队列为6个字节,8088的指令队列为4个字节。不管是8086还是8088,都会在执行指令的同时,从内存中取下面1条指令或几条指令,取来的指令就放在指令队列缓冲器中。这样,一般情况下,8086/8088执行完一条指令就可以立即执行下一条指令,而不像以往的计算机那样,轮番地进行取指令和执行指令的操作,从而提高了CPU的效率。

2)地址加法器用来产生20位地址。8086可用20位地址寻址1MB的内存空间,但8086内部所有的寄存器都是16位的,所以需要由一个附加的机构来根据16位寄存器提供的信息计算出20位的物理地址,这个机构就是20位的地址加法器。

比如,一条指令的物理地址就是根据代码段寄存器CS和指令指针寄存器IP的内容得到的。具体计算时,要将段寄存器的内容左移4位,然后再与IP的内容相加。假设CS=FEOOH,IP=0200H,此时指令的物理地址为FE200H。

——《接口技术》P22

程序计时 jAVA 程序计时器的位数_寄存器_02