zoukankan      html  css  js  c++  java
  • 转:虚拟方法跳过父类继承调用祖父类的代码 --值得试一试

    网友说是 hack 手段,还没有时间深入了解,不明觉厉。

    [沪]风舞轻扬(81924320) 2016-10-25 16:59:08

    TGrandpaObject = class
    public
      procedure AVirtualMethod; virtual;
    end;
    
    TParentObject = class(TGrandpaObject)
    public
      procedure AVirtualMethod; override;
    end;
    
    TCurrentObject = class(TParentObject)
    public
      procedure AVirtualMethod; override;
    end;
    
    TCurrentObject的AVirtualMethod虚拟方法不希望调用父类TParentObject的AVirtualMethod方法的实现代码,而要直接继承调用祖父类TGrandpaObject的AVirtualMethod方法代码。
    类的继承体系中,在VMT中,子类的VMT完全包含父类的VMT,而自身的虚拟方法则是附着在VMT父类虚拟方法表的后面,也就是说子类虚拟方法和父类虚拟方法的相对偏移量是相同的,只是子类的虚拟方法有覆盖时,子类VMT中该虚拟方法的地址被覆盖啦。因此,要跳过父类的虚拟方法而直接调用祖父类的虚拟方法代码,那么只要通过VMT的虚拟方法的相对偏移量找到祖父类的虚拟方法地址,然后调用即可。
    procedure TCurrentObject.AVirtualMethod;
    begin
      asm
            MOV     EDX,VMTOFFSET AVirtualMethod // 虚拟方法VMT偏移量
            MOV     EAX,Self                     // 对象实例 => EAX
            MOV     ECX,[EAX]                    // 类VMT => ECX
            MOV     ECX,[ECX].vmtParent
            MOV     ECX,[ECX]                    // 父类VMT => ECX
            MOV     ECX,[ECX].vmtParent
            MOV     ECX,[ECX]                    // 祖父类VMT => ECX
            MOV     ECX,[ECX+EDX]                // 祖父类虚拟方法地址 => ECX
            CALL    ECX                          // 方法调用
      end;
    end;
  • 相关阅读:
    GreenDao 数据库:使用Raw文件夹下的数据库文件以及数据库升级
    德鲁克的经典五问
    【转】太用力的人跑不远
    Android ViewPager打造3D画廊
    转载:张一鸣:10年面试2000人,我发现混的好的人,全都有同一个特质
    Comparable与Comparator
    Iterator、Iteratable与ListIterator
    shell 数学运算总结
    ADB命令行工具使用
    Android 搭建ssh服务
  • 原文地址:https://www.cnblogs.com/rogge7/p/5999256.html
Copyright © 2011-2022 走看看