diff options
author | Mukul Sabharwal <muks@microsoft.com> | 2019-02-22 15:56:28 -0800 |
---|---|---|
committer | Jan Kotas <jkotas@microsoft.com> | 2019-02-22 15:56:28 -0800 |
commit | 4932d0f6fa87b9a6e3293aacd35cecedde44d87a (patch) | |
tree | 0330e86de295b7d14c8db32478a8aff76147e685 /src | |
parent | 6a392d9084a1afe8b9861138e5d0e5b688deca44 (diff) | |
download | coreclr-4932d0f6fa87b9a6e3293aacd35cecedde44d87a.tar.gz coreclr-4932d0f6fa87b9a6e3293aacd35cecedde44d87a.tar.bz2 coreclr-4932d0f6fa87b9a6e3293aacd35cecedde44d87a.zip |
Enable FEATURE_BASICFREEZE (#22776)
Diffstat (limited to 'src')
-rw-r--r-- | src/System.Private.CoreLib/ILLinkTrim.xml | 5 | ||||
-rw-r--r-- | src/System.Private.CoreLib/src/System/GC.cs | 6 | ||||
-rw-r--r-- | src/gc/gc.cpp | 22 | ||||
-rw-r--r-- | src/gc/gc.h | 7 | ||||
-rw-r--r-- | src/gc/gcee.cpp | 16 | ||||
-rw-r--r-- | src/gc/gcimpl.h | 4 | ||||
-rw-r--r-- | src/gc/gcinterface.h | 3 | ||||
-rw-r--r-- | src/vm/comutilnative.cpp | 58 | ||||
-rw-r--r-- | src/vm/comutilnative.h | 8 | ||||
-rw-r--r-- | src/vm/ecalllist.h | 6 |
10 files changed, 107 insertions, 28 deletions
diff --git a/src/System.Private.CoreLib/ILLinkTrim.xml b/src/System.Private.CoreLib/ILLinkTrim.xml index 77f6e749b4..e334c3703e 100644 --- a/src/System.Private.CoreLib/ILLinkTrim.xml +++ b/src/System.Private.CoreLib/ILLinkTrim.xml @@ -5,6 +5,11 @@ instantiations to save in the ngen image. --> <method name="CommonlyUsedWinRTRedirectedInterfaceStubs" /> </type> + <type fullname="System.GC"> + <!-- Methods are used to register and unregister frozen segments. They are private and experimental. --> + <method name="_RegisterFrozenSegment" /> + <method name="_UnregisterFrozenSegment" /> + </type> <!-- Properties and methods used by a debugger. --> <type fullname="System.Threading.Tasks.Task"> <property name="ParentForDebugger" /> diff --git a/src/System.Private.CoreLib/src/System/GC.cs b/src/System.Private.CoreLib/src/System/GC.cs index 1e0268e905..98266b3349 100644 --- a/src/System.Private.CoreLib/src/System/GC.cs +++ b/src/System.Private.CoreLib/src/System/GC.cs @@ -319,6 +319,12 @@ namespace System return newSize; } + [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)] + private static extern IntPtr _RegisterFrozenSegment(IntPtr sectionAddress, int sectionSize); + + [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)] + private static extern IntPtr _UnregisterFrozenSegment(IntPtr segmentHandle); + [MethodImplAttribute(MethodImplOptions.InternalCall)] private static extern long _GetAllocatedBytesForCurrentThread(); diff --git a/src/gc/gc.cpp b/src/gc/gc.cpp index d7f8d6dfe5..d5a18b1785 100644 --- a/src/gc/gc.cpp +++ b/src/gc/gc.cpp @@ -23957,8 +23957,12 @@ uint8_t* tree_search (uint8_t* tree, uint8_t* old_address) bool gc_heap::frozen_object_p (Object* obj) { #ifdef MULTIPLE_HEAPS +#ifdef SEG_MAPPING_TABLE + heap_segment* pSegment = seg_mapping_table_segment_of((uint8_t*)obj); +#else ptrdiff_t delta = 0; heap_segment* pSegment = segment_of ((uint8_t*)obj, delta); +#endif #else //MULTIPLE_HEAPS heap_segment* pSegment = gc_heap::find_segment ((uint8_t*)obj, FALSE); _ASSERTE(pSegment); @@ -34523,24 +34527,6 @@ Object * GCHeap::NextObj (Object * object) #endif // VERIFY_HEAP } -#ifdef VERIFY_HEAP - -#ifdef FEATURE_BASICFREEZE -BOOL GCHeap::IsInFrozenSegment (Object * object) -{ - uint8_t* o = (uint8_t*)object; - heap_segment * hs = gc_heap::find_segment (o, FALSE); - //We create a frozen object for each frozen segment before the segment is inserted - //to segment list; during ngen, we could also create frozen objects in segments which - //don't belong to current GC heap. - //So we return true if hs is NULL. It might create a hole about detecting invalidate - //object. But given all other checks present, the hole should be very small - return !hs || heap_segment_read_only_p (hs); -} -#endif //FEATURE_BASICFREEZE - -#endif //VERIFY_HEAP - // returns TRUE if the pointer is in one of the GC heaps. bool GCHeap::IsHeapPointer (void* vpObject, bool small_heap_only) { diff --git a/src/gc/gc.h b/src/gc/gc.h index 7d63d4bc3a..225aa6ba58 100644 --- a/src/gc/gc.h +++ b/src/gc/gc.h @@ -264,13 +264,6 @@ public: { return mt->GetBaseSize() >= LARGE_OBJECT_SIZE; } - -protected: -public: -#if defined(FEATURE_BASICFREEZE) && defined(VERIFY_HEAP) - // Return TRUE if object lives in frozen segment - virtual BOOL IsInFrozenSegment (Object * object) = 0; -#endif // defined(FEATURE_BASICFREEZE) && defined(VERIFY_HEAP) }; // Go through and touch (read) each page straddled by a memory block. diff --git a/src/gc/gcee.cpp b/src/gc/gcee.cpp index bd5a8f6154..68310d5b6c 100644 --- a/src/gc/gcee.cpp +++ b/src/gc/gcee.cpp @@ -600,6 +600,22 @@ void GCHeap::UnregisterFrozenSegment(segment_handle seg) #endif // FEATURE_BASICFREEZE } +bool GCHeap::IsInFrozenSegment(Object *object) +{ +#ifdef FEATURE_BASICFREEZE + uint8_t* o = (uint8_t*)object; + heap_segment * hs = gc_heap::find_segment (o, FALSE); + //We create a frozen object for each frozen segment before the segment is inserted + //to segment list; during ngen, we could also create frozen objects in segments which + //don't belong to current GC heap. + //So we return true if hs is NULL. It might create a hole about detecting invalidate + //object. But given all other checks present, the hole should be very small + return !hs || heap_segment_read_only_p (hs); +#else // FEATURE_BASICFREEZE + return false; +#endif +} + bool GCHeap::RuntimeStructuresValid() { return GCScan::GetGcRuntimeStructuresValid(); diff --git a/src/gc/gcimpl.h b/src/gc/gcimpl.h index e70555da6f..dffe2f17aa 100644 --- a/src/gc/gcimpl.h +++ b/src/gc/gcimpl.h @@ -236,6 +236,7 @@ public: // FIX // frozen segment management functions virtual segment_handle RegisterFrozenSegment(segment_info *pseginfo); virtual void UnregisterFrozenSegment(segment_handle seg); + virtual bool IsInFrozenSegment(Object *object); // Event control functions void ControlEvents(GCEventKeyword keyword, GCEventLevel level); @@ -303,9 +304,6 @@ protected: public: Object * NextObj (Object * object); -#if defined (FEATURE_BASICFREEZE) && defined (VERIFY_HEAP) - BOOL IsInFrozenSegment (Object * object); -#endif // defined (FEATURE_BASICFREEZE) && defined (VERIFY_HEAP) }; #endif // GCIMPL_H_ diff --git a/src/gc/gcinterface.h b/src/gc/gcinterface.h index 3814702763..249466aee4 100644 --- a/src/gc/gcinterface.h +++ b/src/gc/gcinterface.h @@ -868,6 +868,9 @@ public: // Unregisters a frozen segment. virtual void UnregisterFrozenSegment(segment_handle seg) = 0; + // Indicates whether an object is in a frozen segment. + virtual bool IsInFrozenSegment(Object *object) = 0; + /* =========================================================================== Routines for informing the GC about which events are enabled. diff --git a/src/vm/comutilnative.cpp b/src/vm/comutilnative.cpp index 3ba0acefb9..aa2ed02a40 100644 --- a/src/vm/comutilnative.cpp +++ b/src/vm/comutilnative.cpp @@ -1238,6 +1238,64 @@ FCIMPL0(INT64, GCInterface::GetAllocatedBytesForCurrentThread) } FCIMPLEND +#ifdef FEATURE_BASICFREEZE + +/*===============================RegisterFrozenSegment=============================== +**Action: Registers the frozen segment +**Returns: segment_handle +**Arguments: args-> pointer to section, size of section +**Exceptions: None +==============================================================================*/ +void* QCALLTYPE GCInterface::RegisterFrozenSegment(void* pSection, INT32 sizeSection) +{ + QCALL_CONTRACT; + + void* retVal = nullptr; + + BEGIN_QCALL; + + _ASSERTE(pSection != nullptr); + _ASSERTE(sizeSection > 0); + + GCX_COOP(); + + segment_info seginfo; + seginfo.pvMem = pSection; + seginfo.ibFirstObject = sizeof(ObjHeader); + seginfo.ibAllocated = sizeSection; + seginfo.ibCommit = seginfo.ibAllocated; + seginfo.ibReserved = seginfo.ibAllocated; + + retVal = (void*)GCHeapUtilities::GetGCHeap()->RegisterFrozenSegment(&seginfo); + + END_QCALL; + + return retVal; +} + +/*===============================UnregisterFrozenSegment=============================== +**Action: Unregisters the frozen segment +**Returns: void +**Arguments: args-> segment handle +**Exceptions: None +==============================================================================*/ +void QCALLTYPE GCInterface::UnregisterFrozenSegment(void* segment) +{ + QCALL_CONTRACT; + + BEGIN_QCALL; + + _ASSERTE(segment != nullptr); + + GCX_COOP(); + + GCHeapUtilities::GetGCHeap()->UnregisterFrozenSegment((segment_handle)segment); + + END_QCALL; +} + +#endif // FEATURE_BASICFREEZE + /*==============================SuppressFinalize================================ **Action: Indicate that an object's finalizer should not be run by the system **Arguments: Object of interest diff --git a/src/vm/comutilnative.h b/src/vm/comutilnative.h index e632acfb97..67c111bbb4 100644 --- a/src/vm/comutilnative.h +++ b/src/vm/comutilnative.h @@ -140,6 +140,14 @@ public: static FCDECL0(INT64, GetAllocatedBytesForCurrentThread); +#ifdef FEATURE_BASICFREEZE + static + void* QCALLTYPE RegisterFrozenSegment(void *pSection, INT32 sizeSection); + + static + void QCALLTYPE UnregisterFrozenSegment(void *segmentHandle); +#endif // FEATURE_BASICFREEZE + static int QCALLTYPE StartNoGCRegion(INT64 totalSize, BOOL lohSizeKnown, INT64 lohSize, BOOL disallowFullBlockingGC); diff --git a/src/vm/ecalllist.h b/src/vm/ecalllist.h index 7e1dc6954b..cc07d0e570 100644 --- a/src/vm/ecalllist.h +++ b/src/vm/ecalllist.h @@ -771,6 +771,12 @@ FCFuncStart(gGCInterfaceFuncs) FCFuncElement("_ReRegisterForFinalize", GCInterface::ReRegisterForFinalize) FCFuncElement("_GetAllocatedBytesForCurrentThread", GCInterface::GetAllocatedBytesForCurrentThread) + +#ifdef FEATURE_BASICFREEZE + QCFuncElement("_RegisterFrozenSegment", GCInterface::RegisterFrozenSegment) + QCFuncElement("_UnregisterFrozenSegment", GCInterface::UnregisterFrozenSegment) +#endif // FEATURE_BASICFREEZE + FCFuncEnd() FCFuncStart(gGCSettingsFuncs) |