首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >关于[base + index*scale + disp]和AT&T disp(基本,索引,刻度)的几个问题

关于[base + index*scale + disp]和AT&T disp(基本,索引,刻度)的几个问题
EN

Stack Overflow用户
提问于 2015-01-14 05:08:01
回答 1查看 13K关注 0票数 21

Intel和AT&T语法中内存寻址的一般形式如下:

代码语言:javascript
复制
[base + index*scale + disp]      # Intel, including GAS .intel_syntax noprefix
disp(base, index, scale)         # AT&T

我的问题如下:

  • baseindex可以注册吗?
  • scale可以接受哪些值,是1、2、4和8(1是默认值)?
  • indexdisp是否可以互换(唯一的区别是index是寄存器,而disp是即时值)?
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2015-01-14 06:51:27

英特尔的手册中描述了这一点:

3.7.5指定偏移量 内存地址的偏移部分可以直接指定为静态值(称为位移),也可以通过由以下一个或多个组件组成的地址计算来指定:

  • 位移-一个8-,16-或32位值.
  • Base -通用寄存器中的值.
  • 索引-通用寄存器中的值.不能是ESP/RSP
  • 刻度因子-乘以索引值的值为2、4或8。

由于添加这些组件而产生的偏移量称为有效地址。

缩放因子被编码为2位移位计数(0, 1,2,3),对于1,2,4或8的比例尺因子。

在AT&T语法中,它的disp(base, index, scale)常量在父类之外。一些英特尔语法汇编程序也允许像1234[ebx]这样的语法,而另一些则不允许。但是AT&T语法是僵化的,寻址模式的每一个组件都只能在适当的位置。例如:

代码语言:javascript
复制
movzwl  foo-0x10(,%edx,2), %eax

从地址foo-0x10 + edx*2将零扩展16位("word")加载到EAX中。EDX是索引寄存器,具有缩放因子2,没有基寄存器.foo-0x10都是位移的一部分,都是链接时间常数.foo是一个符号地址,链接器将填写该地址并从中减去0x10 (因为-0x10组装时间偏移)。

如果您有选择,只使用一个基,而不是一个标度为1的索引。索引需要一个SIB字节来编码,从而使指令更长。这就是为什么编译器选择像8(%ebp)这样的寻址模式来访问堆栈内存,而不是8(,%ebp)

有关何时可以使用基、和/或索引和/或置换的更多信息,请参见Referencing the contents of a memory location. (x86 addressing modes)

16位位移量只有在16位寻址模式下才能编码,这种模式使用的different format不能包含缩放因子,并且具有非常limited selection of which registers可以作为基或索引。

因此,像1234(%edx)这样的模式必须在32位机器代码中将1234编码为32位disp32

字节偏移从-128 ..。+127可以使用短格式8位编码.您的汇编程序将为您处理这一点,使用最短的有效编码的位移。

对于64位寻址模式,所有这些在64位模式下都是相同的,disp32也被符号扩展到64位,就像disp8一样。

64位模式确实添加了一种新的不同的寻址模式,即symbol(%rip),它不适用于任何通用寄存器,只与RIP相距32位。请参阅https://stackoverflow.com/questions/54745872/how-do-rip-relative-variable-references-like-rip-a-in-x86-64-gas-intel-sy,它也涉及AT&T语法。

票数 16
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/27936196

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档