mov指令和寄存器 - 混乱!

new*_*int 10 assembly

我正在阅读"计算机系统:程序员视角",第3章解释mov说明,书中的解释让我感到困惑.

提供功能(第142页1版)

int exchange( int *xp, int y)
{
    int x = *xp;
    *xp = y;
    return x;
} 
Run Code Online (Sandbox Code Playgroud)

函数体的汇编代码

movl 8(%ebp), %eax  //Get xp  
movl 12(%ebp), %edx //Get y  
movl (%eax), %ecx   //Get x at *xp  
movl %edx, (%eax)   //Store y at *xp  
movl %ecx, %eax     //Set x as return value
Run Code Online (Sandbox Code Playgroud)

令我困惑的是,将要存储的是什么,以及
我在何处理解这一点:

movl 8(%ebp), %eax  //Get xp  
Run Code Online (Sandbox Code Playgroud)

CPU在堆栈中向上移动+8个字节(从帧指针%ebp),获取存储在该位置的值,并将该值存储在寄存器中%eax(强调 - 存储值,而不是地址)

我是对的 ?谢谢 !

use*_*379 14

是的,听起来你说得对.恕我直言,AT&T 8(%ebp)语法不如英特尔更直观[ebp+8],更明确.括号显示您正在使用寄存器中地址的值,该数字是您实际需要的地址的偏移量.

  • 所以换句话说,因为%ebp存储指针,所以我们在它的名称周围使用括号,以指定我们将存储的值从%ebp移了8个字节。在这种情况下,`8(%ebp)`包含指针`* xp`。稍后,在行`movl(%eax),%ecx`中,我们以与汇编代码第一行中相同的方式取消对`xp`的引用。 (2认同)

eld*_*his 5

是的,这是使用 AT&T 语法,其形式如下:

instruction     source, dest
Run Code Online (Sandbox Code Playgroud)

英特尔组装是相反的顺序

8(%ebp)从帧指针向上移动 8 个字节也是正确的。具体而言,它移动 8 个字节的原因是因为参数以相反的顺序(在查看典型函数调用时从“右”到“左”)压入堆栈。因此,y首先推送,然后xp最后推送调用者函数的返回地址(这就是您移动 8 个字节而不是 4 个字节的原因)。