这篇文章是用 x86-64 的架构作为例子,因为多数人的电脑是用 x86-64 的架构
只要依照 在linux中看gcc产生出来的组合语言 这篇文章
就可以把 C 语言的档案编议成 x86-64 的组合语言
编译时请记得加上 -Og
这个 flag ,因为较低的优化程度比较好观察 gcc
的行为
如上图,x86-64 共有 16 个 64-bit register ,(不过这张图并没有把 program counter
画上去)
以图中左上的 register 为例,
%rax
代表的是整个 64-bit ,
而写 %eax
时,代表的是较低位元的 32-bit
除了用红色标示的 %rsp
有特别的用途之外 (register stack pointer),
其他的 15 个 register 都算是 general purpose 的 register
这种状况是最简单的,考虑以下的 C 语言程序码:
void callee()
{
/*...
...*/
}
void caller()
{
/*...
...*/
callee();
/*...
...*/
}
编译成组合语言:
callee:
...
...
...
...
ret
caller:
...
...
call callee
...
...
call callee
这行代表让 program counter 指到 callee
的位置
ret
这行代表回到 call callee
的下一行继续执行
几乎就跟 C 语言的运作逻辑相同
回传值的过程大概可以列成以下步骤:
caller
呼叫 callee
callee
执行到最後面时,把回传值放到 %rax
里callee
执行 ret
回到 caller
继续执行caller
从 %rax
拿取回传值(因为 callee
已经把回传值放到%rax
了)透过 callee
把回传值放到 %rax
caller
从 %rax
拿取回传值的模式,
就成功的实作出 C 语言里 function 回传值的功能,
当然不用 %rax
用其他的 register 也可以
但习惯上就是会用 %rax
所以说 C 里的 return value 并不是用硬体来实作的行为,而是一种软件上的设计
考虑以下的 C 语言程序码:
long callee()
{
return -0x87;
}
long caller()
{
long result;
result = callee() + 1;
return result;
}
编译出的组合语言:
callee:
mov $0xffffffffffffff79,%rax
retq
caller:
callq callee
add $0x1,%rax
retq
传参数的方法跟传回传值的方法差不多
就跟回传时要约定好要用 %rax
来当中介一样
传参数也要约定好要用哪些 register 来中介:
第几个参数 | register |
---|---|
1 | %rdi |
2 | %rsi |
3 | %rdx |
4 | %rcx |
5 | %r8 |
6 | %r9 |
考虑以下的 C 语言程序码:
long callee(long a1, long a2, long a3, long a4, long a5, long a6)
{
return a1 + a2 + a3 + a4 + a5 + a6;
}
long caller()
{
long result, a1, a2, a3, a4, a5, a6;
a1 = -1;
a2 = -2;
a3 = -3;
a4 = -4;
a5 = -5;
a6 = -6;
result = callee(a1, a2, a3, a4, a5, a6) - 0x87;
return result;
}
编译出的组合语言:
callee:
add %rsi,%rdi
add %rdx,%rdi
add %rcx,%rdi
add %r8,%rdi
lea (%rdi,%r9,1),%rax (%rax = %rdi + %r9 * 1)
retq
caller:
mov $0xfffffffffffffffa,%r9 (two's complement)
mov $0xfffffffffffffffb,%r8
mov $0xfffffffffffffffc,%rcx
mov $0xfffffffffffffffd,%rdx
mov $0xfffffffffffffffe,%rsi
mov $0xffffffffffffffff,%rdi
callq 40 <caller+0x2f>
sub $0x87,%rax
retq
来不及发文了,这个就留到明天在说!
Computer Systems: A Programmer's Perspective, 3/E (CS:APP3e)
<<: Day1:第一天来点简单的先安装Parrot_Security
React 的核心之一是 JSX 语法, 这意味着整个网页内容,包含 HTML 与 CSS, 基本上...
包含基础设施、架构设计、资料采集(ETL)、主资料管理(MDM)、即时计算、资资料储存和作业排程等。...
专有名词 整理了我觉得该先了解的一些专有名词 wiki-物件导向程序设计、菜鸟式回答:是一种将资料,...
vue.js2.0後版本推荐使用axios来完成ajax请求 为Promise-based HTTP...
The Abstract Factory pattern provides an interface...