16

我正在寻找 VTable 结构、顺序和内容的详细信息,以及 vtable 指针在对象中的位置。

理想情况下,这将涵盖单继承、多继承和虚拟继承。

对外部文档的引用也将不胜感激

GCC 4.0x 类布局的文档在这里,Itanium 和更广泛的 GNU、ABI 布局文档在这里

4

2 回答 2

12

虚拟表通常被视为函数指针数组,尽管编译器可以自由地将数据指针(在 MI 和 VI 场景中,或类型信息)、整数(用于修正)或标记元素(例如 NULL 指针)放入其中也是。布局通常是特定于编译器的(或者是特定于 ABI 的,多个 C++ 编译器共享一个 ABI),但如果正在编译的类具有稳定的接口,则它是稳定的(否则你必须一直重新编译你的代码,这是一个拖累) . 还需要额外的表来处理涉及虚拟和多重继承的极端情况,并确保派生类构造期间的虚拟调用按照标准所说的那样在这些情况下运行(这些是 VTT 和构造表中的下面的输出用于)。

至于 GCC 4.x 的具体情况:-fdump-class-hierarchy开关确实像描述的那样(然后是一些)。我使用下面的示例代码在Coliru上对其进行了测试:

struct Base
{
    virtual ~Base() {}
    virtual void f() = 0;
};

struct OtherBase
{
    virtual ~OtherBase() {}
    virtual void g() {}
};

struct Derived: public Base
{
    virtual ~Derived() {}
    virtual void f() {}
};

struct MultiplyDerived: public Base, public OtherBase
{
    virtual ~MultiplyDerived() {}
    virtual void f() {}
    virtual void g() {}
};

struct OtherDerived: public Base
{
    virtual ~OtherDerived() {}
    virtual void f() {}
};

struct DiamondDerived: public Derived, public OtherDerived
{
    virtual ~DiamondDerived() {}
    virtual void f() {}
};

struct VirtuallyDerived: virtual public Base
{
    virtual ~VirtuallyDerived() {}
    virtual void f() {}
};

struct OtherVirtuallyDerived: virtual public Base
{
    virtual ~OtherVirtuallyDerived() {}
    virtual void f() {}
};

struct VirtuallyDiamondDerived: public VirtuallyDerived, public OtherVirtuallyDerived
{
    virtual ~VirtuallyDiamondDerived() {}
    virtual void f() {}
};

struct DoublyVirtuallyDiamondDerived: virtual public VirtuallyDerived, virtual public OtherVirtuallyDerived
{
    virtual ~DoublyVirtuallyDiamondDerived() {}
    virtual void f() {}
};

struct MixedVirtuallyDerived: virtual public Base, public OtherBase
{
    virtual ~MixedVirtuallyDerived() {}
};

struct MixedVirtuallyDiamondDerived: public VirtuallyDerived, public MixedVirtuallyDerived
{
    virtual ~MixedVirtuallyDiamondDerived() {}
    virtual void f() {}
    virtual void g() {}
};

struct VirtuallyMultiplyDerived: virtual public Base, virtual public OtherBase
{
    virtual ~VirtuallyMultiplyDerived() {}
};

struct OtherVirtuallyMultiplyDerived: virtual public Base, virtual public OtherBase
{
    virtual ~OtherVirtuallyMultiplyDerived() {}
};

struct MultiplyVirtuallyDiamondDerived: public VirtuallyMultiplyDerived, public OtherVirtuallyMultiplyDerived
{
    virtual ~MultiplyVirtuallyDiamondDerived() {}
    virtual void f() {}
    virtual void g() {}
};

并从 G++ 接收(损坏的名称指南:TI 是 typeinfos,TV 是 vtables,Th 和 Tv 是用于在存在多重和/或虚拟继承的情况下进行正确虚拟调用的 thunk):

用于基础的 Vtable

Base::_ZTV4Base: 5u 个条目

0 (int (*)(...))0

8 (int (*)(...))(& _ZTI4Base)

16 0u

24 0u

32 (int (*)(...))__cxa_pure_virtual


类库

   大小=8 对齐=8

   基本尺寸=8 基本对齐=8

Base (0x0x7fd42c0355a0) 0 几乎为空

    vptr=((& Base::_ZTV4Base) + 16u)


OtherBase 的 Vtable

OtherBase::_ZTV9OtherBase: 5u 条目

0 (int (*)(...))0

8 (int (*)(...))(& _ZTI9OtherBase)

16 (int (*)(...))OtherBase::~OtherBase

24 (int (*)(...))OtherBase::~OtherBase

32 (int (*)(...))OtherBase::g


类 OtherBase

   大小=8 对齐=8

   基本尺寸=8 基本对齐=8

OtherBase (0x0x7fd42c035600) 0 几乎为空

    vptr=((& OtherBase::_ZTV9OtherBase) + 16u)


