}
_ASSERTE(GetWriteableData());
- image->FixupPointerField(this, offsetof(MethodTable, m_pWriteableData));
- m_pWriteableData->Fixup(image, this, needsRestore);
+ image->FixupPlainOrRelativePointerField(this, &MethodTable::m_pWriteableData);
+ m_pWriteableData.GetValue()->Fixup(image, this, needsRestore);
#ifdef FEATURE_COMINTEROP
if (HasGuidInfo())
if (NeedsCrossModuleGenericsStaticsInfo())
{
- MethodTableWriteableData * pNewWriteableData = (MethodTableWriteableData *)image->GetImagePointer(m_pWriteableData);
+ MethodTableWriteableData * pNewWriteableData = (MethodTableWriteableData *)image->GetImagePointer(m_pWriteableData.GetValue());
CrossModuleGenericsStaticsInfo * pNewCrossModuleGenericsStaticsInfo = pNewWriteableData->GetCrossModuleGenericsStaticsInfo();
pNewCrossModuleGenericsStaticsInfo->m_DynamicTypeID = pInfo->m_DynamicTypeID;
- image->ZeroPointerField(m_pWriteableData, sizeof(MethodTableWriteableData) + offsetof(CrossModuleGenericsStaticsInfo, m_pModuleForStatics));
+ image->ZeroPointerField(m_pWriteableData.GetValue(), sizeof(MethodTableWriteableData) + offsetof(CrossModuleGenericsStaticsInfo, m_pModuleForStatics));
pNewMT->SetFlag(enum_flag_StaticsMask_IfGenericsThenCrossModule);
}
DacEnumMemoryRegion(dac_cast<TADDR>(it.GetIndirectionSlot()), it.GetSize());
}
- if (m_pWriteableData.IsValid())
+ PTR_MethodTableWriteableData pWriteableData = ReadPointer(this, &MethodTable::m_pWriteableData);
+ if (pWriteableData.IsValid())
{
- m_pWriteableData.EnumMem();
+ pWriteableData.EnumMem();
}
if (flags != CLRDATA_ENUM_MEM_MINI && flags != CLRDATA_ENUM_MEM_TRIAGE)
return false;
}
-#endif // !DACCESS_COMPILE
-
BOOL MethodTable::Validate()
ASSERT_AND_CHECK(SanityCheck());
#ifdef _DEBUG
- if (m_pWriteableData == NULL)
+ if (m_pWriteableData.IsNull())
{
_ASSERTE(IsAsyncPinType());
return TRUE;
}
- DWORD dwLastVerifiedGCCnt = m_pWriteableData->m_dwLastVerifedGCCnt;
+ MethodTableWriteableData *pWriteableData = m_pWriteableData.GetValue();
+ DWORD dwLastVerifiedGCCnt = pWriteableData->m_dwLastVerifedGCCnt;
// Here we used to assert that (dwLastVerifiedGCCnt <= GCHeapUtilities::GetGCHeap()->GetGcCount()) but
// this is no longer true because with background gc. Since the purpose of having
// m_dwLastVerifedGCCnt is just to only verify the same method table once for each GC
#ifdef _DEBUG
// It is not a fatal error to fail the update the counter. We will run slower and retry next time,
// but the system will function properly.
- if (EnsureWritablePagesNoThrow(m_pWriteableData, sizeof(MethodTableWriteableData)))
- m_pWriteableData->m_dwLastVerifedGCCnt = GCHeapUtilities::GetGCHeap()->GetGcCount();
+ if (EnsureWritablePagesNoThrow(pWriteableData, sizeof(MethodTableWriteableData)))
+ pWriteableData->m_dwLastVerifedGCCnt = GCHeapUtilities::GetGCHeap()->GetGcCount();
#endif //_DEBUG
return TRUE;
}
+#endif // !DACCESS_COMPILE
+
NOINLINE BYTE *MethodTable::GetLoaderAllocatorObjectForGC()
{
WRAPPER_NO_CONTRACT;
// Private part of MethodTable
// ------------------------------------------------------------------
+#ifndef DACCESS_COMPILE
inline void SetWriteableData(PTR_MethodTableWriteableData pMTWriteableData)
{
LIMITED_METHOD_CONTRACT;
_ASSERTE(pMTWriteableData);
- m_pWriteableData = pMTWriteableData;
+ m_pWriteableData.SetValue(pMTWriteableData);
}
-
+#endif
+
inline PTR_Const_MethodTableWriteableData GetWriteableData() const
{
LIMITED_METHOD_DAC_CONTRACT;
g_IBCLogger.LogMethodTableWriteableDataAccess(this);
- return m_pWriteableData;
+ return GetWriteableData_NoLogging();
}
inline PTR_Const_MethodTableWriteableData GetWriteableData_NoLogging() const
{
LIMITED_METHOD_DAC_CONTRACT;
- return m_pWriteableData;
+ return ReadPointer(this, &MethodTable::m_pWriteableData);
}
inline PTR_MethodTableWriteableData GetWriteableDataForWrite()
{
- LIMITED_METHOD_CONTRACT;
+ LIMITED_METHOD_DAC_CONTRACT;
g_IBCLogger.LogMethodTableWriteableDataWriteAccess(this);
- return m_pWriteableData;
+ return GetWriteableDataForWrite_NoLogging();
}
inline PTR_MethodTableWriteableData GetWriteableDataForWrite_NoLogging()
{
- return m_pWriteableData;
+ LIMITED_METHOD_DAC_CONTRACT;
+ return ReadPointer(this, &MethodTable::m_pWriteableData);
}
//-------------------------------------------------------------------
RelativePointer<PTR_Module> m_pLoaderModule; // LoaderModule. It is equal to the ZapModule in ngened images
- PTR_MethodTableWriteableData m_pWriteableData;
+#if defined(PLATFORM_UNIX) && defined(_TARGET_ARM_)
+ RelativePointer<PTR_MethodTableWriteableData> m_pWriteableData;
+#else
+ PlainPointer<PTR_MethodTableWriteableData> m_pWriteableData;
+#endif
// The value of lowest two bits describe what the union contains
enum LowBits {