我是靠谱客的博主 眯眯眼花生,这篇文章主要介绍从汇编语言层次追踪c代码的执行过程(return 的研究),现在分享给大家,希望可以做个参考。

简单的hello world之前已分析过,这次分析return ,问题来源于points on c。
知道c函数中的返回值是通过eax寄存器返回的。对应的c就是 return a,但是,如果c代码就是return呢
实验一下

复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
gff@ubuntu:~/cplusplus/return$ cat retn.c #include<stdio.h> int back(int a,int b) { int x; x=a+b; return; } int main() { int s; s=back(1,2); printf("s=%dn",s); return 0; }
复制代码
1
2
3
4
gcc retn.c -o retn gff@ubuntu:~/cplusplus/return$ ./retn s=3

如何这样,难道return隐式就是返回eax的值?
将back函数中return去除,
同样能正确返回数值
首先将c编译程汇编代码

复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
back: .LFB0: pushl %ebp movl %esp, %ebp subl $16, %esp movl 12(%ebp), %eax movl 8(%ebp), %edx addl %edx, %eax movl %eax, -4(%ebp) leave ret .LC0: .string "s=%dn" .text .globl main .type main, @function main: pushl %ebp movl %esp, %ebp andl $-16, %esp subl $32, %esp movl $2, 4(%esp) movl $1, (%esp) call back movl %eax, 28(%esp) movl $.LC0, %eax movl 28(%esp), %edx movl %edx, 4(%esp) movl %eax, (%esp) call printf movl $0, %eax leave ret

下面是将return加上的汇编代码

复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
back: .LFB0: pushl %ebp movl %esp, %ebp subl $16, %esp movl 12(%ebp), %eax movl 8(%ebp), %edx addl %edx, %eax movl %eax, -4(%ebp) leave ret .LC0: .string "s=%dn" .text .globl main .type main, @function main: .LFB1: pushl %ebp movl %esp, %ebp andl $-16, %esp subl $32, %esp movl $2, 4(%esp) movl $1, (%esp) call back movl %eax, 28(%esp) movl $.LC0, %eax movl 28(%esp), %edx movl %edx, 4(%esp) movl %eax, (%esp) call printf movl $0, %eax leave ret

下面是修改为 return x;的汇编代码

复制代码
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
back: .LFB0: .cfi_startproc pushl %ebp movl %esp, %ebp subl $16, %esp movl 12(%ebp), %eax movl 8(%ebp), %edx addl %edx, %eax movl %eax, -4(%ebp) movl -4(%ebp), %eax leave ret .LFE0: .size back, .-back .section .rodata .LC0: .string "s=%dn" .text .globl main .type main, @function main: .LFB1: pushl %ebp movl %esp, %ebp andl $-16, %esp subl $32, %esp movl $2, 4(%esp) movl $1, (%esp) call back movl %eax, 28(%esp) movl $.LC0, %eax movl 28(%esp), %edx movl %edx, 4(%esp) movl %eax, (%esp) call printf movl $0, %eax leave ret

比较这三种情况发现eax的值都是一样的,其实这与c样式函数的返回值的规定不矛盾,
eax作为两个作用
1、计算时的临时存储变量
2、在函数返回时,作为传递返回值的寄存器
如果 在return之前加入表达式,以此改变eax的值,那么返回值就被改变了

最后

以上就是眯眯眼花生最近收集整理的关于从汇编语言层次追踪c代码的执行过程(return 的研究)的全部内容,更多相关从汇编语言层次追踪c代码的执行过程(return内容请搜索靠谱客的其他文章。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(71)

评论列表共有 0 条评论

立即
投稿
返回
顶部