导出的 Vtable

Derived::_ZTV7Derived: 5u 个条目

0 (int (*)(...))0

8 (int (*)(...))(& _ZTI7Derived)

16 (int (*)(...))Derived::~Derived

24 (int (*)(...))Derived::~Derived

32 (int (*)(...))Derived::f


类派生

   大小=8 对齐=8

   基本尺寸=8 基本对齐=8

派生 (0x0x7fd42c02d138) 0 几乎为空

    vptr=((& Derived::_ZTV7Derived) + 16u)

  Base (0x0x7fd42c035660) 0 几乎为空

      主要派生(0x0x7fd42c02d138)


MultiplyDerived 的 Vtable

MultiplyDerived::_ZTV15MultiplyDerived: 11u 个条目

0 (int (*)(...))0

8 (int (*)(...))(& _ZTI15MultiplyDerived)

16 (int (*)(...))MultiplyDerived::~MultiplyDerived

24 (int (*)(...))MultiplyDerived::~MultiplyDerived

32 (int (*)(...))MultiplyDerived::f

40 (int (*)(...))MultiplyDerived::g

48 (int (*)(...))-8

56 (int (*)(...))(& _ZTI15MultiplyDerived)

64 (int (*)(...))MultiplyDerived::_ZThn8_N15MultiplyDerivedD1Ev

72 (int (*)(...))MultiplyDerived::_ZThn8_N15MultiplyDerivedD0Ev

80 (int (*)(...))MultiplyDerived::_ZThn8_N15MultiplyDerived1gEv


类 MultiplyDerived

   尺寸=16 对齐=8

   基本尺寸=16 基本对齐=8

乘法衍生 (0x0x7fd42c04aaf0) 0

    vptr=((& MultiplyDerived::_ZTV15MultiplyDerived) + 16u)

  Base (0x0x7fd42c0356c0) 0 几乎为空

      主要用于 MultiplyDerived (0x0x7fd42c04aaf0)

  OtherBase (0x0x7fd42c035720) 8 几乎为空

      vptr=((& MultiplyDerived::_ZTV15MultiplyDerived) + 64u)


OtherDerived 的 Vtable

OtherDerived::_ZTV12OtherDerived: 5u 条目

0 (int (*)(...))0

8 (int (*)(...))(& _ZTI12OtherDerived)

16 (int (*)(...))OtherDerived::~OtherDerived

24 (int (*)(...))OtherDerived::~OtherDerived

32 (int (*)(...))OtherDerived::f


其他派生类

   大小=8 对齐=8

   基本尺寸=8 基本对齐=8

OtherDerived (0x0x7fd42c02d1a0) 0 几乎为空

    vptr=((& OtherDerived::_ZTV12OtherDerived) + 16u)

  基数 (0x0x7fd42c035780) 0 几乎为空

      主要的其他派生(0x0x7fd42c02d1a0)


DiamondDerived 的 Vtable

DiamondDerived::_ZTV14DiamondDerived: 10u 个条目

0 (int (*)(...))0

8 (int (*)(...))(& _ZTI14DiamondDerived)

16 (int (*)(...))DiamondDerived::~DiamondDerived

24 (int (*)(...))DiamondDerived::~DiamondDerived

32 (int (*)(...))DiamondDerived::f

40 (int (*)(...))-8

48 (int (*)(...))(& _ZTI14DiamondDerived)

56 (int (*)(...))DiamondDerived::_ZThn8_N14DiamondDerivedD1Ev

64 (int (*)(...))DiamondDerived::_ZThn8_N14DiamondDerivedD0Ev

72 (int (*)(...))DiamondDerived::_ZThn8_N14DiamondDerived1fEv


类 DiamondDerived

   尺寸=16 对齐=8

   基本尺寸=16 基本对齐=8

钻石派生(0x0x7fd42c0625b0)0

    vptr=((& DiamondDerived::_ZTV14DiamondDerived) + 16u)

  派生 (0x0x7fd42c02d208) 0 几乎为空

      主要用于 DiamondDerived (0x0x7fd42c0625b0)

    Base (0x0x7fd42c0357e0) 0 几乎为空

        主要派生(0x0x7fd42c02d208)

  OtherDerived (0x0x7fd42c02d270) 8 几乎为空

      vptr=((& DiamondDerived::_ZTV14DiamondDerived) + 56u)

    Base (0x0x7fd42c035840) 8 几乎为空

        主要的其他派生(0x0x7fd42c02d270)


VirtuallyDerived 的 Vtable

VirtuallyDerived::_ZTV16VirtuallyDerived: 8u 条目

0 0u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI16VirtuallyDerived)

40 (int (*)(...))VirtuallyDerived::~VirtuallyDerived

48 (int (*)(...))VirtuallyDerived::~VirtuallyDerived

