ICorProfilerCallback4::MovedReferences2 方法

调用以报告堆中对象的新布局(压缩垃圾回收产生的结果)。 如果探查器已实现 ICorProfilerCallback4 接口,则调用此方法。 此回调可替换 ICorProfilerCallback::MovedReferences 方法,因为它能报告长度超过可用 ULONG 可表达限制的较大对象范围。

语法

HRESULT MovedReferences2(  
    [in]  ULONG  cMovedObjectIDRanges,  
    [in, size_is(cMovedObjectIDRanges)] ObjectID oldObjectIDRangeStart[] ,  
    [in, size_is(cMovedObjectIDRanges)] ObjectID newObjectIDRangeStart[] ,  
    [in, size_is(cMovedObjectIDRanges)] SIZE_T    cObjectIDRangeLength[] );  

参数

cMovedObjectIDRanges
[in] 因压缩垃圾回收而被移动的连续对象的块数。 即 cMovedObjectIDRanges 的值是 oldObjectIDRangeStartnewObjectIDRangeStartcObjectIDRangeLength 数组的总大小。

MovedReferences2 的接下来的三个参数是并行数组。 换言之,oldObjectIDRangeStart[i]newObjectIDRangeStart[i]cObjectIDRangeLength[i] 都涉及单个连续对象单块。

oldObjectIDRangeStart
[in] ObjectID 值的数组,其中每个值均为内存中连续活动对象块的旧(垃圾回收前)起始地址。

newObjectIDRangeStart
[in] ObjectID 值的数组,其中每个值均为内存中连续活动对象块的新(垃圾回收后)起始地址。

cObjectIDRangeLength
[in] 整数数组,其中每个整数均为内存中的连续对象块的大小。

oldObjectIDRangeStartnewObjectIDRangeStart 数组中引用的每个块均有指定的大小。

注解

压缩垃圾回收器将收回由不活动对象占用的内存,但不会压缩释放的空间。 因此,可能在堆中移动活动对象,并且由以前的通知分发的 ObjectID 值也可能更改。

假定现有 ObjectID 值 (oldObjectID) 在以下范围内:

oldObjectIDRangeStart[i]<= oldObjectID<oldObjectIDRangeStart[i] + cObjectIDRangeLength[i]

在这种情况下,从范围起始到对象起始位置的偏移量如下所示:

oldObjectID - oldObjectRangeStart[i]

对于以下范围内的任何 i 值:

0 <= i<cMovedObjectIDRanges

可以按以下方式计算出新的 ObjectID

newObjectID = newObjectIDRangeStart[i] + (oldObjectIDoldObjectIDRangeStart[i])

在该回调本身中,由 MovedReferences2 传递的任何 ObjectID 值都无效,因为垃圾回收器可能正在将对象从旧位置移至新位置。 因此,探查器不应在 MovedReferences2 调用期间尝试检查对象。 ICorProfilerCallback2::GarbageCollectionFinished 回调指示所有对象都已移到新位置,可以执行检查。

如果探查器同时实现 ICorProfilerCallbackICorProfilerCallback4 接口,则在 ICorProfilerCallback::MovedReferences 方法之前调用 MovedReferences2 方法,但这仅在 MovedReferences2 方法成功返回时适用。 探查器可以返回一个 HRESULT,指示由 MovedReferences2 方法引发的故障,以避免调用第二种方法。

要求

平台:请参阅系统要求

头文件: CorProf.idl、CorProf.h

库:CorGuids.lib

.NET Framework 版本:自 4.5 起可用

另请参阅