summaryrefslogtreecommitdiff
path: root/src/vm/i386/asmconstants.h
blob: 70f6e30c4a6284b7cfecbe205ea606e00a46d7c3 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information.
// asmconstants.h -
//
// This header defines field offsets and constants used by assembly code
// Be sure to rebuild clr/src/vm/ceemain.cpp after changing this file, to
// ensure that the constants match the expected C/C++ values

// 
// If you need to figure out a constant that has changed and is causing
// a compile-time assert, check out USE_COMPILE_TIME_CONSTANT_FINDER.
// TODO: put the constant finder in a common place so other platforms can use it.

#ifndef _TARGET_X86_ 
#error this file should only be used on an X86 platform
#endif

#include "../../inc/switches.h"

#ifndef ASMCONSTANTS_C_ASSERT
#define ASMCONSTANTS_C_ASSERT(cond)
#endif

#ifndef ASMCONSTANTS_RUNTIME_ASSERT
#define ASMCONSTANTS_RUNTIME_ASSERT(cond)
#endif

// Some contants are different in _DEBUG builds.  This macro factors out ifdefs from below.
#ifdef _DEBUG
#define DBG_FRE(dbg,fre) dbg
#else
#define DBG_FRE(dbg,fre) fre
#endif

#define INITIAL_SUCCESS_COUNT               0x100

#define DynamicHelperFrameFlags_Default     0
#define DynamicHelperFrameFlags_ObjectArg   1
#define DynamicHelperFrameFlags_ObjectArg2  2


// CONTEXT from rotor_pal.h
#define CONTEXT_Edi 0x9c
ASMCONSTANTS_C_ASSERT(CONTEXT_Edi == offsetof(CONTEXT,Edi))

#define CONTEXT_Esi 0xa0
ASMCONSTANTS_C_ASSERT(CONTEXT_Esi == offsetof(CONTEXT,Esi))

#define CONTEXT_Ebx 0xa4
ASMCONSTANTS_C_ASSERT(CONTEXT_Ebx == offsetof(CONTEXT,Ebx))

#define CONTEXT_Edx 0xa8
ASMCONSTANTS_C_ASSERT(CONTEXT_Edx == offsetof(CONTEXT,Edx))

#define CONTEXT_Eax 0xb0
ASMCONSTANTS_C_ASSERT(CONTEXT_Eax == offsetof(CONTEXT,Eax))

#define CONTEXT_Ebp 0xb4
ASMCONSTANTS_C_ASSERT(CONTEXT_Ebp == offsetof(CONTEXT,Ebp))

#define CONTEXT_Eip 0xb8
ASMCONSTANTS_C_ASSERT(CONTEXT_Eip == offsetof(CONTEXT,Eip))

#define CONTEXT_Esp 0xc4
ASMCONSTANTS_C_ASSERT(CONTEXT_Esp == offsetof(CONTEXT,Esp))

#ifndef WIN64EXCEPTIONS
// EHContext from clr/src/vm/i386/cgencpu.h
#define EHContext_Eax 0x00
ASMCONSTANTS_C_ASSERT(EHContext_Eax == offsetof(EHContext,Eax))

#define EHContext_Ebx 0x04
ASMCONSTANTS_C_ASSERT(EHContext_Ebx == offsetof(EHContext,Ebx))

#define EHContext_Ecx 0x08
ASMCONSTANTS_C_ASSERT(EHContext_Ecx == offsetof(EHContext,Ecx))

#define EHContext_Edx 0x0c
ASMCONSTANTS_C_ASSERT(EHContext_Edx == offsetof(EHContext,Edx))

#define EHContext_Esi 0x10
ASMCONSTANTS_C_ASSERT(EHContext_Esi == offsetof(EHContext,Esi))

#define EHContext_Edi 0x14
ASMCONSTANTS_C_ASSERT(EHContext_Edi == offsetof(EHContext,Edi))

