x86-64 汇编基础 ---- 记读 《CS: APP》

x86-64 汇编基础 ---- 记读 《CS: APP》

通常情况下, 使用现代的优化编译器产生的代码至少与一个熟练的汇编语言程序员手工编写的代码一样有效


1. 看懂汇编码

1). 汇编码的格式

· ATT格式

这是GCC/ OBJDUMP和其它一些工具的常用格式, 由AT&T公司命名

使用命令gcc -S <file.c>输出的汇编码就是这种格式.

一段示例代码如下所示:

        movl    (%rdi), %eax
        imull   %eax, %eax
        movl    %eax, (%rdi)
        ret

在《CS: APP》一书中, 使用ATT格式书写汇编码, 因此, 无特殊说明时, 下文的所有汇编码也是ATT格式.

· Intel格式

Intel和Microsoft的文档中经常会出现这种格式的代码, 它个ATT格式的代码有些许不同, 如下示例:

        mov     eax, DWORD PTR [rdi]
        imul    eax, eax
        mov     DWORD PTR [rdi], eax
        ret

使用命令gcc -S -masm=intel <file.c>以输出这种格式的代码

Introduction to x64 Assembly | Intel® Software

注意, 上述代码中的源操作数和目的操作数的位置发生了变化, 因此在分析代码时应注意汇编码的格式问题.

使用GCC编译器输出的汇编码中, 以 “.” 开头的行是 伪指令 , 可以适当忽略.

2) 数据格式

在C语言中, 变量具有其"数据类型", 但是汇编码中的"变量"没有此概念(或者说, 没有"变量"的概念). 但是C语言中数据类型的概念在汇编语言中必须有与其相对应的机制, 在x86-64汇编中, 控制指令操作数的长度, 与C语言中的数据类型概念对应.

下表是摘自书中的C语言数据类型在x86-64中的大小:

C声明 Intel 数据类型 汇编代码后缀 大小(字节)
char 字节 b 1
short w 2
int 双字 l 4
long 四字 q 8
char * 四字 q 8
float 单精度 s 4
double 双精度 l 8

在汇编码(ATT格式)中, 通过在指令后加"后缀"表明操作数的大小. (后缀见上表)

3) 操作数指示符

几乎每一条指令都有对应的操作数, 操作数的值有几种形式: 立即数/ 寄存器/ 内存, 其中, 立即数和寄存器可以直接参与运算, 但存放于内存中的数参与运算时, 需要访存操作(此时立即数或寄存器中的值是内存地址).

最完整的一种地址形式是 I m m ( r a , r i , s ) Imm(r_a, r_i, s) Imm(ra,ri,s) , 它的运算后有效地址为 I m m + R [ r a ] + R [ r i ] ⋅ s Imm + R[r_a] + R[r_i] \cdot s Imm+

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值