信息安全系统设计基础第六周学习总结

第四章 处理器体系结构

第一节 Y86指令集体系结构

一、程序员可见的状态:

每条指令都会读取或修改处理器状态的某些部分,称为程序员可见状态。

1、8个程序寄存器:%eax,%ecx,%edx,%ebx,%esi,%edi,%esp和%ebp。

2、条件码:ZF(零)、SF(符号)、OF(有符号溢出)

3、程序计数器(PC):存放当前正在执行的指令的地址

4、存储器:很大的字节数组,保存着程序和数据。Y86系统用虚拟地址来引用存储器的位置,硬件和操作系统软件联合起来将虚拟地址翻译成实际或物理地址

5、状态码(stat):表明程序执行的总体状态。(异常处理)

二、Y86指令

1、movl指令

IA32 movl指令:irmovl,rrmovl,mrmovl,rmmovl

(1)源操作数:i-立即数;r-寄存器;m-存储器

(2)目的操作数:r-寄存器;m-存储器

(3)指令附加的寄存器指示符字节依次是数据源(如果是立即数,把这一位设置成0xf)、目的寄存器/基址寄存器。 (4)有些指令需要附加四字节的常数字,采用小端法(倒序)编码

2、四个整数操作指令

addl加

subl减

andl与

xorl异或

三个条件码:

ZF-零

SF-符号

OF-溢出

3、七个跳转指令——分支控制:

jmp 直接跳转

jle(SF^OF)|ZF 有符号数≤

jl SF^OF 有符号<

je ZF 相等/零

jne ~ZF 不相等/非零

jge ~(SF^OF) 有符号≥

jg ~(SF^OF)&~ZF 有符号>

根据分支指令的类型和条件码的设置来选择分支。

4、六个条件传送指令:

cmovle

cmovl

cmove

cmovne

cmovne

cmovg

与寄存器-寄存器传送指令rrmovl一样,但只有当条件码满足所需要的约束时才会更新目的寄存器的值。

5、call和ret:

call:返回地址入栈,然后跳到目的地址;

ret指令从这样的过程调用中返回。

6、pushl和popl:

入栈和出栈

7、halt:

停止指令的执行

三、指令编码

1、指令的字节级编码。每条指令需要1-6个字节不等。每条指令的第一个字节表明指令的类型。

该字节分为两个部分,每部分4位:高4位是代码部分,低4位是功能部分。功能值只有在一组相关指令共用一个代码时才有用。

2、整数操作:代码部分均为6,功能部分区分addl,subl,andl,xorl

分支指令:代码部分均为7

传送指令:代码部分均为2

3、8个程序寄存器当中,每个都有相应的0~7的寄存器标识符。

4、程序寄存器存在CPU中的一个寄存器文件中,这个文件就是一个小的、以寄存器ID作为地址的随机访问存储器。

5、有的指令只有一个字节,而有的需要操作数的指令编码更长一点,就可能有附加的寄存器指示符字节,指定一个或两个寄存器,这些寄存器字段为rA,rB

6、附加4字节的常数字:这个字作为irmovl的立即数数据,rmmovl和mrmovl的地址指示符的偏移量,以及分支指令和调用指令的目的地址。

四、Y86异常

1、状态码Stat可能取值

AOK 正常操作

HLT 处理器执行一条halt指令(指令停止)

ADR 遇到非法地址

INS 遇到非法指令

2、异常处理

Y86——处理器停止运行指令。

五、Y86程序

1、Y86和IA32的区别

1.需要多条指令来执行一条IA32指令所完成的功能

2.以“.”开头的词是编辑器命令

3.命令 .pos0告诉编辑器应该从地址0处开始产生代码,这个地址是所有Y86程序的起点

4.声明标号Steak,并用一个.pos命令指明地址0x100

第二节 逻辑设计和硬件控制语言HCL

电子电路中,用1.0V左右的高电压表示逻辑1,用0.0V左右的低电压表示逻辑0。

一、逻辑门

AND Y=a&&b

OR Y=a||b

NOT Y=!a

二、组合电路和HCL布尔表达式

很多逻辑门组合成一个网,构建计算块。构建这些网有两条限制。

1、两个或多个逻辑门的输出不能连在一起,否则可能会使线上的信号矛盾,导致一个不合法的电压或电路故障

2、这个网必须是无环的

三、字级的组合电路和HCL整数表达式

所有字级的信号都声明为int,并不指定字的大小

多路复用函数是用情况表达式来描述的,格式如下:

  [

  select_1 : expr_1

  select_2 : expr_2

  ……

select_k : expr_k

]

  

从逻辑上讲,这些选择表达式是顺序求值的。

不同选择表达式之间允许不互斥

四、集合关系

通用格式:

iexpr in {iexpr1,iexpr2,...,iexprk}

  

其中被测值iexpr和待匹配的值iexpr1-iexprk均为整数表达式。

五、寄存器和时钟

组合电路简单的响应输入信号,产生等于输入的某个函数的输出,并存在状态在这个状态上进行计时,如此产生了时序电路。

随机访问存储器:存储多个字,用地址来选择应该读写哪个字。

时钟寄存器:存储单个位或字,时钟信号控制寄存器加载输入值。

硬件寄存器工作时,每当每个时钟到达上升沿时,值才会从寄存器的输入传送到输出。 寄存器文件读数据是一个地址为输入,数据为输出的组合逻辑块,写入字是由时钟信号控制的。

第三节 Y86的顺序实现

一、将处理组织成阶段

1、取指:从存储器读取指令字节,地址为程序计数器(PC)的值。指令指示符字节两个四位部分,称为icode(指令代码)和ifun(指令功能)。vaIP(下一条指令的地址)=PC+已取出指令的长度。