#define EHContext_Ebp 0x18
ASMCONSTANTS_C_ASSERT(EHContext_Ebp == offsetof(EHContext,Ebp))

#define EHContext_Esp 0x1c
ASMCONSTANTS_C_ASSERT(EHContext_Esp == offsetof(EHContext,Esp))

#define EHContext_Eip 0x20
ASMCONSTANTS_C_ASSERT(EHContext_Eip == offsetof(EHContext,Eip))
#endif // WIN64EXCEPTIONS


// from clr/src/fjit/helperframe.h
#define SIZEOF_MachState          40
ASMCONSTANTS_C_ASSERT(SIZEOF_MachState == sizeof(MachState))

#define MachState__pEdi           0
ASMCONSTANTS_C_ASSERT(MachState__pEdi == offsetof(MachState, _pEdi))

#define MachState__edi            4
ASMCONSTANTS_C_ASSERT(MachState__edi == offsetof(MachState, _edi))

#define MachState__pEsi           8
ASMCONSTANTS_C_ASSERT(MachState__pEsi == offsetof(MachState, _pEsi))

#define MachState__esi            12
ASMCONSTANTS_C_ASSERT(MachState__esi == offsetof(MachState, _esi))

#define MachState__pEbx           16
ASMCONSTANTS_C_ASSERT(MachState__pEbx == offsetof(MachState, _pEbx))

#define MachState__ebx            20
ASMCONSTANTS_C_ASSERT(MachState__ebx == offsetof(MachState, _ebx))

#define MachState__pEbp           24
ASMCONSTANTS_C_ASSERT(MachState__pEbp == offsetof(MachState, _pEbp))

#define MachState__ebp            28
ASMCONSTANTS_C_ASSERT(MachState__ebp == offsetof(MachState, _ebp))

#define MachState__esp            32
ASMCONSTANTS_C_ASSERT(MachState__esp == offsetof(MachState, _esp))

#define MachState__pRetAddr       36
ASMCONSTANTS_C_ASSERT(MachState__pRetAddr == offsetof(MachState, _pRetAddr))

#define LazyMachState_captureEbp  40
ASMCONSTANTS_C_ASSERT(LazyMachState_captureEbp == offsetof(LazyMachState, captureEbp))

#define LazyMachState_captureEsp  44
ASMCONSTANTS_C_ASSERT(LazyMachState_captureEsp == offsetof(LazyMachState, captureEsp))

#define LazyMachState_captureEip  48
ASMCONSTANTS_C_ASSERT(LazyMachState_captureEip == offsetof(LazyMachState, captureEip))


#define VASigCookie__StubOffset 4
ASMCONSTANTS_C_ASSERT(VASigCookie__StubOffset == offsetof(VASigCookie, pNDirectILStub))

#define SIZEOF_TailCallFrame 32
ASMCONSTANTS_C_ASSERT(SIZEOF_TailCallFrame == sizeof(TailCallFrame))

#define SIZEOF_GSCookie 4

// ICodeManager::SHADOW_SP_IN_FILTER from clr/src/inc/eetwain.h
#define SHADOW_SP_IN_FILTER_ASM 0x1
ASMCONSTANTS_C_ASSERT(SHADOW_SP_IN_FILTER_ASM == ICodeManager::SHADOW_SP_IN_FILTER)

// from clr/src/inc/corinfo.h
#define CORINFO_NullReferenceException_ASM 0
ASMCONSTANTS_C_ASSERT(CORINFO_NullReferenceException_ASM == CORINFO_NullReferenceException)

#define CORINFO_IndexOutOfRangeException_ASM 3
ASMCONSTANTS_C_ASSERT(CORINFO_IndexOutOfRangeException_ASM == CORINFO_IndexOutOfRangeException)

#define CORINFO_OverflowException_ASM 4
ASMCONSTANTS_C_ASSERT(CORINFO_OverflowException_ASM == CORINFO_OverflowException)