56 (int (*)(...))VirtuallyDerived::f


虚拟衍生的 VTT

VirtuallyDerived::_ZTT16VirtuallyDerived: 2u 个条目

0 ((& VirtuallyDerived::_ZTV16VirtuallyDerived) + 40u)

8 ((& VirtuallyDerived::_ZTV16VirtuallyDerived) + 40u)


虚拟派生类

   大小=8 对齐=8

   基本尺寸=8 基本对齐=8

VirtuallyDerived (0x0x7fd42c02d2d8) 0 几乎为空

    vptridx=0u vptr=((& VirtuallyDerived::_ZTV16VirtuallyDerived) + 40u)

  Base (0x0x7fd42c0358a0) 0 几乎为空的虚拟

      主要用于 VirtuallyDerived (0x0x7fd42c02d2d8)

      vptridx=8u vbaseoffset=-40


OtherVirtuallyDerived 的 Vtable

OtherVirtuallyDerived::_ZTV21OtherVirtuallyDerived: 8u 条目

0 0u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI21OtherVirtuallyDerived)

40 (int (*)(...))OtherVirtuallyDerived::~OtherVirtuallyDerived

48 (int (*)(...))OtherVirtuallyDerived::~OtherVirtuallyDerived

56 (int (*)(...))OtherVirtuallyDerived::f


其他虚拟派生的 VTT

OtherVirtuallyDerived::_ZTT21OtherVirtuallyDerived: 2u 个条目

0 ((& OtherVirtuallyDerived::_ZTV21OtherVirtuallyDerived) + 40u)

8 ((& OtherVirtuallyDerived::_ZTV21OtherVirtuallyDerived) + 40u)


类 OtherVirtuallyDerived

   大小=8 对齐=8

   基本尺寸=8 基本对齐=8

OtherVirtuallyDerived (0x0x7fd42c02d340) 0 几乎为空

    vptridx=0u vptr=((& OtherVirtuallyDerived::_ZTV21OtherVirtuallyDerived) + 40u)

  Base (0x0x7fd42c035900) 0 几乎为空的虚拟

      主要用于 OtherVirtuallyDerived (0x0x7fd42c02d340)

      vptridx=8u vbaseoffset=-40


VirtuallyDiamondDerived 的 Vtable

VirtuallyDiamondDerived::_ZTV23VirtuallyDiamondDerived: 16u 个条目

0 0u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI23VirtuallyDiamondDerived)

40 (int (*)(...))VirtuallyDiamondDerived::~VirtuallyDiamondDerived

48 (int (*)(...))VirtuallyDiamondDerived::~VirtuallyDiamondDerived

56 (int (*)(...))VirtuallyDiamondDerived::f

64 18446744073709551608u

72 18446744073709551608u

80 18446744073709551608u

88 (int (*)(...))-8

96 (int (*)(...))(& _ZTI23VirtuallyDiamondDerived)

104 (int (*)(...))VirtuallyDiamondDerived::_ZThn8_N23VirtuallyDiamondDerivedD1Ev

112 (int (*)(...))VirtuallyDiamondDerived::_ZThn8_N23VirtuallyDiamondDerivedD0Ev

120 (int (*)(...))VirtuallyDiamondDerived::_ZThn8_N23VirtuallyDiamondDerived1fEv


VirtuallyDiamondDerived 中 VirtuallyDerived(0x0x7fd42c02d3a8 实例)的构造 vtable

VirtuallyDiamondDerived::_ZTC23VirtuallyDiamondDerived0_16VirtuallyDerived: 8u 条目

0 0u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI16VirtuallyDerived)

40 0u

48 0u

56 (int (*)(...))VirtuallyDerived::f


VirtuallyDiamondDerived 中 OtherVirtuallyDerived (0x0x7fd42c02d410 实例) 的构造 vtable

VirtuallyDiamondDerived::_ZTC23VirtuallyDiamondDerived8_21OtherVirtuallyDerived: 15u 个条目

0 18446744073709551608u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI21OtherVirtuallyDerived)

40 0u

48 0u

56 (int (*)(...))OtherVirtuallyDerived::f

64 8u

72 8u

80 (int (*)(...))8

88 (int (*)(...))(& _ZTI21OtherVirtuallyDerived)

96 0u

104 0u

112 (int (*)(...))OtherVirtuallyDerived::_ZTv0_n32_N21OtherVirtuallyDerived1fEv


VirtuallyDiamondDerived 的 VTT

VirtuallyDiamondDerived::_ZTT23VirtuallyDiamondDerived: 7u 个条目

0 ((& VirtuallyDiamondDerived::_ZTV23VirtuallyDiamondDerived) + 40u)

8 ((& VirtuallyDiamondDerived::_ZTC23VirtuallyDiamondDerived0_16VirtuallyDerived) + 40u)

