2017-2018-1 20155318 《信息安全系统设计基础》第五周学习总结
教材学习内容总结
本周学习了第三章程序的机器级表示,教材学习内容如下:
- ISA(指令集体系结构):机器级程序的格式和行为,定义处理器状态、指令的格式以及每条指令对状态的影响
- 编译处理过程指令
- C预处理器插入宏和头文件:
gcc -E xxx.c -o xxx.i
- 编译器产生源代码的汇编代码:
gcc -S xxx.i -o xxx.s
- 汇编器化成二进制目标代码:
gcc -c xxx.s -o xxx.o
- 链接器生成最终可执行文件:
gcc xxx. -o xxx
- 反汇编
objdump -d xxx.o -o xxx.s
- 建立函数调用栈帧的汇编代码:
pushl %ebp 将寄存器%ebp中的内容压入程序栈
movl %esp,%ebp 将%ebp中的内容放入寄存器%esp
......
popl %ebp 寄存器%ebp中内容出栈
ret 返回结果
- ATT格式和Intel格式区别(Linux和Windows下汇编格式区别)
- Intel代码省略了指示大小的后缀。我们看到指令mov,而不是movl。
- Intel代码省略了寄存器名字前面的‘%’符号。用的是esp,而不是%esp。
- Intel代码用不同的方式来描述存储器中位置。
- 64位机器得到32代码指令:
gcc -m32 -S xxx.c
- 寄存器
- 一个IA32中央处理单元(CPU)包含一组8个存储32位值的寄存器。用来存储整数数据和指针,分别是
指令 | 寄存器 |
---|---|
%ax (%ah %al) | 通用寄存器 |
%cx (%ch %cl) | 通用寄存器 |
%dx (%dh %dl) | 通用寄存器 |
%bx (%bh %bl) | 通用寄存器 |
%si | 用来操纵数组 |
%di | 用来操纵数组 |
%sp | 操纵栈帧 |
%bp | 操纵栈帧 |
- 注意对于32位的eax,16位的ax,8位的ah,al都是独立的
- 寻址方式:
- 立即数寻址方式:操作数为常数值,写作$后加一个整数。
- 寄存器寻址方式:操作数为某个寄存器中的内容。
- 存储器寻址方式:根据计算出来的地址访问某个存储器的位置。
- 寻址模式:一个立即数偏移Imm,一个基址寄存器Eb,一个变址寄存器Ei,一个比例因子s(必须为1,2,4,8)有效地址计算为:Imm(Eb,Ei,s) = Imm + R[Eb] + R[Ei]*s
- mov S,D S中的字节传送到D中
9.push和pop:
pushl S R[%esp] ← R[%esp]-4,M[R[%esp]] ← S
popl D D ← M[R[%esp]],R[%esp] ← R[%esp]+4
10.标志
标志 | 用途 |
---|---|
CF | 进位标志,最近操作使高位产生进位,用来检测无符号操作数的溢出 |
ZF | 零标志,最近操作得出的结果为0 |
SF | 符号标志,最近操作得到的结果为负数 |
OF | 溢出标志,最近操作导致一个补码溢出-正溢出或负溢出。 |
-
栈帧结构:为单个过程分配的栈叫做栈帧,寄存器
%ebp
为帧指针,寄存器指针%esp
为栈指针,程序执行时栈指针移动,大多数信息的访问都是相对于帧指针。栈向低地址方向增长,而栈指针%esp指向栈顶元素。 -
转移控制
- call:目标是指明被调用过程起始的指令地址,效果是将返回地址入栈,并跳转到被调用过程的起始处。
- ret:从栈中弹出地址,并跳转到这个位置。函数返回值存在%eax中
- 栈帧的gdb命令
- backtrace/bt:打印当前的函数调用栈的所有信息。后面加n或-n表示打印栈顶上n层(或者下n层)的栈信息。
- frame n:n为栈中的层编号,从0开始,类似C语言中数组的下标。移动到n指定的栈帧中去,并打印选中的栈的信息。如果没有n,则打印当前帧的信息。
- up n:表示向栈的顶移动n层。
- down n:表示向栈底移动n层。
教材学习中的问题和解决过程
-
问题1:leaq指令的运用
-
问题1解决方案:
-
在编译课本129页代码时产生了scale.s的文件,其中有三条leaq指令
-
查询了加载有效地址leaq指令的用途:从内存读取数据到寄存器,可以执行加法和乘法,如
leaq7(%rdx,%rdx,4)
是7+(x+4x)
的意思
代码调试中的问题和解决过程
- 问题1:调试运行mstore
- 解决方案:
- 用-S产生汇编代码.s文件,用-c产生目标代码.o文件。用ls命令查看
-
用objdump -d xxx.o指令得到反汇编结果
-
将C语言文件编译成可执行文件并查看可执行文件的二进制内容
-
生成可执行文件prog
代码托管
上周考试错题总结
- 下面和代码可移植性相关的C语言属性有()
- A .#define
- B .typedef
- C .sizeof()
- D .union
- 答案: A B C
- 解析:#define可以定义宏使得变量可移植,typedef可以使得类型可移植,sizeof()使得不同类型长度可移植。
- int x; x的二进制为[10010101], x>>4的值为()
- A .[10010101]
- B .[00001001]
- C .[11111001]
- D .[01010000]
- 答案: C
- 解析:x是有符号数,有符号数右移补1!
结对及互评
点评模板:
- 博客中值得学习的或问题:
- xxx
- xxx
- ...
- 代码中值得学习的或问题:
- xxx
- xxx
- ...
- 其他
本周结对学习情况
- [20155227](http://www.cnblogs.com/guyanlin/p/7709615.html)
其他(感悟、思考等)
本周学习的第三张主要是汇编知识,之前汇编语言学的比较浅,所以算是在查漏补缺。
学习进度条
代码行数(新增/累积) | 博客量(新增/累积) | 学习时间(新增/累积) | 重要成长 | |
---|---|---|---|---|
目标 | 5000行 | 30篇 | 400小时 | |
第一周 | 0/0 | 1/1 | 3/3 | |
第二周 | 100/100 | 1/2 | 3/6 | |
第三周 | 300/400 | 1/3 | 4/10 | |
第四周 | 0/400 | 1/4 | 2/12 | |
第五周 | 25/425 | 1/5 | 4/16 |
尝试一下记录「计划学习时间」和「实际学习时间」,到期末看看能不能改进自己的计划能力。这个工作学习中很重要,也很有用。
耗时估计的公式
:Y=X+X/N ,Y=X-X/N,训练次数多了,X、Y就接近了。
-
计划学习时间:5小时
-
实际学习时间:4小时
-
改进情况:
(有空多看看现代软件工程 课件
软件工程师能力自我评价表)