#define CORINFO_ArrayTypeMismatchException_ASM 6
ASMCONSTANTS_C_ASSERT(CORINFO_ArrayTypeMismatchException_ASM == CORINFO_ArrayTypeMismatchException)

#define CORINFO_ArgumentNullException_ASM 8
ASMCONSTANTS_C_ASSERT(CORINFO_ArgumentNullException_ASM == CORINFO_ArgumentNullException)

#define CORINFO_ArgumentException_ASM 9
ASMCONSTANTS_C_ASSERT(CORINFO_ArgumentException_ASM == CORINFO_ArgumentException)


#ifndef CROSSGEN_COMPILE

// from clr/src/vm/threads.h
#define Thread_m_Context    0x38
ASMCONSTANTS_C_ASSERT(Thread_m_Context == offsetof(Thread, m_Context))

#define Thread_m_State      0x04
ASMCONSTANTS_C_ASSERT(Thread_m_State == offsetof(Thread, m_State))
#endif // CROSSGEN_COMPILE

#define Thread_m_fPreemptiveGCDisabled     0x08
#ifndef CROSSGEN_COMPILE
ASMCONSTANTS_C_ASSERT(Thread_m_fPreemptiveGCDisabled == offsetof(Thread, m_fPreemptiveGCDisabled))
#endif // CROSSGEN_COMPILE

#define Thread_m_pFrame     0x0C
#ifndef CROSSGEN_COMPILE
ASMCONSTANTS_C_ASSERT(Thread_m_pFrame == offsetof(Thread, m_pFrame))
#endif // CROSSGEN_COMPILE

#ifndef CROSSGEN_COMPILE
#define Thread_m_dwLockCount 0x18
ASMCONSTANTS_C_ASSERT(Thread_m_dwLockCount == offsetof(Thread, m_dwLockCount))

#define Thread_m_ThreadId 0x1C
ASMCONSTANTS_C_ASSERT(Thread_m_ThreadId == offsetof(Thread, m_ThreadId))

#ifdef FEATURE_HIJACK
#define TS_Hijacked_ASM 0x80
ASMCONSTANTS_C_ASSERT(Thread::TS_Hijacked == TS_Hijacked_ASM)
#endif

#endif // CROSSGEN_COMPILE


// from clr/src/vm/appdomain.hpp

#define AppDomain__m_dwId 0x4
ASMCONSTANTS_C_ASSERT(AppDomain__m_dwId == offsetof(AppDomain, m_dwId));

// This is the offset from EBP at which the original CONTEXT is stored in one of the 
// RedirectedHandledJITCase*_Stub functions.
#define REDIRECTSTUB_EBP_OFFSET_CONTEXT (-4)

#define MethodTable_m_wNumInterfaces    0x0E
ASMCONSTANTS_C_ASSERT(MethodTable_m_wNumInterfaces == offsetof(MethodTable, m_wNumInterfaces))

#define MethodTable_m_dwFlags           0x0
ASMCONSTANTS_C_ASSERT(MethodTable_m_dwFlags == offsetof(MethodTable, m_dwFlags))

#define MethodTable_m_pInterfaceMap     DBG_FRE(0x28, 0x24)
ASMCONSTANTS_C_ASSERT(MethodTable_m_pInterfaceMap == offsetof(MethodTable, m_pMultipurposeSlot2))

#define SIZEOF_MethodTable              DBG_FRE(0x2C, 0x28)
ASMCONSTANTS_C_ASSERT(SIZEOF_MethodTable == sizeof(MethodTable))

#define SIZEOF_InterfaceInfo_t          0x4
ASMCONSTANTS_C_ASSERT(SIZEOF_InterfaceInfo_t == sizeof(InterfaceInfo_t))

#ifdef FEATURE_COMINTEROP