16 ((& VirtuallyDiamondDerived::_ZTC23VirtuallyDiamondDerived0_16VirtuallyDerived) + 40u)

24 ((& VirtuallyDiamondDerived::_ZTC23VirtuallyDiamondDerived8_21OtherVirtuallyDerived) + 40u)

32 ((& VirtuallyDiamondDerived::_ZTC23VirtuallyDiamondDerived8_21OtherVirtuallyDerived) + 96u)

40 ((& VirtuallyDiamondDerived::_ZTV23VirtuallyDiamondDerived) + 40u)

48 ((& VirtuallyDiamondDerived::_ZTV23VirtuallyDiamondDerived) + 104u)


VirtuallyDiamondDerived 类

   尺寸=16 对齐=8

   基本尺寸=16 基本对齐=8

VirtuallyDiamondDerived (0x0x7fd42c07e460) 0

    vptridx=0u vptr=((& VirtuallyDiamondDerived::_ZTV23VirtuallyDiamondDerived) + 40u)

  VirtuallyDerived (0x0x7fd42c02d3a8) 0 几乎为空

      主要用于 VirtuallyDiamondDerived (0x0x7fd42c07e460)

      subvttidx=8u

    Base (0x0x7fd42c035960) 0 几乎为空的虚拟

        主要用于 VirtuallyDerived (0x0x7fd42c02d3a8)

        vptridx=40u vbaseoffset=-40

  OtherVirtuallyDerived (0x0x7fd42c02d410) 8 几乎为空

      失主

      subvttidx=24u vptridx=48u vptr=((& VirtuallyDiamondDerived::_ZTV23VirtuallyDiamondDerived) + 104u)

    基本 (0x0x7fd42c035960) 替代路径


DoublyVirtuallyDiamondDerived 的 Vtable

DoublyVirtuallyDiamondDerived::_ZTV29DoublyVirtuallyDiamondDerived: 18u 个条目

0 8u

8 0u

16 0u

24 0u

32 0u

40 (int (*)(...))0

48 (int (*)(...))(& _ZTI29DoublyVirtuallyDiamondDerived)

56 (int (*)(...))DoublyVirtuallyDiamondDerived::~DoublyVirtuallyDiamondDerived

64 (int (*)(...))DoublyVirtuallyDiamondDerived::~DoublyVirtuallyDiamondDerived

72 (int (*)(...))DoublyVirtuallyDiamondDerived::f

80 18446744073709551608u

88 18446744073709551608u

96 18446744073709551608u

104 (int (*)(...))-8

112 (int (*)(...))(& _ZTI29DoublyVirtuallyDiamondDerived)

120 (int (*)(...))DoublyVirtuallyDiamondDerived::_ZTv0_n24_N29DoublyVirtuallyDiamondDerivedD1Ev

128 (int (*)(...))DoublyVirtuallyDiamondDerived::_ZTv0_n24_N29DoublyVirtuallyDiamondDerivedD0Ev

136 (int (*)(...))DoublyVirtuallyDiamondDerived::_ZTv0_n32_N29DoublyVirtuallyDiamondDerived1fEv


DoublyVirtuallyDiamondDerived 中 VirtuallyDerived 的构造 vtable

DoublyVirtuallyDiamondDerived::_ZTC29DoublyVirtuallyDiamondDerived0_16VirtuallyDerived: 8u 个条目

0 0u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI16VirtuallyDerived)

40 0u

48 0u

56 (int (*)(...))VirtuallyDerived::f


DoublyVirtuallyDiamondDerived 中 OtherVirtuallyDerived 的构造 vtable

DoublyVirtuallyDiamondDerived::_ZTC29DoublyVirtuallyDiamondDerived8_21OtherVirtuallyDerived: 15u 个条目

0 18446744073709551608u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI21OtherVirtuallyDerived)

40 0u

48 0u

56 (int (*)(...))OtherVirtuallyDerived::f

64 8u

72 8u

80 (int (*)(...))8

88 (int (*)(...))(& _ZTI21OtherVirtuallyDerived)

96 0u

104 0u

112 (int (*)(...))OtherVirtuallyDerived::_ZTv0_n32_N21OtherVirtuallyDerived1fEv


VTT for DoublyVirtuallyDiamondDerived

DoublyVirtuallyDiamondDerived::_ZTT29DoublyVirtuallyDiamondDerived: 8u 个条目

0 ((&DoublyVirtuallyDiamondDerived::_ZTV29DoublyVirtuallyDiamondDerived) + 56u)

8 ((&DoublyVirtuallyDiamondDerived::_ZTV29DoublyVirtuallyDiamondDerived) + 56u)

16 ((&DoublyVirtuallyDiamondDerived::_ZTV29DoublyVirtuallyDiamondDerived) + 56u)

24 ((&DoublyVirtuallyDiamondDerived::_ZTV29DoublyVirtuallyDiamondDerived) + 120u)

