From 8d80b9e76830d2188b8300b35783f9bb02c0dd7f Mon Sep 17 00:00:00 2001 From: Stephen Toub Date: Thu, 2 May 2019 14:41:02 -0400 Subject: [PATCH] Fix MultipleCallsToGetSpan test with pinning (dotnet/corefx#37373) The test is getting two pointers to an array and validating that they're the same pointer. But if the array is moved by the GC between the two calls, the test fails. The fix is to pin the array. Commit migrated from https://github.com/dotnet/corefx/commit/1a2401cd4c3f56c022173d2ac1e0c34799d387e3 --- .../ArrayBufferWriter/ArrayBufferWriterTests.T.cs | 44 ++++++++++++++-------- 1 file changed, 29 insertions(+), 15 deletions(-) diff --git a/src/libraries/System.Memory/tests/ArrayBufferWriter/ArrayBufferWriterTests.T.cs b/src/libraries/System.Memory/tests/ArrayBufferWriter/ArrayBufferWriterTests.T.cs index 1675955..013307a 100644 --- a/src/libraries/System.Memory/tests/ArrayBufferWriter/ArrayBufferWriterTests.T.cs +++ b/src/libraries/System.Memory/tests/ArrayBufferWriter/ArrayBufferWriterTests.T.cs @@ -357,25 +357,39 @@ namespace System.Buffers.Tests [Fact] public void MultipleCallsToGetSpan() { + if (RuntimeHelpers.IsReferenceOrContainsReferences()) + { + return; + } + var output = new ArrayBufferWriter(300); - int previousAvailable = output.FreeCapacity; - Assert.True(previousAvailable >= 300); - Assert.True(output.Capacity >= 300); - Assert.Equal(previousAvailable, output.Capacity); - Span span = output.GetSpan(); - Assert.True(span.Length >= previousAvailable); - Assert.True(span.Length >= 256); - Span newSpan = output.GetSpan(); - Assert.Equal(span.Length, newSpan.Length); + Assert.True(MemoryMarshal.TryGetArray(output.GetMemory(), out ArraySegment array)); + GCHandle pinnedArray = GCHandle.Alloc(array.Array, GCHandleType.Pinned); + try + { + int previousAvailable = output.FreeCapacity; + Assert.True(previousAvailable >= 300); + Assert.True(output.Capacity >= 300); + Assert.Equal(previousAvailable, output.Capacity); + Span span = output.GetSpan(); + Assert.True(span.Length >= previousAvailable); + Assert.True(span.Length >= 256); + Span newSpan = output.GetSpan(); + Assert.Equal(span.Length, newSpan.Length); - unsafe + unsafe + { + void* pSpan = Unsafe.AsPointer(ref MemoryMarshal.GetReference(span)); + void* pNewSpan = Unsafe.AsPointer(ref MemoryMarshal.GetReference(newSpan)); + Assert.Equal((IntPtr)pSpan, (IntPtr)pNewSpan); + } + + Assert.Equal(span.Length, output.GetSpan().Length); + } + finally { - void* pSpan = Unsafe.AsPointer(ref MemoryMarshal.GetReference(span)); - void* pNewSpan = Unsafe.AsPointer(ref MemoryMarshal.GetReference(newSpan)); - Assert.Equal((IntPtr)pSpan, (IntPtr)pNewSpan); + pinnedArray.Free(); } - - Assert.Equal(span.Length, output.GetSpan().Length); } public abstract void WriteData(IBufferWriter bufferWriter, int numBytes); -- 2.7.4