#define SIZEOF_FrameHandlerExRecord 0x0c
#define OFFSETOF__FrameHandlerExRecord__m_ExReg__Next 0
#define OFFSETOF__FrameHandlerExRecord__m_ExReg__Handler 4
#define OFFSETOF__FrameHandlerExRecord__m_pEntryFrame 8
ASMCONSTANTS_C_ASSERT(SIZEOF_FrameHandlerExRecord == sizeof(FrameHandlerExRecord))
ASMCONSTANTS_C_ASSERT(OFFSETOF__FrameHandlerExRecord__m_ExReg__Next == offsetof(FrameHandlerExRecord, m_ExReg) + offsetof(EXCEPTION_REGISTRATION_RECORD, Next))
ASMCONSTANTS_C_ASSERT(OFFSETOF__FrameHandlerExRecord__m_ExReg__Handler == offsetof(FrameHandlerExRecord, m_ExReg) + offsetof(EXCEPTION_REGISTRATION_RECORD, Handler))
ASMCONSTANTS_C_ASSERT(OFFSETOF__FrameHandlerExRecord__m_pEntryFrame == offsetof(FrameHandlerExRecord, m_pEntryFrame))

#ifdef _DEBUG
#ifndef STACK_OVERWRITE_BARRIER_SIZE 
#define STACK_OVERWRITE_BARRIER_SIZE 20
#endif
#ifndef STACK_OVERWRITE_BARRIER_VALUE 
#define STACK_OVERWRITE_BARRIER_VALUE 0xabcdefab
#endif

#define SIZEOF_FrameHandlerExRecordWithBarrier 0x5c
ASMCONSTANTS_C_ASSERT(SIZEOF_FrameHandlerExRecordWithBarrier == sizeof(FrameHandlerExRecordWithBarrier))
#endif


#ifdef MDA_SUPPORTED
#define SIZEOF_StackImbalanceCookie 0x14
ASMCONSTANTS_C_ASSERT(SIZEOF_StackImbalanceCookie == sizeof(StackImbalanceCookie))

#define StackImbalanceCookie__m_pMD            0x00
#define StackImbalanceCookie__m_pTarget        0x04
#define StackImbalanceCookie__m_dwStackArgSize 0x08
#define StackImbalanceCookie__m_callConv       0x0c
#define StackImbalanceCookie__m_dwSavedEsp     0x10
#define StackImbalanceCookie__HAS_FP_RETURN_VALUE 0x80000000

ASMCONSTANTS_C_ASSERT(StackImbalanceCookie__m_pMD            == offsetof(StackImbalanceCookie, m_pMD))
ASMCONSTANTS_C_ASSERT(StackImbalanceCookie__m_pTarget        == offsetof(StackImbalanceCookie, m_pTarget))
ASMCONSTANTS_C_ASSERT(StackImbalanceCookie__m_dwStackArgSize == offsetof(StackImbalanceCookie, m_dwStackArgSize))
ASMCONSTANTS_C_ASSERT(StackImbalanceCookie__m_callConv       == offsetof(StackImbalanceCookie, m_callConv))
ASMCONSTANTS_C_ASSERT(StackImbalanceCookie__m_dwSavedEsp     == offsetof(StackImbalanceCookie, m_dwSavedEsp))
ASMCONSTANTS_C_ASSERT(StackImbalanceCookie__HAS_FP_RETURN_VALUE == StackImbalanceCookie::HAS_FP_RETURN_VALUE)
#endif // MDA_SUPPORTED

#define MethodDesc_m_wFlags                   DBG_FRE(0x1a, 0x06)
ASMCONSTANTS_C_ASSERT(MethodDesc_m_wFlags == offsetof(MethodDesc, m_wFlags))

#define MethodDesc_mdcClassification          7
ASMCONSTANTS_C_ASSERT(MethodDesc_mdcClassification == mdcClassification)

#define MethodDesc_mcComInterop               6
ASMCONSTANTS_C_ASSERT(MethodDesc_mcComInterop == mcComInterop)