32 ((&DoublyVirtuallyDiamondDerived::_ZTC29DoublyVirtuallyDiamondDerived0_16VirtuallyDerived) + 40u)

40 ((&DoublyVirtuallyDiamondDerived::_ZTC29DoublyVirtuallyDiamondDerived0_16VirtuallyDerived) + 40u)

48 ((&DoublyVirtuallyDiamondDerived::_ZTC29DoublyVirtuallyDiamondDerived8_21OtherVirtuallyDerived) + 40u)

56 ((&DoublyVirtuallyDiamondDerived::_ZTC29DoublyVirtuallyDiamondDerived8_21OtherVirtuallyDerived) + 96u)


类 DoubleVirtuallyDiamondDerived

   尺寸=16 对齐=8

   基本尺寸=8 基本对齐=8

DoublyVirtuallyDiamondDerived (0x0x7fd42c07ea10) 0 几乎为空

    vptridx=0u vptr=((&DoublyVirtuallyDiamondDerived::_ZTV29DoublyVirtuallyDiamondDerived) + 56u)

  VirtuallyDerived (0x0x7fd42c02d478) 0 几乎为空的虚拟

      主要用于 DoublyVirtuallyDiamondDerived (0x0x7fd42c07ea10)

      subvttidx=32u vptridx=8u vbaseoffset=-48

    Base (0x0x7fd42c035a80) 0 几乎为空的虚拟

        主要用于 VirtuallyDerived (0x0x7fd42c02d478)

        vptridx=16u vbaseoffset=-40

  OtherVirtuallyDerived (0x0x7fd42c02d4e0) 8 几乎为空的虚拟

      失主

      subvttidx=48u vptridx=24u vbaseoffset=-56 vptr=((&DoublyVirtuallyDiamondDerived::_ZTV29DoublyVirtuallyDiamondDerived) + 120u)

    基本 (0x0x7fd42c035a80) 替代路径


MixedVirtuallyDerived 的 Vtable

MixedVirtuallyDerived::_ZTV21MixedVirtuallyDerived: 13u 个条目

0 8u

8 (int (*)(...))0

16 (int (*)(...))(& _ZTI21MixedVirtuallyDerived)

24 0u

32 0u

40 (int (*)(...))OtherBase::g

48 0u

56 18446744073709551608u

64 (int (*)(...))-8

72 (int (*)(...))(& _ZTI21MixedVirtuallyDerived)

80 0u

88 0u

96 (int (*)(...))__cxa_pure_virtual


混合虚拟衍生的 VTT

MixedVirtuallyDerived::_ZTT21MixedVirtuallyDerived: 2u 个条目

0 ((& MixedVirtuallyDerived::_ZTV21MixedVirtuallyDerived) + 24u)

8 ((& MixedVirtuallyDerived::_ZTV21MixedVirtuallyDerived) + 80u)


类 MixedVirtuallyDerived

   尺寸=16 对齐=8

   基本尺寸=8 基本对齐=8

MixedVirtuallyDerived (0x0x7fd42c07eee0) 0 几乎为空

    vptridx=0u vptr=((& MixedVirtuallyDerived::_ZTV21MixedVirtuallyDerived) + 24u)

  Base (0x0x7fd42c035c60) 8 个几乎为空的虚拟

      vptridx=8u vbaseoffset=-24 vptr=((& MixedVirtuallyDerived::_ZTV21MixedVirtuallyDerived) + 80u)

  OtherBase (0x0x7fd42c035cc0) 0 几乎为空

      主要用于 MixedVirtuallyDerived (0x0x7fd42c07eee0)


MixedVirtuallyDiamondDerived 的 Vtable

MixedVirtuallyDiamondDerived::_ZTV28MixedVirtuallyDiamondDerived: 15u 个条目

0 0u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI28MixedVirtuallyDiamondDerived)

40 (int (*)(...))MixedVirtuallyDiamondDerived::~MixedVirtuallyDiamondDerived

48 (int (*)(...))MixedVirtuallyDiamondDerived::~MixedVirtuallyDiamondDerived

56 (int (*)(...))MixedVirtuallyDiamondDerived::f

64 (int (*)(...))MixedVirtuallyDiamondDerived::g

72 18446744073709551608u

80 (int (*)(...))-8

88 (int (*)(...))(& _ZTI28MixedVirtuallyDiamondDerived)

96 (int (*)(...))MixedVirtuallyDiamondDerived::_ZThn8_N28MixedVirtuallyDiamondDerivedD1Ev

104 (int (*)(...))MixedVirtuallyDiamondDerived::_ZThn8_N28MixedVirtuallyDiamondDerivedD0Ev

112 (int (*)(...))MixedVirtuallyDiamondDerived::_ZThn8_N28MixedVirtuallyDiamondDerived1gEv


