Насколько я понимаю, все экземпляры объекта .NET начинаются с 8-байтового "заголовка объекта": блока синхронизации (4-байтовый указатель на таблицу SynchTableEntry) и дескриптора типа (4-байтовый указатель на таблицу методов типов).
Я не вижу этого в окнах памяти отладчика VS 2010 RC (CLR 4.0).
Вот простой класс, который сгенерирует 16-байтовый экземпляр за вычетом заголовка объекта.
class Program
{
short myInt = 2; // 4 bytes
long myLong = 3; // 8 bytes
string myString = "aString"; // 4 byte object reference
// 16 byte instance
static void Main(string[] args)
{
new Program();
return;
}
}
Дамп объекта SOS сообщает мне, что общий размер объекта составляет 24 байта. В этом есть смысл. Мой 16-байтовый экземпляр плюс 8-байтовый заголовок объекта.
!DumpObj 0205b660
Name: Offset_Test.Program
MethodTable: 000d383c
EEClass: 000d13f8
Size: 24(0x18) bytes
File: C:\Users\Bob\Desktop\Offset_Test\Offset_Test\bin\Debug\Offset_Test.exe
Fields:
MT Field Offset Type VT Attr Value Name
632020fc 4000001 10 System.Int16 1 instance 2 myInt
632050d8 4000002 4 System.Int64 1 instance 3 myLong
631fd2b8 4000003 c System.String 0 instance 0205b678 myString
Вот необработанная память:
0x0205B660 000d383c 00000003 00000000 0205b678 00000002 ...
А вот некоторые аннотации:
offset 0 000d383c ;TypeHandle (pointer to MethodTable), 4 bytes
offset 4 00000003 00000000 ;myLong, 8 bytes
offset 12 0205b678 ;myString, 4 byte reference to address of "myString" on GC Heap
offset 16 00000002 ;myInt, 4 bytes
Мой объект начинает адрес 0x0205B660. Но я могу объяснить только 20 байтов, дескриптор типа и поля экземпляра. Нет признаков указателя блока синхронизации. Размер объекта составляет 24 байта, но отладчик показывает, что он занимает только 20 байтов памяти.
Я читаю Детализация внутренних компонентов .NET Framework, чтобы увидеть, как CLR создает объекты времени выполнения , и ожидал, что первые 4 байта моего объекта будут нулевым указателем блока синхронизации, как показано на рисунке 8 этой статьи. Конечно, это статья о CLR 1.1.
Мне просто интересно, если разница между тем, что я вижу, и тем, о чем говорится в этой ранней статье, заключается в изменении либо отображения отладчика макета объекта, либо способа, которым CLR выкладывает объекты в версиях более поздних, чем 1.1.
В любом случае, кто-нибудь может объяснить мои 4 пропущенных байта?