diff --git a/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/HandleCollector.cs b/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/HandleCollector.cs index a874251c5dbc4..7e83303a5bcbb 100644 --- a/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/HandleCollector.cs +++ b/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/HandleCollector.cs @@ -40,6 +40,7 @@ public HandleCollector(string? name, int initialThreshold, int maximumThreshold) MaximumThreshold = maximumThreshold; _threshold = initialThreshold; _handleCount = 0; + _gcGeneration = 0; } public int Count => _handleCount; diff --git a/src/libraries/System.Runtime.InteropServices/tests/System.Runtime.InteropServices.UnitTests/System/Runtime/InteropServices/HandleCollectorTests.cs b/src/libraries/System.Runtime.InteropServices/tests/System.Runtime.InteropServices.UnitTests/System/Runtime/InteropServices/HandleCollectorTests.cs index ce0ad62b912d5..471c8bf2a84fa 100644 --- a/src/libraries/System.Runtime.InteropServices/tests/System.Runtime.InteropServices.UnitTests/System/Runtime/InteropServices/HandleCollectorTests.cs +++ b/src/libraries/System.Runtime.InteropServices/tests/System.Runtime.InteropServices.UnitTests/System/Runtime/InteropServices/HandleCollectorTests.cs @@ -122,6 +122,7 @@ public static void Add_Overflows_ThrowsInvalidOperationException() public static void TestHandleCollector() { (int gen0, int gen1, int gen2) initialGcState = (GC.CollectionCount(0), GC.CollectionCount(1), GC.CollectionCount(2)); + int initSum = initialGcState.gen0 + initialGcState.gen1 + initialGcState.gen2; HandleCollector lowLimitCollector = new HandleCollector("LowLimit.Collector", LowLimitSize); for (int i = 0; i < LowLimitSize + 1; ++i) @@ -129,9 +130,13 @@ public static void TestHandleCollector() HandleLimitTester hlt = new HandleLimitTester(lowLimitCollector); } - (int gen0, int gen1, int gen2) postLowLimitState = (GC.CollectionCount(0),GC.CollectionCount(1), GC.CollectionCount(2)); + // HandleLimitTester does the decrement on the HandleCollector during finalization, so we wait for pending finalizers. + GC.WaitForPendingFinalizers(); - Assert.True(initialGcState.gen0 + initialGcState.gen1 + initialGcState.gen2 < postLowLimitState.gen0 + postLowLimitState.gen1 + postLowLimitState.gen2, "Low limit handle did not trigger a GC"); + (int gen0, int gen1, int gen2) postLowLimitState = (GC.CollectionCount(0), GC.CollectionCount(1), GC.CollectionCount(2)); + int postLowLimitSum = postLowLimitState.gen0 + postLowLimitState.gen1 + postLowLimitState.gen2; + + Assert.True(initSum < postLowLimitSum, $"Low limit handle did not trigger a GC: {initSum} < {postLowLimitSum}"); HandleCollector highLimitCollector = new HandleCollector("HighLimit.Collector", HighLimitSize); for (int i = 0; i < HighLimitSize + 10; ++i) @@ -139,9 +144,13 @@ public static void TestHandleCollector() HandleLimitTester hlt = new HandleLimitTester(highLimitCollector); } + // HandleLimitTester does the decrement on the HandleCollector during finalization, so we wait for pending finalizers. + GC.WaitForPendingFinalizers(); + (int gen0, int gen1, int gen2) postHighLimitState = (GC.CollectionCount(0), GC.CollectionCount(1), GC.CollectionCount(2)); + int postHighLimitSum = postHighLimitState.gen0 + postHighLimitState.gen1 + postHighLimitState.gen2; - Assert.True(postLowLimitState.gen0 + postLowLimitState.gen1 + postLowLimitState.gen2 < postHighLimitState.gen0 + postHighLimitState.gen1 + postHighLimitState.gen2, "High limit handle did not trigger a GC"); + Assert.True(postLowLimitSum < postHighLimitSum, $"High limit handle did not trigger a GC: {postLowLimitSum} < {postHighLimitSum}"); } private sealed class HandleLimitTester