MixedVirtuallyDiamondDerived 中 VirtuallyDerived(0x0x7fd42c02d750 实例)的构造 vtable

MixedVirtuallyDiamondDerived::_ZTC28MixedVirtuallyDiamondDerived0_16VirtuallyDerived: 8u 个条目

0 0u

8 0u

16 0u

24 (int (*)(...))0

32 (int (*)(...))(& _ZTI16VirtuallyDerived)

40 0u

48 0u

56 (int (*)(...))VirtuallyDerived::f


MixedVirtuallyDiamondDerived 中 MixedVirtuallyDerived(0x0x7fd42c0b5380 实例)的构造 vtable

MixedVirtuallyDiamondDerived::_ZTC28MixedVirtuallyDiamondDerived8_21MixedVirtuallyDerived: 13u 个条目

0 18446744073709551608u

8 (int (*)(...))0

16 (int (*)(...))(& _ZTI21MixedVirtuallyDerived)

24 0u

32 0u

40 (int (*)(...))OtherBase::g

48 0u

56 8u

64 (int (*)(...))8

72 (int (*)(...))(& _ZTI21MixedVirtuallyDerived)

80 0u

88 0u

96 (int (*)(...))__cxa_pure_virtual


VTT for MixedVirtuallyDiamondDerived

MixedVirtuallyDiamondDerived::_ZTT28MixedVirtuallyDiamondDerived: 7u 个条目

0 ((& MixedVirtuallyDiamondDerived::_ZTV28MixedVirtuallyDiamondDerived) + 40u)

8 ((& MixedVirtuallyDiamondDerived::_ZTC28MixedVirtuallyDiamondDerived0_16VirtuallyDerived) + 40u)

16 ((& MixedVirtuallyDiamondDerived::_ZTC28MixedVirtuallyDiamondDerived0_16VirtuallyDerived) + 40u)

24 ((& MixedVirtuallyDiamondDerived::_ZTC28MixedVirtuallyDiamondDerived8_21MixedVirtuallyDerived) + 24u)

32 ((& MixedVirtuallyDiamondDerived::_ZTC28MixedVirtuallyDiamondDerived8_21MixedVirtuallyDerived) + 80u)

40 ((& MixedVirtuallyDiamondDerived::_ZTV28MixedVirtuallyDiamondDerived) + 40u)

48 ((& MixedVirtuallyDiamondDerived::_ZTV28MixedVirtuallyDiamondDerived) + 96u)


类 MixedVirtuallyDiamondDerived

   尺寸=16 对齐=8

   基本尺寸=16 基本对齐=8

MixedVirtuallyDiamondDerived (0x0x7fd42c0b5310) 0

    vptridx=0u vptr=((& MixedVirtuallyDiamondDerived::_ZTV28MixedVirtuallyDiamondDerived) + 40u)

  VirtuallyDerived (0x0x7fd42c02d750) 0 几乎为空

      主要用于 MixedVirtuallyDiamondDerived (0x0x7fd42c0b5310)

      subvttidx=8u

    Base (0x0x7fd42c035d20) 0 几乎为空的虚拟

        主要用于 VirtuallyDerived (0x0x7fd42c02d750)

        vptridx=40u vbaseoffset=-40

  MixedVirtuallyDerived (0x0x7fd42c0b5380) 8 几乎为空

      subvttidx=24u vptridx=48u vptr=((& MixedVirtuallyDiamondDerived::_ZTV28MixedVirtuallyDiamondDerived) + 96u)

    基本 (0x0x7fd42c035d20) 替代路径

    OtherBase (0x0x7fd42c035d80) 8 几乎为空

        主要用于 MixedVirtuallyDerived (0x0x7fd42c0b5380)


VirtuallyMultiplyDerived 的 Vtable

VirtuallyMultiplyDerived::_ZTV24VirtuallyMultiplyDerived:16u 个条目

0 8u

8 0u

16 0u

24 0u

32 (int (*)(...))0

40 (int (*)(...))(& _ZTI24VirtuallyMultiplyDerived)

48 0u

56 0u

64 (int (*)(...))__cxa_pure_virtual

72 0u

80 18446744073709551608u

88 (int (*)(...))-8

96 (int (*)(...))(& _ZTI24VirtuallyMultiplyDerived)

104 0u

112 0u

120 (int (*)(...))OtherBase::g


VirtuallyMultiplyDerived 的 VTT

VirtuallyMultiplyDerived::_ZTT24VirtuallyMultiplyDerived:3u 个条目

0 ((& VirtuallyMultiplyDerived::_ZTV24VirtuallyMultiplyDerived) + 48u)

8 ((& VirtuallyMultiplyDerived::_ZTV24VirtuallyMultiplyDerived) + 48u)

16 ((& VirtuallyMultiplyDerived::_ZTV24VirtuallyMultiplyDerived) + 104u)


