Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/dotnet/runtime.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'src/coreclr/vm/jitinterface.cpp')
-rw-r--r--src/coreclr/vm/jitinterface.cpp116
1 files changed, 38 insertions, 78 deletions
diff --git a/src/coreclr/vm/jitinterface.cpp b/src/coreclr/vm/jitinterface.cpp
index 9c8d9cbe59c..e39d70e9910 100644
--- a/src/coreclr/vm/jitinterface.cpp
+++ b/src/coreclr/vm/jitinterface.cpp
@@ -1480,6 +1480,8 @@ void CEEInfo::getFieldInfo (CORINFO_RESOLVED_TOKEN * pResolvedToken,
DWORD fieldFlags = 0;
pResult->offset = pField->GetOffset();
+ pResult->fieldLookup.addr = nullptr;
+
if (pField->IsStatic())
{
fieldFlags |= CORINFO_FLG_FIELD_STATIC;
@@ -1496,16 +1498,17 @@ void CEEInfo::getFieldInfo (CORINFO_RESOLVED_TOKEN * pResolvedToken,
// Provide helper to use if the JIT is not able to emit the TLS access
// as intrinsic
pResult->helper = CORINFO_HELP_GETSTATICFIELDADDR_TLS;
-
pResult->offset = module->GetFieldTlsOffset(pResult->offset);
}
else
{
fieldAccessor = CORINFO_FIELD_STATIC_RVA_ADDRESS;
+ pResult->fieldLookup.addr = pField->GetStaticAddressHandle(NULL);
+ pResult->fieldLookup.accessType = IAT_VALUE;
}
// We are not going through a helper. The constructor has to be triggered explicitly.
- if (!pFieldMT->IsClassPreInited())
+ if (!pFieldMT->IsClassInited())
fieldFlags |= CORINFO_FLG_FIELD_INITCLASS;
}
else
@@ -1545,9 +1548,41 @@ void CEEInfo::getFieldInfo (CORINFO_RESOLVED_TOKEN * pResolvedToken,
{
fieldAccessor = CORINFO_FIELD_STATIC_ADDRESS;
+ // Allocate space for the local class if necessary, but don't trigger
+ // class construction.
+ DomainLocalModule* pLocalModule = pFieldMT->GetDomainLocalModule();
+ pLocalModule->PopulateClass(pFieldMT);
+
// We are not going through a helper. The constructor has to be triggered explicitly.
- if (!pFieldMT->IsClassPreInited())
+ if (!pFieldMT->IsClassInited())
fieldFlags |= CORINFO_FLG_FIELD_INITCLASS;
+
+ GCX_COOP();
+
+ pResult->fieldLookup.addr = pField->GetStaticAddressHandle((void*)pField->GetBase());
+ if (fieldFlags & CORINFO_FLG_FIELD_STATIC_IN_HEAP)
+ {
+ Object* frozenObj = VolatileLoad((Object**)pResult->fieldLookup.addr);
+
+ if (frozenObj == nullptr)
+ {
+ // Boxed static is not yet set, allocate it
+ pFieldMT->AllocateRegularStaticBox(pField, (BYTE*)pResult->fieldLookup.addr);
+ frozenObj = VolatileLoad((Object**)pResult->fieldLookup.addr);
+ }
+
+ _ASSERT(frozenObj != nullptr);
+
+ // ContainsPointers here is unnecessary but it's cheaper than IsInFrozenSegment
+ // for structs containing gc handles
+ if (!frozenObj->GetMethodTable()->ContainsPointers() &&
+ GCHeapUtilities::GetGCHeap()->IsInFrozenSegment(frozenObj))
+ {
+ pResult->fieldLookup.addr = frozenObj->GetData();
+ fieldFlags &= ~CORINFO_FLG_FIELD_STATIC_IN_HEAP;
+ }
+ }
+ pResult->fieldLookup.accessType = IAT_VALUE;
}
}
@@ -11963,54 +11998,6 @@ InfoAccessType CEEJitInfo::emptyStringLiteral(void ** ppValue)
return result;
}
-/*********************************************************************/
-void* CEEJitInfo::getFieldAddress(CORINFO_FIELD_HANDLE fieldHnd,
- void **ppIndirection)
-{
- CONTRACTL {
- THROWS;
- GC_TRIGGERS;
- MODE_PREEMPTIVE;
- } CONTRACTL_END;
-
- void *result = NULL;
-
- if (ppIndirection != NULL)
- *ppIndirection = NULL;
-
- JIT_TO_EE_TRANSITION();
-
- FieldDesc* field = (FieldDesc*) fieldHnd;
-
- MethodTable* pMT = field->GetEnclosingMethodTable();
-
- _ASSERTE(!pMT->ContainsGenericVariables());
-
- void *base = NULL;
-
- if (!field->IsRVA())
- {
- // <REVISIT_TODO>@todo: assert that the current method being compiled is unshared</REVISIT_TODO>
- // We must not call here for statics of collectible types.
- _ASSERTE(!pMT->Collectible());
-
- // Allocate space for the local class if necessary, but don't trigger
- // class construction.
- DomainLocalModule *pLocalModule = pMT->GetDomainLocalModule();
- pLocalModule->PopulateClass(pMT);
-
- GCX_COOP();
-
- base = (void *) field->GetBase();
- }
-
- result = field->GetStaticAddressHandle(base);
-
- EE_TO_JIT_TRANSITION();
-
- return result;
-}
-
bool CEEInfo::getReadonlyStaticFieldValue(CORINFO_FIELD_HANDLE fieldHnd, uint8_t* buffer, int bufferSize, bool ignoreMovableObjects)
{
CONTRACTL {
@@ -14562,33 +14549,6 @@ InfoAccessType CEEInfo::emptyStringLiteral(void ** ppValue)
UNREACHABLE(); // only called on derived class.
}
-void* CEEInfo::getFieldAddress(CORINFO_FIELD_HANDLE fieldHnd,
- void **ppIndirection)
-{
- CONTRACTL{
- THROWS;
- GC_TRIGGERS;
- MODE_PREEMPTIVE;
- } CONTRACTL_END;
-
- void *result = NULL;
-
- if (ppIndirection != NULL)
- *ppIndirection = NULL;
-
- JIT_TO_EE_TRANSITION();
-
- FieldDesc* field = (FieldDesc*)fieldHnd;
-
- _ASSERTE(field->IsRVA());
-
- result = field->GetStaticAddressHandle(NULL);
-
- EE_TO_JIT_TRANSITION();
-
- return result;
-}
-
CORINFO_CLASS_HANDLE CEEInfo::getStaticFieldCurrentClass(CORINFO_FIELD_HANDLE fieldHnd,
bool* pIsSpeculative)
{