2、译码:从寄存器文件读入最多两个操作数,得到valA和/或valB。

3、执行:算数逻辑单元(ALU)根据ifun的值执行指令指明的操作,计算存储器引用的有效地址,或者增加或减少栈指针。得到的值称为valE。也可根据条件码执行跳转。

4、访存:将数据写入存储器,或者从存储器读出数据。读出的值为valM。

5、写回:最多可以写两个结果到寄存器文件。

6、更新PC:将PC设置成下一条指令的地址。

二、SEQ硬件结构

1、取指:将程序计数器寄存器作为地址,指令存储器读取指令的字节。PC增加器计算valP,即增加了的程序计数器。

2、译码:寄存器文件有两个读端口A和B,从这两个端口同时读寄存器的值valA和valB。

3、执行:根据指令类型将算数/逻辑单元(ALU)用于不同的目的。条件码寄存器有三个条件码位,ALU负责计算条件码的新值,当执行跳转指令时会根据条件码和跳转类型来计算分支信号Cnd。

4、访存:数据存储器读出或写入一个存储器字。指令和数据存储器访问的是相同的存储器位置,但用于不同的目的。

5、写回:寄存器文件有两个写端口,E用来写ALU计算出来的值,M用来写从数据存储器中读出来的值。

三、SEQ的时序

四个硬件单元:

1、程序计数器

2、条件码寄存器

3、数据存储器

4.寄存器文件

它们通过一个时钟信号来控制。

Y86指令集的计算原则: 处理器从来不需要为了完成一条指令的执行而去读由该指令更新了的状态

四、SEQ阶段的实现

1、取指阶段,包括指令储存器硬件单元

2、译码和回写阶段

3、执行阶段,包括算数/逻辑单元

4、访存阶段,读或写程序数据

5、更新PC阶段

6、SEQ小结

五、实验运行结果

(1)构建YIS环境:

cd ~/Code/shiyanlou_cs413
wget http://labfile.oss.aliyuncs.com/courses/413/sim.tar
tar -xvf sim.tar
cd sim
sudo apt-get install tk
sudo ln -s  /usr/lib/x86_64-linux-gnu/libtk8.6.so /usr/lib/libtk.so
sudo ln -s  /usr/lib/x86_64-linux-gnu/libtk8.6.so /usr/lib/libtk.so
make

  

(2)测试教材P239代码asuml.ys,得到代码:

  | /* $begin code-yso */
  | /* $begin code-ysa */
  | # Execution begins at address 0
  | # This version uses a leave instruction
  0x000:  |     .pos 0
  0x000: 30f400040000 | init:   irmovl Stack, %esp      # Set up Stack pointer
  0x006: 30f500040000 |     irmovl Stack, %ebp      # Set up base pointer
  0x00c: 7024000000   |     jmp Main        # Execute main program
  | 
  | # Array of 4 elements
  0x014:  |     .align 4
  0x014: 0d000000 | array:  .long 0xd
  0x018: c0000000 |     .long 0xc0
  0x01c: 000b0000 |     .long 0xb00
  0x020: 00a00000 |     .long 0xa000
  | 
  0x024: 30f004000000 | Main:   irmovl $4,%eax
  0x02a: a00f |     pushl %eax  # Push 4
  0x02c: 30f214000000 |     irmovl array,%edx
  0x032: a02f |     pushl %edx  # Push array
  0x034: 803a000000   |     call rSum   # Sum(array, 4)
  0x039: 00   |     halt
  | 
  |     # int Sum(int *Start, int Count)
  0x03a: a05f | rSum:   pushl %ebp
  0x03c: 2045 |     rrmovl %esp,%ebp
  0x03e: 30f014000000 |     irmovl $20,%eax
  0x044: 6104 |     subl %eax,%esp
  0x046: a03f |     pushl %ebx
  0x048: 503508000000 |     mrmovl 8(%ebp),%ebx
  0x04e: 50050c000000 |     mrmovl 12(%ebp),%eax
  0x054: 6200 |     andl %eax,%eax
  0x056: 718b000000   |     jle L38
  0x05b: 30f2f8ffffff |     irmovl $-8,%edx
  0x061: 6024 |     addl %edx,%esp
  0x063: 30f2ffffffff |     irmovl $-1,%edx
  0x069: 6020 |     addl %edx,%eax
  0x06b: a00f |     pushl %eax
  0x06d: 30f204000000 |     irmovl $4,%edx
  0x073: 2030 |     rrmovl %ebx,%eax
  0x075: 6020 |     addl %edx,%eax
  0x077: a00f |     pushl %eax
  0x079: 803a000000   |     call rSum
  0x07e: 502300000000 |     mrmovl (%ebx),%edx
  0x084: 6020 |     addl %edx,%eax
  0x086: 708d000000   |     jmp L39
  0x08b: 6300 | L38:    xorl %eax,%eax
  0x08d: 5035e8ffffff | L39:    mrmovl -24(%ebp),%ebx
  0x093: d0   |     leave
  0x094: 90   |     ret
  | 
  0x400:  |     .pos 0x400
  0x400:  | Stack:  # The stack goes here
  | /* $end code-ysa */
  | /* $end code-yso */

  

六、遇到的问题

1、先是没有找到Y86模拟器安装入口

应该将sim得压缩包解压,最后成功连接Y86

七、参考来源

1、教材《深入理解计算机系统》

2、实验楼实验指导书《深入理解计算机系统》:https://www.shiyanlou.com/courses/413 实验五

3、Y86 Tools:http://csapp.cs.cmu.edu/2e/students.html

原文地址:https://www.cnblogs.com/bonjourvivi/p/4890021.html