IA32 组装:lea 指令

Posted

技术标签:

【中文标题】IA32 组装:lea 指令【英文标题】:IA32 Assembly: lea instruction 【发布时间】:2013-11-02 15:36:20 【问题描述】:

我知道我要说的那句话可能是很快在 *** 上变得非常冷门的最好方法。无论如何我都会说:为什么这不起作用(完全)?

我试图弄清楚 lea/leal 指令的作用。我理解的方式是,lea/leal 找出第一个操作数的内存地址,并将该地址写入第二个操作数(可能是一个寄存器左右)。

这部分似乎有效。当我运行下面的程序时,它说:

The memory address of var is 134518204.

但是,在此之后,它会说“内存访问错误”之类的内容。 pushl (%eax) 显然不起作用。为什么不呢?

.data
    var:    .long 42
    str1:   .string "The memory address of var is %d.\n"
    str2:   .string "At this memory address we find var's value: %d.\n"

.text
.global main
main: 
    leal var, %eax          # Copy the address of var into %eax
    pushl %eax
    pushl $str1
    call printf             # Print str1
    pushl (%eax)
    pushl $str2
    call printf             # Print str2

    # Some stack cleaning should be here :)

    movl $1, %eax
    int $0x80

我什至不确定 lea/leal 所做的是否正确。帮助表示赞赏。 ;)

【问题讨论】:

movl src, dest 表示dest = srcleal src, dest 表示 dest = &src(即 dest = src 的地址) 更准确地说,movl 评估源,将其视为地址并将其内容移动到目标。但是,leal 评估源并将评估值移动到目标。 What's the purpose of the LEA instruction? 的可能重复项 【参考方案1】:

按照我的理解,lea/leal 找出第一个操作数的内存地址,并将这个地址写入第二个操作数(可能是一个寄存器左右)。

听起来足够准确。它用于执行地址运算;这可以像加载一个地址一样简单,但您也可以使用它来执行某些常数的乘法。


pushl (%eax) 显然不起作用。为什么不呢?

您的 push 指令没有引用您认为的地址:printf 返回写入的字符数,并且该值在 %eax 寄存器中返回,因此 %eax 不再包含var.

【讨论】:

非常感谢!实际上,我刚刚读到根据 C 调用约定,总是会更改 %eax。看来我真的需要一段时间做点别的事情......:D【参考方案2】:

lea 通常(ab)用于计算:如果您只想要寄存器中的全局地址,movl $var, %eaxlea 更清晰(并且短一个字节)。

另外,为了清楚起见,lea 的目标操作数必须是一个寄存器。

【讨论】:

非常感谢,也很有帮助!

以上是关于IA32 组装:lea 指令的主要内容,如果未能解决你的问题,请参考以下文章

两个 x86 IA32 ISA 指令之间的区别?

IA-32指令解析详解

IA-32汇编语言笔记—— 基础概念

Intel 64 and IA-32 Architectures Instruction Format 指令格式

IA-32汇编语言笔记——堆栈的作用

IA-32汇编语言笔记—— 分支程序设计