类 VirtuallyMultiplyDerived

   尺寸=16 对齐=8

   基本尺寸=8 基本对齐=8

VirtuallyMultiplyDerived (0x0x7fd42c0b59a0) 0 几乎为空

    vptridx=0u vptr=((& VirtuallyMultiplyDerived::_ZTV24VirtuallyMultiplyDerived) + 48u)

  Base (0x0x7fd42c035e40) 0 几乎为空的虚拟

      主要用于 VirtuallyMultiplyDerived (0x0x7fd42c0b59a0)

      vptridx=8u vbaseoffset=-40

  OtherBase (0x0x7fd42c035ea0) 8 几乎为空的虚拟

      vptridx=16u vbaseoffset=-48 vptr=((& VirtuallyMultiplyDerived::_ZTV24VirtuallyMultiplyDerived) + 104u)


OtherVirtuallyMultiplyDerived 的 Vtable

OtherVirtuallyMultiplyDerived::_ZTV29OtherVirtuallyMultiplyDerived: 16u 个条目

0 8u

8 0u

16 0u

24 0u

32 (int (*)(...))0

40 (int (*)(...))(& _ZTI29OtherVirtuallyMultiplyDerived)

48 0u

56 0u

64 (int (*)(...))__cxa_pure_virtual

72 0u

80 18446744073709551608u

88 (int (*)(...))-8

96 (int (*)(...))(& _ZTI29OtherVirtuallyMultiplyDerived)

104 0u

112 0u

120 (int (*)(...))OtherBase::g


其他虚拟乘法衍生的 VTT

OtherVirtuallyMultiplyDerived::_ZTT29OtherVirtuallyMultiplyDerived: 3u 个条目

0 ((& OtherVirtuallyMultiplyDerived::_ZTV29OtherVirtuallyMultiplyDerived) + 48u)

8 ((& OtherVirtuallyMultiplyDerived::_ZTV29OtherVirtuallyMultiplyDerived) + 48u)

16 ((& OtherVirtuallyMultiplyDerived::_ZTV29OtherVirtuallyMultiplyDerived) + 104u)


类 OtherVirtuallyMultiplyDerived

   尺寸=16 对齐=8

   基本尺寸=8 基本对齐=8

OtherVirtuallyMultiplyDerived (0x0x7fd42c0b5d90) 0 几乎为空

    vptridx=0u vptr=((& OtherVirtuallyMultiplyDerived::_ZTV29OtherVirtuallyMultiplyDerived) + 48u)

  Base (0x0x7fd42c035f00) 0 几乎为空的虚拟

      主要用于 OtherVirtuallyMultiplyDerived (0x0x7fd42c0b5d90)

      vptridx=8u vbaseoffset=-40

  OtherBase (0x0x7fd42c035f60) 8 几乎为空的虚拟

      vptridx=16u vbaseoffset=-48 vptr=((& OtherVirtuallyMultiplyDerived::_ZTV29OtherVirtuallyMultiplyDerived) + 104u)


MultiplyVirtuallyDiamondDerived 的 Vtable

MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived: 26u 个条目

0 16u

8 0u

16 0u

24 0u

32 (int (*)(...))0

40 (int (*)(...))(& _ZTI31MultiplyVirtuallyDiamondDerived)

48 (int (*)(...))MultiplyVirtuallyDiamondDerived::~MultiplyVirtuallyDiamondDerived

56 (int (*)(...))MultiplyVirtuallyDiamondDerived::~MultiplyVirtuallyDiamondDerived

64 (int (*)(...))MultiplyVirtuallyDiamondDerived::f

72 (int (*)(...))MultiplyVirtuallyDiamondDerived::g

80 8u

88 18446744073709551608u

96 18446744073709551608u

104 18446744073709551608u

112 (int (*)(...))-8

120 (int (*)(...))(& _ZTI31MultiplyVirtuallyDiamondDerived)

128 (int (*)(...))MultiplyVirtuallyDiamondDerived::_ZThn8_N31MultiplyVirtuallyDiamondDerivedD1Ev

136 (int (*)(...))MultiplyVirtuallyDiamondDerived::_ZThn8_N31MultiplyVirtuallyDiamondDerivedD0Ev

144 0u

152 18446744073709551600u

160 18446744073709551600u

168(整数(*)(...))-16

176(int(*)(...))(&_ZTI31MultiplyVirtuallyDiamondDerived)

184 (int (*)(...))MultiplyVirtuallyDiamondDerived::_ZTv0_n24_N31MultiplyVirtuallyDiamondDerivedD1Ev

192 (int (*)(...))MultiplyVirtuallyDiamondDerived::_ZTv0_n24_N31MultiplyVirtuallyDiamondDerivedD0Ev

