【c++内存分布系列】虚基类表

本文通过实例详细解析了虚基类表的工作原理及其在内存中的布局方式,对比虚函数表,解释了虚基类表中各项的具体含义。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

  虚基类表相对于虚函数表要稍微难理解些,故单独提出来。

  虚函数表是在对象生成时插入一个虚函数指针,指向虚函数表,这个表中所列就是虚函数。

  虚基类表原理与虚函数表类似,不过虚基类表的内容有所不同。表的第一项表示派生类对象指针相对于虚基类表指针的偏移,从第二项开始表示各个基类地址相对于虚基类表指针的偏移。

  程序

#include <cstdio>

class A
{
public:
    int a;
    int aa;
    virtual void vfuna(){};
};

class B
{
public:
    int b;
    int bb;
    virtual void vfunb(){};
};

class C: virtual public A,virtual public B
{
public:
    int c;
    int cc;
    void vfuna(){};
};


int main(int argc, char** argv)
{
    printf("%d\n", sizeof(C));

    C c;
    c.a = 0xaaaaaaaa;
    c.aa = 0xbbbbbbbb;
    c.b = 0xdddddddd;
    c.bb = 0xeeeeeeee;
    c.c = 0x11111111;
    c.cc = 0x22222222;
    C* pc = &c;
    printf("%08x\n", pc);
}

  windows输出:

36
0034f834

  查看对象c内存0x34f834:

0034F834 60 
0034F835 57 
0034F836 1D 00 11 11 11 
0034F83B 11 22  
0034F83D 22 22  
0034F83F 22 58 57  
0034F842 1D 00 AA AA AA  
0034F847 AA 
0034F848 BB BB BB BB 4C 
0034F84D 57 
0034F84E 1D 00 DD DD DD 
0034F853 DD EE
0034F855 EE
0034F856 EE  
0034F857 EE 

  查看虚基类表0x001d5760:

C::`vbtable':
001D5760 00 00 add byte ptr [eax],al
001D5762 00 00 add byte ptr [eax],al
001D5764 0C 00 or al,0
001D5766 00 00 add byte ptr [eax],al
001D5768 18 00 sbb byte ptr [eax],al
001D576A 00 00 add byte ptr [eax],al
001D576C 00 00 add byte ptr [eax],al
001D576E 00 00 add byte ptr [eax],al

  得派生类对象指针相对于虚基类表指针的偏移0,基类A地址相对于虚基类表指针的偏移12,基类B地址相对于虚基类表指针的偏移24。查看偏移12位内容为0x001d5758。其指向地址内容:

C::`vftable':
001D5758 91 xchg eax,ecx
001D5759 10 1D 00 00 00 00 adc byte ptr ds:[0],bl
001D575F 00 00 add byte ptr [eax],al

C::vfuna:
001D1091 E9 AA 05 00 00 jmp C::vfuna (1D1640h)

  偏移24位内容为0x0014574c,其指向地址内容为:

C::`vftable':
001D574C 0A 10 or dl,byte ptr [eax]
001D574E 1D 00 00 00 00 sbb eax,0
001D5753 00 F8 add al,bh

B::vfunb:
001D100A E9 F1 05 00 00 jmp B::vfunb (1D1600h)

  验证一个为虚基类A内容,一个为虚基类B内容。

 

转载于:https://www.cnblogs.com/budapeng/p/3305790.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值