# 3.ISA

# 3.1AT&T 格式

长度后缀 b 表示操作数长度为 8 位;w 表示字,16 位;l 表示双字,32 位;q 表示 4 字,64 位
% eax 表示寄存器 eax 的内容 R[eax]
(% eax) 表示寄存器 eax 的内容所指向的存储单元 M[R[eax]]

# 3.2 寄存器组织和寻址方式

# 3.2.1 定点寄存器组

# 3.2.2 寻址方式

# 3.3IA-32 常用指令

# 3.3.1 传送指令

movb、movw、movl
movs:符号扩展传送指令 高位补符号
movz:0 扩展传送指令 高位补 0

lea:地址传送指令
mov 指令和 lea 指令的区别:mov 是对寄存器内容操作,而 lea 指令是传输操作数的地址

# 3.3.2 算术运算指令

add SRC DST ==> DST=DST+SRC
sub SRC DST ==> DST=DST-SRC
cmp SRC DST ==> DST-SRC

# 3.3.3 逻辑运算指令

andb $0xf,%al
orw $0x3,%bx
xorw $0x1,%bx
testb % al,% al 判断 al 是否为 0

# 3.3.4 条件转移指令

cmp B A
ja 判断 A>B 跳转

# 3.4 过程调用和栈帧

1
2
3
4
5
6
7
8
9
10
High Addresses
| ebp在上一栈帧的旧值 |
| 局部变量 | <--- -4(%ebp)
| 局部变量 | <--- -8(%ebp)
|-------------|
|参数n|
| 参数1 | ebp+8
| 返回地址 | <--- ebp+4
| ebp在当前栈帧的值 |
Low Addresses

返回值总是保存在 eax 中

# 3.5 循环结构的机器级表示

1
2
3
4
5
6
7
8
9
begin_expr;
c=cond_expr;
if(!c) goto done;
loop:
loop_body_statement;
update_expr;
c=cond_expr;
if(c) goto loop;
done:

# 3.6 逆向工程

根据汇编代码补充 c 语言代码

# 3.7 复杂数据类型的分配和访问

数组访问:(% edx,% ecx,4) -->&s [0]+4*i
指针数组:数组里面全部为指针类型
数组指针:指向数组的指针
数据的对齐:最大对齐方式的整数倍

# 3.8 越界访问和缓冲区溢出

越界访问(Out-of-Bounds Access):指的是在访问数组、指针或其他数据结构时,使用了超出其边界范围的索引或指针进行访问。这种访问可能会导致程序读取或修改无效的内存位置,破坏数据完整性,甚至导致崩溃或安全漏洞。

例如,如果有一个包含 10 个元素的数组,但是访问该数组的第 11 个元素,或者使用一个指针指向数组末尾后的下一个元素,那么就发生了越界访问。

缓冲区溢出(Buffer Overflow):是一种特定类型的越界访问,指的是向一个缓冲区写入超过其容量的数据,导致溢出。当程序试图向缓冲区写入更多数据时,超出缓冲区的边界,数据可能会覆盖到相邻的内存区域。这可能会导致数据损坏、程序崩溃或者利用该漏洞进行恶意攻击。

缓冲区溢出通常发生在使用 C/C++ 等语言编写的程序中,特别是在处理字符串或者用户输入时。例如,如果一个字符数组作为字符串的缓冲区,而没有适当的边界检查,输入的字符串超过缓冲区的大小,就会导致缓冲区溢出。

虽然越界访问和缓冲区溢出有一定的关联,但越界访问不一定导致缓冲区溢出,而缓冲区溢出是一种特殊情况的越界访问,涉及到对缓冲区的写入操作。缓冲区溢出是一种常见的软件漏洞,可能会被恶意利用,因此在编程中需要特别注意边界检查和缓冲区大小的控制,以避免越界访问和缓冲区溢出问题的发生。