Imported Upstream version 6.0.0.172

Former-commit-id: f3cc9b82f3e5bd8f0fd3ebc098f789556b44e9cd
This commit is contained in:
Xamarin Public Jenkins (auto-signing)
2019-04-12 14:10:50 +00:00
parent 8016999e4d
commit 64ac736ec5
32155 changed files with 3981439 additions and 75368 deletions

View File

@@ -121,25 +121,22 @@ namespace System.Diagnostics
IntPtr cacheKey = (inMemoryPdbAddress != IntPtr.Zero) ? inMemoryPdbAddress : loadedPeAddress;
MetadataReaderProvider provider;
if (_metadataCache.TryGetValue(cacheKey, out provider))
while (!_metadataCache.TryGetValue(cacheKey, out provider))
{
return provider?.GetMetadataReader();
provider = (inMemoryPdbAddress != IntPtr.Zero) ?
TryOpenReaderForInMemoryPdb(inMemoryPdbAddress, inMemoryPdbSize) :
TryOpenReaderFromAssemblyFile(assemblyPath, loadedPeAddress, loadedPeSize);
// If the add loses the race with another thread, then the dispose the provider just
// created and return the provider already in the cache.
if (_metadataCache.TryAdd(cacheKey, provider))
break;
provider?.Dispose();
}
provider = (inMemoryPdbAddress != IntPtr.Zero) ?
TryOpenReaderForInMemoryPdb(inMemoryPdbAddress, inMemoryPdbSize) :
TryOpenReaderFromAssemblyFile(assemblyPath, loadedPeAddress, loadedPeSize);
// This may fail as another thread might have beaten us to it, but it doesn't matter
_metadataCache.TryAdd(cacheKey, provider);
if (provider == null)
{
return null;
}
// The reader has already been open, so this doesn't throw:
return provider.GetMetadataReader();
// The reader has already been open, so this doesn't throw.
return provider?.GetMetadataReader();
}
private static unsafe MetadataReaderProvider TryOpenReaderForInMemoryPdb(IntPtr inMemoryPdbAddress, int inMemoryPdbSize)

View File

@@ -4,6 +4,7 @@
using System.Collections.Generic;
using System.Reflection;
using System.Runtime.CompilerServices;
using Xunit;
namespace System.Diagnostics.Tests
@@ -63,13 +64,10 @@ namespace System.Diagnostics.Tests
{
StackFrame stackFrame = CallMethod(1);
MethodInfo expectedMethod = typeof(StackFrameTests).GetMethod(nameof(SkipFrames_CallMethod_ReturnsExpected));
#if DEBUG
Assert.Equal(expectedMethod, stackFrame.GetMethod());
#else
Assert.NotEqual(expectedMethod, stackFrame.GetMethod());
#endif
}
[MethodImpl(MethodImplOptions.NoInlining)]
public StackFrame CallMethod(int skipFrames) => new StackFrame(skipFrames);
[Theory]
@@ -113,16 +111,12 @@ namespace System.Diagnostics.Tests
public static IEnumerable<object[]> ToString_TestData()
{
#if DEBUG
yield return new object[] { new StackFrame(), "MoveNext at offset {offset} in file:line:column {fileName}:{lineNumber}:{column}" + Environment.NewLine };
yield return new object[] { new StackFrame("FileName", 1, 2), "MoveNext at offset {offset} in file:line:column FileName:1:2" + Environment.NewLine };
yield return new object[] { new StackFrame(int.MaxValue), "<null>" + Environment.NewLine };
yield return new object[] { GenericMethod<string>(), "GenericMethod<T> at offset {offset} in file:line:column {fileName}:{lineNumber}:{column}" + Environment.NewLine };
yield return new object[] { GenericMethod<string, int>(), "GenericMethod<T,U> at offset {offset} in file:line:column {fileName}:{lineNumber}:{column}" + Environment.NewLine };
yield return new object[] { new ClassWithConstructor().StackFrame, ".ctor at offset {offset} in file:line:column {fileName}:{lineNumber}:{column}" + Environment.NewLine };
#else
yield break;
#endif
}
[Theory]
@@ -136,12 +130,17 @@ namespace System.Diagnostics.Tests
Assert.Equal(expectedToString, stackFrame.ToString());
}
[MethodImpl(MethodImplOptions.NoInlining)]
private static StackFrame GenericMethod<T>() => new StackFrame();
[MethodImpl(MethodImplOptions.NoInlining)]
private static StackFrame GenericMethod<T, U>() => new StackFrame();
private class ClassWithConstructor
{
public StackFrame StackFrame { get; }
[MethodImpl(MethodImplOptions.NoInlining)]
public ClassWithConstructor() => StackFrame = new StackFrame();
}
@@ -164,15 +163,9 @@ namespace System.Diagnostics.Tests
{
Assert.Equal(StackFrame.OFFSET_UNKNOWN, stackFrame.GetILOffset());
}
#if !DEBUG
else if ((!PlatformDetection.IsFullFramework && isFileConstructor) || (PlatformDetection.IsFullFramework && !isFileConstructor && !isCurrentFrame && skipFrames == 0))
{
Assert.Equal(0, stackFrame.GetILOffset());
}
#endif
else
{
Assert.True(stackFrame.GetILOffset() > 0, $"Expected GetILOffset() {stackFrame.GetILOffset()} for {stackFrame} to be greater than zero.");
Assert.True(stackFrame.GetILOffset() >= 0, $"Expected GetILOffset() {stackFrame.GetILOffset()} for {stackFrame} to be greater or equal to zero.");
}
// GetMethod returns null for unknown frames.