读CSAPP之ISA、Circuit和SEQ
今年是离开校园的第六年,这六年来我一直在从事应用软件的设计、开发工作,大部分时间是在与高级编程语言、设计模式、业务逻辑打交道。它们大多流于表面,久而久之,与技术底层疏远了,诸如计算机组成原理、汇编语言、编译原理、数据结构以及算法慢慢得生疏,时至今日,向上碰到天花板,向下触到花岗岩。五年是一个契机,趁着下一个五年开始之际,我计划用三个月至半年时想间,重新学习这些知识,以期达到巩固基础,厚积薄发的目的。
本篇是我阅读《Computer System: A Programmer’s Perspective》一书的笔记,该书和与之搭配的《Professional Assembly Language》是我当下阅读计划的一部分。
我曾经不止三次翻阅第四章–处理器体系机构,然而至今未能完整读懂,其中的电子学和布尔代数小节,使我深深地为当年的逃课行为感到懊恼,–为此,我特意找了《数字电路简明教程》来补上这一课。下面这些文字,是我在半懂不懂的情况下,“断章取意”摘录的,只做自己的读书笔记。
ISA
指令集体系结构(Instrunction-Set Architecture, ISA)是指处理器所支持的指令和指令的字节级编码,其在编译器编写者和处理器设计者之间提供了一个概念抽象层。
每条指令由若干个字节组成,第一个字节包含了code部分(高四位)和function部分(低四位),不同指令的code部分可能相同,但code和function的二者组合则惟一标识一条指令,并根据其确定其他附加字节的长度和定义,处理器可以无二义性地执行目标代码程序。
数字系统由三个主要部分组成,对位进行操作的函数的组合逻辑、存储位的存储器元素,以及控制存储器元素更新的时钟信号。
Circuit
逻辑门是数字电路的基本计算元素,包括了与门、或门、与非门、或非门和非门,其构成了组合逻辑电路和时序逻辑电路,前者没有存储能力,输出仅取决于当时的输入,后者具有存储能力,其输出不仅取决于当时的输入,也取决于以前的输入序列。
在组合逻辑电路(combinational circuits)中,两个或多个逻辑门的输出不能连接在一起,同时不能形成回路。在时序逻辑电路中,存储设备由同一个时钟控制,时钟是一个周期性信号,其决定了什么时候要把新值加载到设备中。
硬件寄存器用作电路不同部分中的组合逻辑之间的屏障,每当一个时钟到达了上升沿时,值才会从寄存器的输入传送到输出,在Y86中用来保存程序计数器(PC)、条件代码(CC)和程序状态(Stat)。
SEQ
处理一条指令会有很多的操作,这些操作可以被组织成一个阶段序列,虽然不同的指令对应的操作也不相同,但阶段序列则是统一的。
- 取值(fetch),从存储器读取指令字节,地址为程序计数器(PC)的值。
- 译码(decode),从寄存器读取最多两个操作数。
- 执行(execute),算术/逻辑单元(ALU)执行指令指明的操作,或者增加或减少栈指针。
- 访存(memory),将数据写回存储器,或者从存储器读出数据。
- 写回(write back),将最多两个结果写到寄存器文件。
- 更新PC(PC update),将PC设置成下一条指令的地址。
SEQ的实现包括组合逻辑、时钟寄存器(程序计数器和条件码寄存器)、随机访问存储器(寄存器文件、指令存储器和数据存储器),组合逻辑和指令寄存器可视作不需要时序控制,程序计数器、条件码寄存器、数据存储器和寄存器文件则需要对其时序进行控制。
处理器从来不需要为了完成一条指令的执行而去读由该指令更新了的状态。
用时钟控制状态元素的更新,以及值通过组合逻辑来传播,足够控制我们SEQ实现中每条指令执行的计算了。每次时钟由低变高时,处理器开始执行一条新指令。