#define ComPlusCallMethodDesc__m_pComPlusCallInfo DBG_FRE(0x1C, 0x8)
ASMCONSTANTS_C_ASSERT(ComPlusCallMethodDesc__m_pComPlusCallInfo == offsetof(ComPlusCallMethodDesc, m_pComPlusCallInfo))

#define ComPlusCallInfo__m_pRetThunk 0x10
ASMCONSTANTS_C_ASSERT(ComPlusCallInfo__m_pRetThunk == offsetof(ComPlusCallInfo, m_pRetThunk))

#endif // FEATURE_COMINTEROP

#define               NonTrivialInterfaceCastFlags (0x00080000 + 0x40000000 + 0x00400000)
ASMCONSTANTS_C_ASSERT(NonTrivialInterfaceCastFlags == MethodTable::public_enum_flag_NonTrivialInterfaceCast)

#define ASM__VTABLE_SLOTS_PER_CHUNK 8
ASMCONSTANTS_C_ASSERT(ASM__VTABLE_SLOTS_PER_CHUNK == VTABLE_SLOTS_PER_CHUNK)

#define ASM__VTABLE_SLOTS_PER_CHUNK_LOG2 3
ASMCONSTANTS_C_ASSERT(ASM__VTABLE_SLOTS_PER_CHUNK_LOG2 == VTABLE_SLOTS_PER_CHUNK_LOG2)

#define JIT_TailCall_StackOffsetToFlags       0x08

#define CallDescrData__pSrc                0x00
#define CallDescrData__numStackSlots       0x04
#define CallDescrData__pArgumentRegisters  0x08
#define CallDescrData__fpReturnSize        0x0C
#define CallDescrData__pTarget             0x10
#ifndef __GNUC__
#define CallDescrData__returnValue         0x18
#else
#define CallDescrData__returnValue         0x14
#endif

ASMCONSTANTS_C_ASSERT(CallDescrData__pSrc                 == offsetof(CallDescrData, pSrc))
ASMCONSTANTS_C_ASSERT(CallDescrData__numStackSlots        == offsetof(CallDescrData, numStackSlots))
ASMCONSTANTS_C_ASSERT(CallDescrData__pArgumentRegisters   == offsetof(CallDescrData, pArgumentRegisters))
ASMCONSTANTS_C_ASSERT(CallDescrData__fpReturnSize         == offsetof(CallDescrData, fpReturnSize))
ASMCONSTANTS_C_ASSERT(CallDescrData__pTarget              == offsetof(CallDescrData, pTarget))
ASMCONSTANTS_C_ASSERT(CallDescrData__returnValue          == offsetof(CallDescrData, returnValue))

#define               UMEntryThunk__m_pUMThunkMarshInfo     0x0C
ASMCONSTANTS_C_ASSERT(UMEntryThunk__m_pUMThunkMarshInfo == offsetof(UMEntryThunk, m_pUMThunkMarshInfo))

#define               UMEntryThunk__m_dwDomainId            0x10
ASMCONSTANTS_C_ASSERT(UMEntryThunk__m_dwDomainId == offsetof(UMEntryThunk, m_dwDomainId))

#define               UMThunkMarshInfo__m_pILStub           0x00
ASMCONSTANTS_C_ASSERT(UMThunkMarshInfo__m_pILStub == offsetof(UMThunkMarshInfo, m_pILStub))

#define               UMThunkMarshInfo__m_cbActualArgSize   0x04
ASMCONSTANTS_C_ASSERT(UMThunkMarshInfo__m_cbActualArgSize == offsetof(UMThunkMarshInfo, m_cbActualArgSize))

#ifdef FEATURE_STUBS_AS_IL
#define               UMThunkMarshInfo__m_cbRetPop   0x08
ASMCONSTANTS_C_ASSERT(UMThunkMarshInfo__m_cbRetPop == offsetof(UMThunkMarshInfo, m_cbRetPop))
#endif //FEATURE_STUBS_AS_IL

