信息安全程序设计基础第四周总结

第三章 程序的机器级表示

1.P104\P105

X86 寻址方式经历三代:

-DOS时代的平坦模式,不区分用户空间和内核空间,很不安全

-8086的分段模式

-IA32的带保护模式的平坦模式

2.P106

ISA:机器级程序的格式和行为,定义为指令集体系机构,它定义了处理器状态指令的格式,以及每条指令对状态的影响。

 机器级程序使用的存储器地址是虚拟地址,提供的存储器模型看上去是一个非常大的字符数组

PC:程序计数器。在IA32中,用%eip表示,指示将要执行的下一条指令在存储器中的地址。

程序存储器:包含程序的可执行机器代码,操作系统需要的一些信息,用来管理过程调用和返回的运行时栈,以及用户分配的存储器块。

3.P107

64位机上想得到32位代码:gcc -m32 -S xxx.c

编译并产生汇编目标文件xxx.o:gcc -O1 -c xxx.c

获得汇编代码:gcc -S xxx.c -o xxx.s

Ubuntu中获得汇编代码:gcc -S xxx.c更接近教材

教材中获得汇编代码:gcc -O1 -S xxx.c(编译器使用的事第一级优化)

 

4.P108

 二进制文件可用od命令查看,也可以用gdb的x查看:(gdb)x/17xb sum表示检查17个十六进制的字节;

 显示代码过多或过少可用more、less结合管道查看,也可以用输出重定向:

 od xxx.o | more

 od xxx.o > xxx.txt

5.P109

gcc -S 产生的汇编中可以把 以”.“开始的语句都删除了再阅读

 6.P110

 Linux和windows的汇编格式的区别:

 -Intel代码省略了指示大小的后缀,即'l'

 -Intel代码省略了寄存器名字前面的‘%’符号,用的是esp,而不是%esp

 -Intel代码用不同的方式来描述存储器中位置

 -在带有多个操作数的指令情况下,列出操作数的顺序相反

7.P111

 -db char 1

-dw short int 2

-dd int 或float 4

-dq long int 或 double 8

8.P112

-esi、edi可以用来操纵数组,esp、ebp用来操纵栈帧。

-通用寄存器中的eax,ebx,ecx,edx中,32位的eax,16位的ax,8位的ah,al都是独立的。例如:假定当前是32位x86机器,eax寄存器的值为0x8226,执行完addw $0x8266, %ax指令后eax的值是多少?

解析:0x8226+0x826=0x1044c, ax是16位寄存器,出现溢出,最高位的1会丢掉,剩下0x44c,不要以为eax是32位的不会发生溢出。

多数情况下,前6个寄存器为通用寄存器,最后两个寄存器保存着指向程序栈中重要位置的指针。

另外,字节操作指令可以独立的读或者写前4个寄存器的2个低位字节。

9.P113

操作数的三种类型:立即数(常数值)、寄存器(某个寄存器的内容)、存储器(根据计算出来的地址访问某个存储器位置)

-有效地址的计算方式 Imm(Eb,Ei,s) = Imm + R[Eb] + R[Ei]*s

 

10.P114

-MOV:相当于C语言的赋值“=”,将源操作数的值复制到目的操作数中;

 MOVS:将一个较小的源数据复制到一个较大的数据位置,高位用位扩展;

 MOVZ:将一个较小的源数据复制到一个较大的数据位置,高位用零扩展。

-push:把数据压入栈中;

 pop:删除数据。

11.P115\P116

 -栈顶元素的地址是所有栈中元素地址中最低的

-栈指针%esp保存栈顶元素的地址。

 

12.P117

 -指针就是地址

-局部变量保存在寄存器中

13.P119

按目的操作数分类:

第一类:加载有效地址。实际是将有效地址写入目的操作数,目的操作数必须是寄存器。

第二类:一元操作。操作数既是源又是目的。可以是寄存器也可以是存储器。

第三类:二元操作。第二个操作数既是源又是目的。但两个操作数不能同时是存储器。

第四类:移位操作。位移量是一个立即数或放在单字节寄存器%cl中。移位操作的目的操作数可以是一个寄存器或是一个存储器位置。

14.P123\P124

 有条件跳转(实现if,switch,while,for)

 无条件跳转jmp(实现goto)

 

15.P125

SET指令根据t=a-b的结果设置条件码

 16.P127

跳转指令(导致执行切换到程序中一个全新的位置,跳转的目的地通常用一个标号指明)

无条件跳转:JMP 可以是直接跳转也可以是间接跳转(写法是*后面加操作数指示符)

 有条件跳转:根据条件码的某个组合,或者跳转或者继续执行下一条指令

17.P130-P145

-条件分支——if-else结构:在两个分支语句中选择执行一个,汇编实现通过goto,就是汇编器为两个分支产生各自的代码块,它会插入条件和无条件分支,以保证能执行正确的代码块。

-循环结构——do-while、while、for:用条件测试和跳转组合实现循环的效果。大多数汇编器根据do-while形式来产生循环代码,其他的循环会首先转换成do-while形式,然后再编译成机器代码。

-switch语句:根据一个整数索引值进行多重分支。通过使用跳转表这种数据结构实现更加高效。跳转表是一个数组,表项i是一个代码段的地址,这个代码段实现当开关索引值为i时程序该做的。此时跳转可以用goto/jmp

18.P149

IA32通过程序栈来实现过程调用

19.P150\P151

call指令\ret指令

函数返回值存在%eax

 

 

20.P174

关于栈帧的gdb命令bt/frame/up/down

命令

描述

backtrace(或bt)            

查看各级函数调用及参数

finish

连续运行到当前函数返回为止,然后停下来等待命令

frame(或f) 帧编号

选择栈帧

info(或i) locals

查看当前栈帧局部变量的值

list(或l)

列出源代码,接着上次的位置往下列,每次列10行

list 行号

列出从第几行开始的源代码

list 函数名

列出某个函数的源代码

next(或n)

执行下一行语句

print(或p)

打印表达式的值,通过表达式可以修改变量的值或者调用函数

quit(或q)

退出gdb调试环境

set var

修改变量的值

start

开始执行程序,停在main函数第一行语句前面等待命令

step(或s)

执行下一行语句,如果有函数调用则进入到函数中    

break(或b) 行号             

在某一行设置断点                                                                       

break 函数名

在某个函数开头设置断点

break ... if ...

设置条件断点

continue(或c)

从当前位置开始连续运行程序

delete breakpoints

删除断点

display 变量名

跟踪查看某个变量,每次停下来都显示它的值

disable breakpoints

禁用断点

enable 断点号

启用断点

info(或i)breakpoints

查看当前设置了哪些断点

run(或r)

从头开始连续运行程序

undisplay 跟踪显示号

取消跟踪显示

watch                                  

设置观察点     

info(或i) watchpoints

查看当前设置了哪些观察点  

x

从某个位置开始打印存储单元的内容,全部当成字节来看,   

 而不区分哪个字节属于哪个变量

 

 

 

 

 

 

 

遇到的问题:

-当时学c语言时对if-else\do-while\while\for\switch掌握得就不好,现在还加上了汇编结构,以及有条件跳转和无条件跳转的使用

-CMP和SUB用在什么地方

 

posted @ 2015-10-11 16:53  20135326王亦可  阅读(489)  评论(1编辑  收藏  举报