diff options
Diffstat (limited to 'src/gc/objecthandle.h')
-rw-r--r-- | src/gc/objecthandle.h | 686 |
1 files changed, 686 insertions, 0 deletions
diff --git a/src/gc/objecthandle.h b/src/gc/objecthandle.h new file mode 100644 index 0000000000..89365267d6 --- /dev/null +++ b/src/gc/objecthandle.h @@ -0,0 +1,686 @@ +// 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. + +/* + * Wraps handle table to implement various handle types (Strong, Weak, etc.) + * + + * + */ + +#ifndef _OBJECTHANDLE_H +#define _OBJECTHANDLE_H + +/* + * include handle manager declarations + */ +#include "handletable.h" + +#ifdef FEATURE_COMINTEROP +#include <weakreference.h> +#endif // FEATURE_COMINTEROP + +/* + * Convenience macros for accessing handles. StoreFirstObjectInHandle is like + * StoreObjectInHandle, except it only succeeds if transitioning from NULL to + * non-NULL. In other words, if this handle is being initialized for the first + * time. + */ +#define ObjectFromHandle(handle) HndFetchHandle(handle) +#define StoreObjectInHandle(handle, object) HndAssignHandle(handle, object) +#define InterlockedCompareExchangeObjectInHandle(handle, object, oldObj) HndInterlockedCompareExchangeHandle(handle, object, oldObj) +#define StoreFirstObjectInHandle(handle, object) HndFirstAssignHandle(handle, object) +#define ObjectHandleIsNull(handle) HndIsNull(handle) +#define IsHandleNullUnchecked(handle) HndCheckForNullUnchecked(handle) + + +/* + * HANDLES + * + * The default type of handle is a strong handle. + * + */ +#define HNDTYPE_DEFAULT HNDTYPE_STRONG + + +/* + * WEAK HANDLES + * + * Weak handles are handles that track an object as long as it is alive, + * but do not keep the object alive if there are no strong references to it. + * + * The default type of weak handle is 'long-lived' weak handle. + * + */ +#define HNDTYPE_WEAK_DEFAULT HNDTYPE_WEAK_LONG + + +/* + * SHORT-LIVED WEAK HANDLES + * + * Short-lived weak handles are weak handles that track an object until the + * first time it is detected to be unreachable. At this point, the handle is + * severed, even if the object will be visible from a pending finalization + * graph. This further implies that short weak handles do not track + * across object resurrections. + * + */ +#define HNDTYPE_WEAK_SHORT (0) + + +/* + * LONG-LIVED WEAK HANDLES + * + * Long-lived weak handles are weak handles that track an object until the + * object is actually reclaimed. Unlike short weak handles, long weak handles + * continue to track their referents through finalization and across any + * resurrections that may occur. + * + */ +#define HNDTYPE_WEAK_LONG (1) + + +/* + * STRONG HANDLES + * + * Strong handles are handles which function like a normal object reference. + * The existence of a strong handle for an object will cause the object to + * be promoted (remain alive) through a garbage collection cycle. + * + */ +#define HNDTYPE_STRONG (2) + + +/* + * PINNED HANDLES + * + * Pinned handles are strong handles which have the added property that they + * prevent an object from moving during a garbage collection cycle. This is + * useful when passing a pointer to object innards out of the runtime while GC + * may be enabled. + * + * NOTE: PINNING AN OBJECT IS EXPENSIVE AS IT PREVENTS THE GC FROM ACHIEVING + * OPTIMAL PACKING OF OBJECTS DURING EPHEMERAL COLLECTIONS. THIS TYPE + * OF HANDLE SHOULD BE USED SPARINGLY! + */ +#define HNDTYPE_PINNED (3) + + +/* + * VARIABLE HANDLES + * + * Variable handles are handles whose type can be changed dynamically. They + * are larger than other types of handles, and are scanned a little more often, + * but are useful when the handle owner needs an efficient way to change the + * strength of a handle on the fly. + * + */ +#define HNDTYPE_VARIABLE (4) + +#if defined(FEATURE_COMINTEROP) || defined(FEATURE_REDHAWK) +/* + * REFCOUNTED HANDLES + * + * Refcounted handles are handles that behave as strong handles while the + * refcount on them is greater than 0 and behave as weak handles otherwise. + * + * N.B. These are currently NOT general purpose. + * The implementation is tied to COM Interop. + * + */ +#define HNDTYPE_REFCOUNTED (5) +#endif // FEATURE_COMINTEROP || FEATURE_REDHAWK + + +/* + * DEPENDENT HANDLES + * + * Dependent handles are two handles that need to have the same lifetime. One handle refers to a secondary object + * that needs to have the same lifetime as the primary object. The secondary object should not cause the primary + * object to be referenced, but as long as the primary object is alive, so must be the secondary + * + * They are currently used for EnC for adding new field members to existing instantiations under EnC modes where + * the primary object is the original instantiation and the secondary represents the added field. + * + * They are also used to implement the ConditionalWeakTable class in mscorlib.dll. If you want to use + * these from managed code, they are exposed to BCL through the managed DependentHandle class. + * + * + */ +#define HNDTYPE_DEPENDENT (6) + +/* + * PINNED HANDLES for asynchronous operation + * + * Pinned handles are strong handles which have the added property that they + * prevent an object from moving during a garbage collection cycle. This is + * useful when passing a pointer to object innards out of the runtime while GC + * may be enabled. + * + * NOTE: PINNING AN OBJECT IS EXPENSIVE AS IT PREVENTS THE GC FROM ACHIEVING + * OPTIMAL PACKING OF OBJECTS DURING EPHEMERAL COLLECTIONS. THIS TYPE + * OF HANDLE SHOULD BE USED SPARINGLY! + */ +#define HNDTYPE_ASYNCPINNED (7) + + +/* + * SIZEDREF HANDLES + * + * SizedRef handles are strong handles. Each handle has a piece of user data associated + * with it that stores the size of the object this handle refers to. These handles + * are scanned as strong roots during each GC but only during full GCs would the size + * be calculated. + * + */ +#define HNDTYPE_SIZEDREF (8) + +#ifdef FEATURE_COMINTEROP + +/* + * WINRT WEAK HANDLES + * + * WinRT weak reference handles hold two different types of weak handles to any + * RCW with an underlying COM object that implements IWeakReferenceSource. The + * object reference itself is a short weak handle to the RCW. In addition an + * IWeakReference* to the underlying COM object is stored, allowing the handle + * to create a new RCW if the existing RCW is collected. This ensures that any + * code holding onto a WinRT weak reference can always access an RCW to the + * underlying COM object as long as it has not been released by all of its strong + * references. + */ +#define HNDTYPE_WEAK_WINRT (9) + +#endif // FEATURE_COMINTEROP + +typedef DPTR(struct HandleTableMap) PTR_HandleTableMap; +typedef DPTR(struct HandleTableBucket) PTR_HandleTableBucket; +typedef DPTR(PTR_HandleTableBucket) PTR_PTR_HandleTableBucket; + +struct HandleTableMap +{ + PTR_PTR_HandleTableBucket pBuckets; + PTR_HandleTableMap pNext; + uint32_t dwMaxIndex; +}; + +GVAL_DECL(HandleTableMap, g_HandleTableMap); + +#define INITIAL_HANDLE_TABLE_ARRAY_SIZE 10 + +// struct containing g_SystemInfo.dwNumberOfProcessors HHANDLETABLEs and current table index +// instead of just single HHANDLETABLE for on-fly balancing while adding handles on multiproc machines + +struct HandleTableBucket +{ + PTR_HHANDLETABLE pTable; + uint32_t HandleTableIndex; + + bool Contains(OBJECTHANDLE handle); +}; + + +/* + * Type mask definitions for HNDTYPE_VARIABLE handles. + */ +#define VHT_WEAK_SHORT (0x00000100) // avoid using low byte so we don't overlap normal types +#define VHT_WEAK_LONG (0x00000200) // avoid using low byte so we don't overlap normal types +#define VHT_STRONG (0x00000400) // avoid using low byte so we don't overlap normal types +#define VHT_PINNED (0x00000800) // avoid using low byte so we don't overlap normal types + +#define IS_VALID_VHT_VALUE(flag) ((flag == VHT_WEAK_SHORT) || \ + (flag == VHT_WEAK_LONG) || \ + (flag == VHT_STRONG) || \ + (flag == VHT_PINNED)) + +#ifndef DACCESS_COMPILE +/* + * Convenience macros and prototypes for the various handle types we define + */ + +inline OBJECTHANDLE CreateTypedHandle(HHANDLETABLE table, OBJECTREF object, int type) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, type, object); +} + +inline void DestroyTypedHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandleOfUnknownType(HndGetHandleTable(handle), handle); +} + +inline OBJECTHANDLE CreateHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_DEFAULT, object); +} + +inline void DestroyHandle(OBJECTHANDLE handle) +{ + CONTRACTL + { + NOTHROW; + GC_NOTRIGGER; + MODE_ANY; + CAN_TAKE_LOCK; + SO_TOLERANT; + } + CONTRACTL_END; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_DEFAULT, handle); +} + +inline OBJECTHANDLE CreateDuplicateHandle(OBJECTHANDLE handle) { + WRAPPER_NO_CONTRACT; + + // Create a new STRONG handle in the same table as an existing handle. + return HndCreateHandle(HndGetHandleTable(handle), HNDTYPE_DEFAULT, ObjectFromHandle(handle)); +} + + +inline OBJECTHANDLE CreateWeakHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_WEAK_DEFAULT, object); +} + +inline void DestroyWeakHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_WEAK_DEFAULT, handle); +} + +inline OBJECTHANDLE CreateShortWeakHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_WEAK_SHORT, object); +} + +inline void DestroyShortWeakHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_WEAK_SHORT, handle); +} + + +inline OBJECTHANDLE CreateLongWeakHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_WEAK_LONG, object); +} + +inline void DestroyLongWeakHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_WEAK_LONG, handle); +} + +#ifndef FEATURE_REDHAWK +typedef Holder<OBJECTHANDLE,DoNothing<OBJECTHANDLE>,DestroyLongWeakHandle> LongWeakHandleHolder; +#endif + +inline OBJECTHANDLE CreateStrongHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_STRONG, object); +} + +inline void DestroyStrongHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_STRONG, handle); +} + +inline OBJECTHANDLE CreatePinningHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_PINNED, object); +} + +inline void DestroyPinningHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_PINNED, handle); +} + +#ifndef FEATURE_REDHAWK +typedef Wrapper<OBJECTHANDLE, DoNothing<OBJECTHANDLE>, DestroyPinningHandle, NULL> PinningHandleHolder; +#endif + +inline OBJECTHANDLE CreateAsyncPinningHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_ASYNCPINNED, object); +} + +inline void DestroyAsyncPinningHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_ASYNCPINNED, handle); +} + +#ifndef FEATURE_REDHAWK +typedef Wrapper<OBJECTHANDLE, DoNothing<OBJECTHANDLE>, DestroyAsyncPinningHandle, NULL> AsyncPinningHandleHolder; +#endif + +inline OBJECTHANDLE CreateSizedRefHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_SIZEDREF, object, (uintptr_t)0); +} + +void DestroySizedRefHandle(OBJECTHANDLE handle); + +#ifndef FEATURE_REDHAWK +typedef Wrapper<OBJECTHANDLE, DoNothing<OBJECTHANDLE>, DestroySizedRefHandle, NULL> SizeRefHandleHolder; +#endif + +#ifdef FEATURE_COMINTEROP +inline OBJECTHANDLE CreateRefcountedHandle(HHANDLETABLE table, OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(table, HNDTYPE_REFCOUNTED, object); +} + +inline void DestroyRefcountedHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_REFCOUNTED, handle); +} + +inline OBJECTHANDLE CreateWinRTWeakHandle(HHANDLETABLE table, OBJECTREF object, IWeakReference* pWinRTWeakReference) +{ + WRAPPER_NO_CONTRACT; + _ASSERTE(pWinRTWeakReference != NULL); + return HndCreateHandle(table, HNDTYPE_WEAK_WINRT, object, reinterpret_cast<uintptr_t>(pWinRTWeakReference)); +} + +void DestroyWinRTWeakHandle(OBJECTHANDLE handle); + +#endif // FEATURE_COMINTEROP + +#endif // !DACCESS_COMPILE + +OBJECTREF GetDependentHandleSecondary(OBJECTHANDLE handle); + +#ifndef DACCESS_COMPILE +OBJECTHANDLE CreateDependentHandle(HHANDLETABLE table, OBJECTREF primary, OBJECTREF secondary); +void SetDependentHandleSecondary(OBJECTHANDLE handle, OBJECTREF secondary); + +inline void DestroyDependentHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_DEPENDENT, handle); +} +#endif // !DACCESS_COMPILE + +#ifndef DACCESS_COMPILE + +OBJECTHANDLE CreateVariableHandle(HHANDLETABLE hTable, OBJECTREF object, uint32_t type); +uint32_t GetVariableHandleType(OBJECTHANDLE handle); +void UpdateVariableHandleType(OBJECTHANDLE handle, uint32_t type); +uint32_t CompareExchangeVariableHandleType(OBJECTHANDLE handle, uint32_t oldType, uint32_t newType); + +inline void DestroyVariableHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_VARIABLE, handle); +} + +void GCHandleValidatePinnedObject(OBJECTREF obj); + +/* + * Holder for OBJECTHANDLE + */ + +#ifndef FEATURE_REDHAWK +typedef Wrapper<OBJECTHANDLE, DoNothing<OBJECTHANDLE>, DestroyHandle > OHWrapper; + +class OBJECTHANDLEHolder : public OHWrapper +{ +public: + FORCEINLINE OBJECTHANDLEHolder(OBJECTHANDLE p = NULL) : OHWrapper(p) + { + LIMITED_METHOD_CONTRACT; + } + FORCEINLINE void operator=(OBJECTHANDLE p) + { + WRAPPER_NO_CONTRACT; + + OHWrapper::operator=(p); + } +}; +#endif + +#ifdef FEATURE_COMINTEROP + +typedef Wrapper<OBJECTHANDLE, DoNothing<OBJECTHANDLE>, DestroyRefcountedHandle> RefCountedOHWrapper; + +class RCOBJECTHANDLEHolder : public RefCountedOHWrapper +{ +public: + FORCEINLINE RCOBJECTHANDLEHolder(OBJECTHANDLE p = NULL) : RefCountedOHWrapper(p) + { + LIMITED_METHOD_CONTRACT; + } + FORCEINLINE void operator=(OBJECTHANDLE p) + { + WRAPPER_NO_CONTRACT; + + RefCountedOHWrapper::operator=(p); + } +}; + +#endif // FEATURE_COMINTEROP +/* + * Convenience prototypes for using the global handles + */ + +int GetCurrentThreadHomeHeapNumber(); + +inline OBJECTHANDLE CreateGlobalTypedHandle(OBJECTREF object, int type) +{ + WRAPPER_NO_CONTRACT; + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], type, object); +} + +inline void DestroyGlobalTypedHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandleOfUnknownType(HndGetHandleTable(handle), handle); +} + +inline OBJECTHANDLE CreateGlobalHandle(OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + CONDITIONAL_CONTRACT_VIOLATION(ModeViolation, object == NULL); + + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], HNDTYPE_DEFAULT, object); +} + +inline void DestroyGlobalHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_DEFAULT, handle); +} + +inline OBJECTHANDLE CreateGlobalWeakHandle(OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], HNDTYPE_WEAK_DEFAULT, object); +} + +inline void DestroyGlobalWeakHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_WEAK_DEFAULT, handle); +} + +inline OBJECTHANDLE CreateGlobalShortWeakHandle(OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + CONDITIONAL_CONTRACT_VIOLATION(ModeViolation, object == NULL); + + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], HNDTYPE_WEAK_SHORT, object); +} + +inline void DestroyGlobalShortWeakHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_WEAK_SHORT, handle); +} + +#ifndef FEATURE_REDHAWK +typedef Holder<OBJECTHANDLE,DoNothing<OBJECTHANDLE>,DestroyGlobalShortWeakHandle> GlobalShortWeakHandleHolder; +#endif + +inline OBJECTHANDLE CreateGlobalLongWeakHandle(OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], HNDTYPE_WEAK_LONG, object); +} + +inline void DestroyGlobalLongWeakHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_WEAK_LONG, handle); +} + +inline OBJECTHANDLE CreateGlobalStrongHandle(OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + CONDITIONAL_CONTRACT_VIOLATION(ModeViolation, object == NULL); + + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], HNDTYPE_STRONG, object); +} + +inline void DestroyGlobalStrongHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_STRONG, handle); +} + +#ifndef FEATURE_REDHAWK +typedef Holder<OBJECTHANDLE,DoNothing<OBJECTHANDLE>,DestroyGlobalStrongHandle> GlobalStrongHandleHolder; +#endif + +inline OBJECTHANDLE CreateGlobalPinningHandle(OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], HNDTYPE_PINNED, object); +} + +inline void DestroyGlobalPinningHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_PINNED, handle); +} + +#ifdef FEATURE_COMINTEROP +inline OBJECTHANDLE CreateGlobalRefcountedHandle(OBJECTREF object) +{ + WRAPPER_NO_CONTRACT; + + return HndCreateHandle(g_HandleTableMap.pBuckets[0]->pTable[GetCurrentThreadHomeHeapNumber()], HNDTYPE_REFCOUNTED, object); +} + +inline void DestroyGlobalRefcountedHandle(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + HndDestroyHandle(HndGetHandleTable(handle), HNDTYPE_REFCOUNTED, handle); +} +#endif // FEATURE_COMINTEROP + +inline void ResetOBJECTHANDLE(OBJECTHANDLE handle) +{ + WRAPPER_NO_CONTRACT; + + StoreObjectInHandle(handle, NULL); +} + +#ifndef FEATURE_REDHAWK +typedef Holder<OBJECTHANDLE,DoNothing<OBJECTHANDLE>,ResetOBJECTHANDLE> ObjectInHandleHolder; +#endif + +/* + * Table maintenance routines + */ +bool Ref_Initialize(); +void Ref_Shutdown(); +HandleTableBucket *Ref_CreateHandleTableBucket(ADIndex uADIndex); +BOOL Ref_HandleAsyncPinHandles(); +void Ref_RelocateAsyncPinHandles(HandleTableBucket *pSource, HandleTableBucket *pTarget); +void Ref_RemoveHandleTableBucket(HandleTableBucket *pBucket); +void Ref_DestroyHandleTableBucket(HandleTableBucket *pBucket); +BOOL Ref_ContainHandle(HandleTableBucket *pBucket, OBJECTHANDLE handle); + +/* + * GC-time scanning entrypoints + */ +struct ScanContext; +struct DhContext; +struct ProfilingScanContext; +void Ref_BeginSynchronousGC (uint32_t uCondemnedGeneration, uint32_t uMaxGeneration); +void Ref_EndSynchronousGC (uint32_t uCondemnedGeneration, uint32_t uMaxGeneration); + +typedef void Ref_promote_func(class Object**, ScanContext*, uint32_t); + +void Ref_TraceRefCountHandles(HANDLESCANPROC callback, uintptr_t lParam1, uintptr_t lParam2); +void Ref_TracePinningRoots(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +void Ref_TraceNormalRoots(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +void Ref_UpdatePointers(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +void Ref_UpdatePinnedPointers(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +DhContext *Ref_GetDependentHandleContext(ScanContext* sc); +bool Ref_ScanDependentHandlesForPromotion(DhContext *pDhContext); +void Ref_ScanDependentHandlesForClearing(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +void Ref_ScanDependentHandlesForRelocation(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +void Ref_ScanSizedRefHandles(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +#ifdef FEATURE_REDHAWK +void Ref_ScanPointers(uint32_t condemned, uint32_t maxgen, ScanContext* sc, Ref_promote_func* fn); +#endif + +void Ref_CheckReachable (uint32_t uCondemnedGeneration, uint32_t uMaxGeneration, uintptr_t lp1); +void Ref_CheckAlive (uint32_t uCondemnedGeneration, uint32_t uMaxGeneration, uintptr_t lp1); +void Ref_ScanPointersForProfilerAndETW(uint32_t uMaxGeneration, uintptr_t lp1); +void Ref_ScanDependentHandlesForProfilerAndETW(uint32_t uMaxGeneration, ProfilingScanContext * SC); +void Ref_AgeHandles (uint32_t uCondemnedGeneration, uint32_t uMaxGeneration, uintptr_t lp1); +void Ref_RejuvenateHandles(uint32_t uCondemnedGeneration, uint32_t uMaxGeneration, uintptr_t lp1); + +void Ref_VerifyHandleTable(uint32_t condemned, uint32_t maxgen, ScanContext* sc); + +#endif // DACCESS_COMPILE + +#endif //_OBJECTHANDLE_H |