或许有人对这话题不屑,return 语句不就返回一个值吗?有什么好讨论的,好理解.
非也,非也.探讨return 语句的初衷是对返回值的存放存在疑惑.
下面开始探讨之路.什么东西都是从简单到复杂.从简单开始:
测试程序如下:
- //VC 6.0 调试
- #include <iostream>
- using namespace std;
- int Test(void)
- {
- return 3;
- }
- int main()
- {
- int b=Test();//此处下断点
- return 0;//此处下断点
- }
按F5调试.VIEW->DEBUG WINDOWS下选中 register ,watch,disassembly,memory窗口.进行观察.
- 11: int b=Test();
- 00401078 call @ILT+0(Test) (00401005) //跟进去
- 0040107D mov dword ptr [ebp-4],eax
- @ILT+0(?Test@@YAHXZ):
- 00401005 jmp Test (00401030)//跟进去,呵呵我是不明白为什么要多这条指令
- //希望高手指点
- push ebp
- 00401031 mov ebp,esp
- 00401033 sub esp,40h
- 00401036 push ebx
- 00401037 push esi
- 00401038 push edi
- 00401039 lea edi,[ebp-40h] //让 edi存 栈的一块40h大小的内存区首地址 不知道操作系统为什么这么做
- 0040103C mov ecx,10h //注意 10h*4=40h
- 00401041 mov eax,0CCCCCCCCh
- 00401046 rep stos dword ptr [edi] / /把 40h大小的内存初始化为CC .......
- 6: return 3;
- 00401048 mov eax,3 //把 3放入eax可见 返回值放在eax中.
- 7: }
- 0040104D pop edi
- 0040104E pop esi
- 0040104F pop ebx
- 00401050 mov esp,ebp
- 00401052 pop ebp //此处esp指向栈中存放EIP的值的地址
- 00401053 ret
- 0040107D mov dword ptr [ebp-4],eax //可见返回值通过EAX传到了外一层函数中.
现在我们看这个程序的全貌.
-
- 1: #include <iostream>
- 2: using namespace std;
- 3:
- 4: int Test(void)
- 5: {
- 00401030 push ebp
- 00401031 mov ebp,esp
- 00401033 sub esp,40h
- 00401036 push ebx
- 00401037 push esi
- 00401038 push edi
- 00401039 lea edi,[ebp-40h]
- 0040103C mov ecx,10h
- 00401041 mov eax,0CCCCCCCCh
- 00401046 rep stos dword ptr [edi]
- 6: return 3;
- 00401048 mov eax,3
- 7: }
- 0040104D pop edi
- 0040104E pop esi
- 0040104F pop ebx
- 00401050 mov esp,ebp
- 00401052 pop ebp
- 00401053 ret
- 9: int main()
- 10: {
- 00401060 push ebp
- 00401061 mov ebp,esp
- 00401063 sub esp,44h
- 00401066 push ebx
- 00401067 push esi
- 00401068 push edi
- 00401069 lea edi,[ebp-44h]
- 0040106C mov ecx,11h
- 00401071 mov eax,0CCCCCCCCh
- 00401076 rep stos dword ptr [edi]
- 11: int b=Test();
- 00401078 call @ILT+0(Test) (00401005)
- 0040107D mov dword ptr [ebp-4],eax //此处分析可得,eax
- //存到最接近的外层函数栈那块44h的内存块中.
- 12: return 0;
- 00401080 xor eax,eax
- 13: }
- 00401082 pop edi
- 00401083 pop esi
- 00401084 pop ebx
- 00401085 add esp,44h
- 00401088 cmp ebp,esp
- 0040108A call __chkesp (00408170)
- 0040108F mov esp,ebp
- 00401091 pop ebp
- 00401092 ret
结论:eax为返回值的临时变量.