引用和宏定义的汇编实现

引用的实现实质上跟指针是一样的,如下:

//------------------------------------------------

#include <iostream>

using namespace std;

int main()
{
 int a = 3;
 int &ref_a = a;

 ref_a += 2;
 return 0;
}

//-----------------------------------------------

 

1:    #include <iostream>
2:
3:    using namespace std;
4:
5:    int main()
6:    {
00401030 55                   push        ebp
00401031 8B EC                mov         ebp,esp
00401033 83 EC 48             sub         esp,48h
00401036 53                   push        ebx
00401037 56                   push        esi
00401038 57                   push        edi
00401039 8D 7D B8             lea         edi,[ebp-48h]
0040103C B9 12 00 00 00       mov         ecx,12h
00401041 B8 CC CC CC CC       mov         eax,0CCCCCCCCh
00401046 F3 AB                rep stos    dword ptr [edi]
7:        int a = 3;
00401048 C7 45 FC 03 00 00 00 mov         dword ptr [ebp-4],3  ; a存储在内存中的[ebp-4]处,初值为3
8:        int &ref_a = a;
0040104F 8D 45 FC             lea         eax,[ebp-4]   ; 取[ebp-4]地址给eax,(ref_a = &a)
00401052 89 45 F8             mov         dword ptr [ebp-8],eax  ; 将此地址值保存在[ebp-8]处,作为ref_a的内容(也就是其所指向的变量的地址)
9:
10:       ref_a += 2;
00401055 8B 4D F8             mov         ecx,dword ptr [ebp-8]  ; 地址赋给ecx
00401058 8B 11                mov         edx,dword ptr [ecx]  ; 取ecx中保存的地址处的值赋给edx(也就是a的值)
0040105A 83 C2 02             add         edx,2    ; 加2
0040105D 8B 45 F8             mov         eax,dword ptr [ebp-8]  ; 将a的地址赋给eax (eax = &a)
00401060 89 10                mov         dword ptr [eax],edx  ; 把计算结果保存到a的地址空间处,实现了对a的改变
11:       return 0;
00401062 33 C0                xor         eax,eax
12:   }

---------------------------------------------

 

观察宏的反汇编代码


//---------------------------------------------

#include <stdio.h>

#define CMP(x,y) ( (x) > (y) ? 1 : -1)

int main()
{
    int r = CMP(2,1+2);
    printf("%d/n", r);

 return 0;
}

//-----------------------------------------------

$gcc -O2 -S macro_disasm.c
GCC优化编译后:

 .file "macro_disasm.c"
gcc2_compiled.:
___gnu_compiled_c:
.text
LC0:
 .ascii "%d/12/0"
 .p2align 2
.globl _main
_main:
 pushl %ebp
 movl %esp,%ebp
 subl $8,%esp
 addl $-8,%esp
 pushl $-1 ; 居然直接在汇编代码中显示结果-1
 pushl $LC0
 call _printf
 xorl %eax,%eax
 movl %ebp,%esp
 popl %ebp
 ret

 

$gcc -S macro_disasm.c

不用优化编译:

 .file "macro_disasm.c"
gcc2_compiled.:
___gnu_compiled_c:
.text
LC0:
 .ascii "%d/12/0"
 .p2align 2
.globl _main
_main:
 pushl %ebp
 movl %esp,%ebp
 subl $24,%esp
 movl $-1,-4(%ebp) ; 仍然直接将结果-1放入内存
 addl $-8,%esp
 movl -4(%ebp),%eax ; 读出结果-1,进栈
 pushl %eax
 pushl $LC0
 call _printf
 addl $16,%esp
 xorl %eax,%eax
 jmp L2
 .p2align 4,,7
L2:
 movl %ebp,%esp
 popl %ebp
 ret


宏在编译过程中就被编译器直接替换,不生成额外的执行代码。
 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值