为什么 vtable 指针在 x86 编译程序上对齐到 8 字节?
Why is vtable pointer aligned to 8 bytes on x86 compiled program?
我在一段代码中有以下结构(在 x86 上编译):
0:012> dt prog!_TESTSTRUCT
+0x000 __VFN_table : Ptr32
+0x008 szAddr : Ptr32 Wchar
+0x00c szOpCode : Ptr32 Wchar
+0x010 szMnemonic : Ptr32 Wchar
+0x014 szArgs : Ptr32 Wchar
+0x018 addr : Uint8B
+0x020 nextOffset : Uint8B
如您所见,vtable ptr,虽然大小为 4 个字节,但已对齐到 8 个字节。
作为参考,这是来自同一段代码的另一个结构,通常是对齐的:
0:012> dt prog!_TESTSTRUCT2
+0x000 __VFN_table : Ptr32
+0x004 pClient : Ptr32 IDebugClient5
+0x008 pDebugControl : Ptr32 IDebugControl4
+0x00c pDebugSystemObjects : Ptr32 IDebugSystemObjects
+0x010 pDebugDataSpaces : Ptr32 IDebugDataSpaces
+0x014 pDebugSymbols : Ptr32 IDebugSymbols3
+0x018 handlesAcquired : Bool
为什么 x86 上的 32 位指针与第一个结构中的 8 字节对齐?我在这里错过了什么?
编辑 1:
class _TESTSTRUCT size(40):
1> +---
1> 0 | {vfptr}
1> 8 | szAddr
1> 12 | szOpCode
1> 16 | szMnemonic
1> 20 | szArgs
1> 24 | addr
1> 32 | nextOffset
1> +---
1>
1> _TESTSTRUCT::$vftable@:
1> | &_TESTSTRUCT_meta
1> | 0
1> 0 | &_TESTSTRUCT::{dtor}
1>
1> _TESTSTRUCT::{dtor} this adjustor: 0
1> _TESTSTRUCT::__delDtor this adjustor: 0
1> _TESTSTRUCT::__vecDelDtor this adjustor: 0
class _TESTSTRUCT2 size(28):
1> +---
1> 0 | {vfptr}
1> 4 | pDebugClient
1> 8 | pDebugControl
1> 12 | pDebugSystemObjects
1> 16 | pDebugDataSpaces
1> 20 | pDebugSymbols
1> 24 | handlesAcquired
1> | <alignment member> (size=3)
1> +---
1>
1> _TESTSTRUCT2::$vftable@:
1> | &_TESTSTRUCT2_meta
1> | 0
1> 0 | &_TESTSTRUCT2::{dtor}
1>
1> _TESTSTRUCT2::{dtor} this adjustor: 0
1> _TESTSTRUCT2::__delDtor this adjustor: 0
1> _TESTSTRUCT2::__vecDelDtor this adjustor: 0
如此处所述
http://lolengine.net/blog/2012/10/21/the-stolen-bytes
8 字节结构成员导致 vfptr 未对齐到 8 字节而不是 4 字节,因为 vfptr 是在所有其他成员 added/aligned 之后添加到结构中的。这种行为似乎是 Visual Studio 特定的
我在一段代码中有以下结构(在 x86 上编译):
0:012> dt prog!_TESTSTRUCT
+0x000 __VFN_table : Ptr32
+0x008 szAddr : Ptr32 Wchar
+0x00c szOpCode : Ptr32 Wchar
+0x010 szMnemonic : Ptr32 Wchar
+0x014 szArgs : Ptr32 Wchar
+0x018 addr : Uint8B
+0x020 nextOffset : Uint8B
如您所见,vtable ptr,虽然大小为 4 个字节,但已对齐到 8 个字节。
作为参考,这是来自同一段代码的另一个结构,通常是对齐的:
0:012> dt prog!_TESTSTRUCT2
+0x000 __VFN_table : Ptr32
+0x004 pClient : Ptr32 IDebugClient5
+0x008 pDebugControl : Ptr32 IDebugControl4
+0x00c pDebugSystemObjects : Ptr32 IDebugSystemObjects
+0x010 pDebugDataSpaces : Ptr32 IDebugDataSpaces
+0x014 pDebugSymbols : Ptr32 IDebugSymbols3
+0x018 handlesAcquired : Bool
为什么 x86 上的 32 位指针与第一个结构中的 8 字节对齐?我在这里错过了什么?
编辑 1:
class _TESTSTRUCT size(40):
1> +---
1> 0 | {vfptr}
1> 8 | szAddr
1> 12 | szOpCode
1> 16 | szMnemonic
1> 20 | szArgs
1> 24 | addr
1> 32 | nextOffset
1> +---
1>
1> _TESTSTRUCT::$vftable@:
1> | &_TESTSTRUCT_meta
1> | 0
1> 0 | &_TESTSTRUCT::{dtor}
1>
1> _TESTSTRUCT::{dtor} this adjustor: 0
1> _TESTSTRUCT::__delDtor this adjustor: 0
1> _TESTSTRUCT::__vecDelDtor this adjustor: 0
class _TESTSTRUCT2 size(28):
1> +---
1> 0 | {vfptr}
1> 4 | pDebugClient
1> 8 | pDebugControl
1> 12 | pDebugSystemObjects
1> 16 | pDebugDataSpaces
1> 20 | pDebugSymbols
1> 24 | handlesAcquired
1> | <alignment member> (size=3)
1> +---
1>
1> _TESTSTRUCT2::$vftable@:
1> | &_TESTSTRUCT2_meta
1> | 0
1> 0 | &_TESTSTRUCT2::{dtor}
1>
1> _TESTSTRUCT2::{dtor} this adjustor: 0
1> _TESTSTRUCT2::__delDtor this adjustor: 0
1> _TESTSTRUCT2::__vecDelDtor this adjustor: 0
如此处所述
http://lolengine.net/blog/2012/10/21/the-stolen-bytes
8 字节结构成员导致 vfptr 未对齐到 8 字节而不是 4 字节,因为 vfptr 是在所有其他成员 added/aligned 之后添加到结构中的。这种行为似乎是 Visual Studio 特定的