#ifndef CROSSGEN_COMPILE
#define               Thread__m_pDomain                     0x14
ASMCONSTANTS_C_ASSERT(Thread__m_pDomain == offsetof(Thread, m_pDomain));

#endif

#ifdef FEATURE_STUBS_AS_IL
// DelegateObject from src/vm/object.h
#define DelegateObject___target             0x04    // offset 0 is m_pMethTab of base class Object
#define DelegateObject___methodBase         0x08
#define DelegateObject___methodPtr          0x0c
#define DelegateObject___methodPtrAux       0x10
#define DelegateObject___invocationList     0x14
#define DelegateObject___invocationCount    0x18

ASMCONSTANTS_C_ASSERT(DelegateObject___target           == offsetof(DelegateObject, _target));
ASMCONSTANTS_C_ASSERT(DelegateObject___methodBase       == offsetof(DelegateObject, _methodBase));
ASMCONSTANTS_C_ASSERT(DelegateObject___methodPtr        == offsetof(DelegateObject, _methodPtr));
ASMCONSTANTS_C_ASSERT(DelegateObject___methodPtrAux     == offsetof(DelegateObject, _methodPtrAux));
ASMCONSTANTS_C_ASSERT(DelegateObject___invocationList   == offsetof(DelegateObject, _invocationList));
ASMCONSTANTS_C_ASSERT(DelegateObject___invocationCount  == offsetof(DelegateObject, _invocationCount));

#endif

#ifndef CROSSGEN_COMPILE
// ResolveCacheElem from src/vm/virtualcallstub.h
#define ResolveCacheElem__pMT               0x00
#define ResolveCacheElem__token             0x04
#define ResolveCacheElem__target            0x08
#define ResolveCacheElem__pNext             0x0C

ASMCONSTANTS_C_ASSERT(ResolveCacheElem__pMT     == offsetof(ResolveCacheElem, pMT));
ASMCONSTANTS_C_ASSERT(ResolveCacheElem__token   == offsetof(ResolveCacheElem, token));
ASMCONSTANTS_C_ASSERT(ResolveCacheElem__target  == offsetof(ResolveCacheElem, target));
ASMCONSTANTS_C_ASSERT(ResolveCacheElem__pNext   == offsetof(ResolveCacheElem, pNext));

#endif // !CROSSGEN_COMPILE

#undef ASMCONSTANTS_C_ASSERT
#undef ASMCONSTANTS_RUNTIME_ASSERT

// #define USE_COMPILE_TIME_CONSTANT_FINDER // Uncomment this line to use the constant finder
#if defined(__cplusplus) && defined(USE_COMPILE_TIME_CONSTANT_FINDER)
// This class causes the compiler to emit an error with the constant we're interested in
// in the error message. This is useful if a size or offset changes. To use, comment out
// the compile-time assert that is firing, enable the constant finder, add the appropriate
// constant to find to BogusFunction(), and build.
// 
// Here's a sample compiler error:
// d:\dd\clr\src\ndp\clr\src\vm\i386\asmconstants.h(326) : error C2248: 'FindCompileTimeConstant<N>::FindCompileTimeConstant' : cannot access private member declared in class 'FindCompileTimeConstant<N>'
//         with
//         [
//             N=1520
//         ]
//         d:\dd\clr\src\ndp\clr\src\vm\i386\asmconstants.h(321) : see declaration of 'FindCompileTimeConstant<N>::FindCompileTimeConstant'
//         with
//         [
//             N=1520
//         ]
template<size_t N>
class FindCompileTimeConstant
{
private:
	FindCompileTimeConstant();
};

void BogusFunction()
{
	// Sample usage to generate the error
	FindCompileTimeConstant<offsetof(AppDomain, m_dwId)> bogus_variable;
}
#endif // defined(__cplusplus) && defined(USE_COMPILE_TIME_CONSTANT_FINDER)