[教程]逆向反汇编第六课

既然要玩逆向,驱动那我们就算不懂但至少要了解下C/C++语言,C++是一门支持OO的语言,对面想对象的软件开发提供了丰富的支持库.但要高效 正确的使用C++中的继承 多态等语言的特性,必须对这些特性性的底层实现有一定得了解.

    其实就核心概念而言,C++的对象模型的核心概念并不多,但最核心的是虚函数.虚函数是在程序运行时刻定义的函数,虚函数的地址是不能在编译时刻确定的,它只能在调用即将进行之前加以确定.对所有虚函数引用通常放在一个专用数组--虚函数表中,每个至少使用一个虚函数的对象里面都具有虚函数表指针.虚函数通常通过指向虚函数表的指针间接的加以调用.

    将实例的普通成员改编为虚函数调用,来看看VC在虚函数上面是如何处理的.

 

  1. class CSum    
  2. {    
  3.     public:    
  4.     virtual int Add(int a,int b)    
  5.     {    
  6.         return (a+b);    
  7.     }    
  8.     virtual int Sub(int a,int b)    
  9.     {    
  10.     return (a-b);    
  11.     }    
  12. };    
  13. void main()    
  14. {    
  15.     CSum* pCSum =new CSum;    
  16.     pCSum->Add(1,2);    
  17.     pCSum->Sub(1,2);    
  18. }   

 

这是C的一个简单代码,我们看反汇编后的代码是如何的样式,

 

  1.     push    esi    
  2.     push    4    
  3.     call    00401060    
  4.     add        esp,4            ;为新建对象实力分配4字节内存    
  5.    test    eax,eax    
  6.     je        short 00401019    
  7.     mov        dword ptr [eax],4050A0    ;将4050A0h写入创建的对象实例中4050A0h是CSum类虚函数表的指针,表中的元素是CSum类的虚函数,他们指向CSum函数的成员    
  8.    mov        esi,eax            ;esi是4050A0hCSum类虚函数表的指针    
  9.    jmp        short 0040101B    
  10.     xor        esi,esi            ;用NULL指向对象实例指针,该分支在内存分配失败才会来到,空指针将激活SEH    
  11. 0040101B:    
  12.     mov        eax,dword ptr [esi]        ;eax=**Add[]    
  13.     push    2    
  14.     push    1    
  15.     mov        ecx,esi            ;ecx=this    
  16.     call    dword ptr [eax]            ;对虚函数的调用,此时eax=**Add(),也就是CALL 401040    
  17.     mov        edx,dword ptr [esi]    
  18.     push    2    
  19.     push    1    
  20.     mov        ecx,esi    
  21.     call    dword ptr [edx+4]    
  22.     pop        esi    
  23.     retn   

 

这段代码首先调用new函数分配class所需内存,调用成功后,eax保存了分配的内存指针,然后将对象实例指向CSum类虚函数表4050A0h.
    VTBL里有两组数据
   [VTBL]=401040h
    [VTBL+4]=401050h

    进一步看看这两个指针是什么内容,

    ;401040h内容如下:Add函数

 

  1. mov        eax,dword ptr [esp+8]    
  2.  mov        ecx,dword ptr [esp+4]    
  3.  add        eax,ecx    
  4.  retn    8   

 

401050h函数如下:Sub 函数

 

  1. mov        eax,dword ptr [esp+4]    
  2.  mov        ecx,dword ptr [esp+8]    
  3.  sub        eax,ecx    
  4.  retn  8   

 

原来虚函数是通过浙西iangxuhanshubiaode指针间接地加以调用的,程序仍然使用ecx作为this指针的载体传递给虚成员函数,并且利用两次间接寻址,得到虚函数的正确地址,从而执行

 

  1. mov        eax,dword ptr [esi]        ;eax=*指针=**Add()    
  2.  push    2    
  3.  push    1    
  4.  mov        ecx,esi                                ;ecx=this    
  5.  call    dword ptr [eax]  
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值