2020#include " objecthandle.h"
2121#include " handletablepriv.h"
2222
23- #ifndef FEATURE_REDHAWK
24- #include " nativeoverlapped.h"
25- #endif
26-
2723/* ***************************************************************************
2824 *
2925 * FORWARD DECLARATIONS
@@ -626,34 +622,31 @@ void HndLogSetEvent(OBJECTHANDLE handle, _UNCHECKED_OBJECTREF value)
626622 FireEtwSetGCHandle ((void *) handle, value, hndType, generation, (int64_t ) pAppDomain, GetClrInstanceId ());
627623 FireEtwPrvSetGCHandle ((void *) handle, value, hndType, generation, (int64_t ) pAppDomain, GetClrInstanceId ());
628624
629- #ifndef FEATURE_REDHAWK
630625 // Also fire the things pinned by Async pinned handles
631626 if (hndType == HNDTYPE_ASYNCPINNED)
632627 {
633- if (value->GetMethodTable () == g_pOverlappedDataClass)
628+ // the closure passed to "WalkOverlappedObject" is not permitted to implicitly
629+ // capture any variables in this scope, since WalkForOverlappedObject takes a bare
630+ // function pointer and context pointer as arguments. We can still /explicitly/
631+ // close over values in this scope by doing what the compiler would do and introduce
632+ // a structure that contains all of the things we closed over, while passing a pointer
633+ // to this structure as our closure's context pointer.
634+ struct ClosureCapture
634635 {
635- OverlappedDataObject* overlapped = (OverlappedDataObject*) value;
636- if (overlapped->m_isArray )
637- {
638- ArrayBase* pUserObject = (ArrayBase*)OBJECTREFToObject (overlapped->m_userObject );
639- Object **ppObj = (Object**)pUserObject->GetDataPtr (TRUE );
640- size_t num = pUserObject->GetNumComponents ();
641- for (size_t i = 0 ; i < num; i ++)
642- {
643- value = ppObj[i];
644- uint32_t generation = value != 0 ? g_theGCHeap->WhichGeneration (value) : 0 ;
645- FireEtwSetGCHandle (overlapped, value, HNDTYPE_PINNED, generation, (int64_t ) pAppDomain, GetClrInstanceId ());
646- }
647- }
648- else
649- {
650- value = OBJECTREF_TO_UNCHECKED_OBJECTREF (overlapped->m_userObject );
651- uint32_t generation = value != 0 ? g_theGCHeap->WhichGeneration (value) : 0 ;
652- FireEtwSetGCHandle (overlapped, value, HNDTYPE_PINNED, generation, (int64_t ) pAppDomain, GetClrInstanceId ());
653- }
654- }
636+ AppDomain* pAppDomain;
637+ Object* overlapped;
638+ };
639+
640+ ClosureCapture captured;
641+ captured.pAppDomain = pAppDomain;
642+ captured.overlapped = value;
643+ GCToEEInterface::WalkAsyncPinned (value, &captured, [](Object*, Object* to, void * ctx)
644+ {
645+ ClosureCapture* captured = reinterpret_cast <ClosureCapture*>(ctx);
646+ uint32_t generation = to != nullptr ? g_theGCHeap->WhichGeneration (to) : 0 ;
647+ FireEtwSetGCHandle (captured->overlapped , to, HNDTYPE_PINNED, generation, (int64_t ) captured->pAppDomain , GetClrInstanceId ());
648+ });
655649 }
656- #endif // FEATURE_REDHAWK
657650 }
658651#else
659652 UNREFERENCED_PARAMETER (handle);
@@ -709,14 +702,12 @@ void HndWriteBarrier(OBJECTHANDLE handle, OBJECTREF objref)
709702 int generation = g_theGCHeap->WhichGeneration (value);
710703 uint32_t uType = HandleFetchType (handle);
711704
712- #ifndef FEATURE_REDHAWK
713705 // OverlappedData need special treatment: because all user data pointed by it needs to be reported by this handle,
714706 // its age is consider to be min age of the user data, to be simple, we just make it 0
715- if (uType == HNDTYPE_ASYNCPINNED && objref-> GetGCSafeMethodTable () == g_pOverlappedDataClass )
707+ if (uType == HNDTYPE_ASYNCPINNED)
716708 {
717709 generation = 0 ;
718710 }
719- #endif // !FEATURE_REDHAWK
720711
721712 if (uType == HNDTYPE_DEPENDENT)
722713 {
@@ -1165,7 +1156,6 @@ uint32_t HndCountAllHandles(BOOL fUseLocks)
11651156
11661157BOOL Ref_HandleAsyncPinHandles (async_pin_enum_fn asyncPinCallback, void * context)
11671158{
1168- #ifndef FEATURE_REDHAWK
11691159 CONTRACTL
11701160 {
11711161 NOTHROW;
@@ -1186,14 +1176,13 @@ BOOL Ref_HandleAsyncPinHandles(async_pin_enum_fn asyncPinCallback, void* contex
11861176 }
11871177
11881178 return result;
1189- #else
1190- return true ;
1191- #endif // !FEATURE_REDHAWK
11921179}
11931180
1194- void Ref_RelocateAsyncPinHandles (HandleTableBucket *pSource, HandleTableBucket *pTarget)
1181+ void Ref_RelocateAsyncPinHandles (HandleTableBucket *pSource,
1182+ HandleTableBucket *pTarget,
1183+ void (*clearIfComplete)(Object* object),
1184+ void (*setHandle)(Object* object, OBJECTHANDLE handle))
11951185{
1196- #ifndef FEATURE_REDHAWK
11971186 CONTRACTL
11981187 {
11991188 NOTHROW;
@@ -1204,9 +1193,8 @@ void Ref_RelocateAsyncPinHandles(HandleTableBucket *pSource, HandleTableBucket
12041193 int limit = getNumberOfSlots ();
12051194 for (int n = 0 ; n < limit; n ++ )
12061195 {
1207- TableRelocateAsyncPinHandles (Table (pSource->pTable [n]), Table (pTarget->pTable [n]));
1196+ TableRelocateAsyncPinHandles (Table (pSource->pTable [n]), Table (pTarget->pTable [n]), clearIfComplete, setHandle );
12081197 }
1209- #endif // !FEATURE_REDHAWK
12101198}
12111199
12121200/* --------------------------------------------------------------------------*/
0 commit comments