Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/assembly/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 这个问题与汇编代码有关,我不知道;我不理解为什么最初被调用方保存的寄存器值被推入堆栈_C_Assembly_X86_X86 64 - Fatal编程技术网

C 这个问题与汇编代码有关,我不知道;我不理解为什么最初被调用方保存的寄存器值被推入堆栈

C 这个问题与汇编代码有关,我不知道;我不理解为什么最初被调用方保存的寄存器值被推入堆栈,c,assembly,x86,x86-64,C,Assembly,X86,X86 64,上面的代码来自CSAPP第3.7.5节,我想知道为什么在汇编代码中,它需要将%rbp和%rbx推入堆栈,因为它说x和y分别在%rdi和%rsi中,那么%rbp和%rbx中会有什么值。在书中,它描述为“保存来自%rbp和%rbx的值,但它保存的值确实令人困惑,我目前的猜测是,如果%rbp和%rbx不包含任何值,那么pushq会将两个地址推入内存,然后,对这两个寄存器的任何更改都将在堆栈中自动更新rbp和rbx都是被调用方保存的寄存器。被调用方在返回时必须保留其内容。调用P的用户希望这些寄存器被调用

上面的代码来自CSAPP第3.7.5节,我想知道为什么在汇编代码中,它需要将%rbp和%rbx推入堆栈,因为它说x和y分别在%rdi和%rsi中,那么%rbp和%rbx中会有什么值。在书中,它描述为“保存来自%rbp和%rbx的值,但它保存的值确实令人困惑,我目前的猜测是,如果%rbp和%rbx不包含任何值,那么pushq会将两个地址推入内存,然后,对这两个寄存器的任何更改都将在堆栈中自动更新

rbp和rbx都是被调用方保存的寄存器。被调用方在返回时必须保留其内容。调用
P
的用户希望这些寄存器被调用保留。因此,这些寄存器中的值属于调用链更上层的调用方。@ErikEidt感谢您的帮助,那么这是否意味着只有当另一个函数调用它时,两个步骤(第2-3行)才起作用?和%rbp,%rbx包含来自前一个调用方的数据?我不确定“仅当另一个函数调用它时才工作”是什么意思。这个函数
P
被调用的唯一方式就是当另一个函数调用它时。CPU无法自发地开始执行此函数的代码。因此,总是需要推送和弹出被调用方保存的寄存器-是的,它们包含前一个调用方在其中输入的任何值(如果有)。可能是前一个调用者没有使用这些寄存器,在这种情况下,它们仍然包含来自“祖父母”调用者的值,而“祖父母”调用者同样希望保留这些值。Related:,还解释了为什么像“callee saved”这样的名称很难理解,以及为什么“call preserved”与“call clobbed”之间存在差异用一种明智的方式来思考它们。
(a) Calling function
long P(long x, long y)
{
   long u = Q(y);
   long v = Q(x);
   return u + v;
}

(b) Generated assembly code for the calling function
long P(long x, long y)
x in %rdi, y in %rsi

1 P:
2 pushq %rbp       \\Save %rbp
3 pushq %rbx        \\Save %rbx
4 subq $8, %rsp     \\Align stack frame
5 movq %rdi, %rbp   \\Save x
6 movq %rsi, %rdi   \\Move y to first argument
7 call Q Call Q(y)
8 movq %rax, %rbx   \\Save result
9 movq %rbp, %rdi   \\Move x to first argument
10 call Q           \\Call Q(x)
11 addq %rbx, %rax  \\Add saved Q(y) to Q(x)
12 addq $8, %rsp    \\Deallocate last part of stack
13 popq %rbx        \\Restore %rbx
14 popq %rbp        \\Restore %rbp
15 ret