200 (int (*)(...))MultiplyVirtuallyDiamondDerived::_ZTv0_n32_N31MultiplyVirtuallyDiamondDerived1gEv


MultiplyVirtuallyDiamondDerived 中 VirtuallyMultiplyDerived(0x0x7fd42bcdf230 实例)的构造 vtable

MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived0_24VirtuallyMultiplyDerived: 16u 个条目

0 16u

8 0u

16 0u

24 0u

32 (int (*)(...))0

40 (int (*)(...))(& _ZTI24VirtuallyMultiplyDerived)

48 0u

56 0u

64 (int (*)(...))__cxa_pure_virtual

72 0u

80 18446744073709551600u

88 (int (*)(...))-16

96 (int (*)(...))(& _ZTI24VirtuallyMultiplyDerived)

104 0u

112 0u

120 (int (*)(...))OtherBase::g


MultiplyVirtuallyDiamondDerived 中 OtherVirtuallyMultiplyDerived(0x0x7fd42bcdf2a0 实例)的构造 vtable

MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived8_29OtherVirtuallyMultiplyDerived: 23u 个条目

0 8u

8 18446744073709551608u

16 18446744073709551608u

24 0u

32 (int (*)(...))0

40 (int (*)(...))(& _ZTI29OtherVirtuallyMultiplyDerived)

48 0u

56 0u

64 (int (*)(...))__cxa_pure_virtual

72 0u

80 8u

88 (int (*)(...))8

96 (int (*)(...))(& _ZTI29OtherVirtuallyMultiplyDerived)

104 0u

112 0u

120 (int (*)(...))__cxa_pure_virtual

128 0u

136 18446744073709551608u

144(整数(*)(...))-8

152 (int (*)(...))(& _ZTI29OtherVirtuallyMultiplyDerived)

160 0u

168 0u

176 (int (*)(...))OtherBase::g


MultiplyVirtuallyDiamondDerived 的 VTT

MultiplyVirtuallyDiamondDerived::_ZTT31MultiplyVirtuallyDiamondDerived: 10u 个条目

0 ((& MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived) + 48u)

8 ((& MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived0_24VirtuallyMultiplyDerived) + 48u)

16 ((& MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived0_24VirtuallyMultiplyDerived) + 48u)

24 ((& MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived0_24VirtuallyMultiplyDerived) + 104u)

32 ((& MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived8_29OtherVirtuallyMultiplyDerived) + 48u)

40 ((& MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived8_29OtherVirtuallyMultiplyDerived) + 104u)

48 ((& MultiplyVirtuallyDiamondDerived::_ZTC31MultiplyVirtuallyDiamondDerived8_29OtherVirtuallyMultiplyDerived) + 160u)

56 ((& MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived) + 48u)

64 ((& MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived) + 184u)

72 ((& MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived) + 128u)


类 MultiplyVirtuallyDiamondDerived

   大小=24 对齐=8

   基本尺寸=16 基本对齐=8

MultiplyVirtuallyDiamondDerived (0x0x7fd42bcdf1c0) 0

    vptridx=0u vptr=((& MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived) + 48u)

  VirtuallyMultiplyDerived (0x0x7fd42bcdf230) 0 几乎为空

      主要用于 MultiplyVirtuallyDiamondDerived (0x0x7fd42bcdf1c0)

      subvttidx=8u

    Base (0x0x7fd42bce2000) 0 几乎为空的虚拟

        主要用于 VirtuallyMultiplyDerived (0x0x7fd42bcdf230)

        vptridx=56u vbaseoffset=-40

    OtherBase (0x0x7fd42bce2060) 16 几乎为空的虚拟

        vptridx=64u vbaseoffset=-48 vptr=((& MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived) + 184u)

  OtherVirtuallyMultiplyDerived (0x0x7fd42bcdf2a0) 8 几乎为空

      失主

      subvttidx=32u vptridx=72u vptr=((& MultiplyVirtuallyDiamondDerived::_ZTV31MultiplyVirtuallyDiamondDerived) + 128u)

    基本 (0x0x7fd42bce2000) 替代路径

    OtherBase (0x0x7fd42bce2060) 替代路径
于 2015-01-26T17:50:25.493 回答
-5

我见过的大多数编译器实现只是将基础对象“嵌入”到派生对象中。保留 vtable 的位置变得无关紧要,因为对象的相对偏移量只会在编译时在评估引用时添加。

多重继承和虚拟继承更加复杂,并且可能需要不同的偏移量,具体取决于正在访问的内容。

我强烈推荐阅读这篇关于代码项目的文章:The Impossibly Fast C++ Delegates

它出色地概括了不同编译器如何处理继承的各个方面。如果您对不同编译器的低级工作感兴趣,请好好阅读。

编辑:我在那里链接了错误的文章。已更正。

于 2014-09-04T20:54:59.247 回答