using System;
using System.Threading;
using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
namespace PInvokeTest
{
+ static class PInvokeExampleNative
+ {
+ public static int GetConstant()
+ {
+ return GetConstantInternal();
+ }
+
+ [DllImport(nameof(PInvokeExampleNative))]
+ private extern static int GetConstantInternal();
+ }
+
internal class Test
{
[MethodImpl(MethodImplOptions.AggressiveInlining)]
- static bool AsForceInline()
+ static int AsForceInline()
{
- return Thread.Yield();
+ return PInvokeExampleNative.GetConstant();
}
- static bool AsNormalInline()
+ static int AsNormalInline()
{
- return Thread.Yield();
+ return PInvokeExampleNative.GetConstant();
}
[MethodImpl(MethodImplOptions.NoInlining)]
- static bool AsNoInline()
+ static int AsNoInline()
{
- return Thread.Yield();
+ return PInvokeExampleNative.GetConstant();
}
static bool FromTryCatch()
try
{
// All pinvokes should be inline, except on x64
- result = (Thread.Yield() == AsNormalInline());
+ result = (PInvokeExampleNative.GetConstant() == AsNormalInline());
}
catch (Exception)
{
try
{
// All pinvokes should be inline, except on x64
- result1 = (Thread.Yield() == AsNormalInline());
- result2 = (Thread.Yield() == AsNormalInline());
+ result1 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
+ result2 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
}
finally
{
try
{
// These two pinvokes should be inline, except on x64
- result1 = (Thread.Yield() == AsNormalInline());
+ result1 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
}
finally
{
// These two pinvokes should *not* be inline (finally)
- result2 = (Thread.Yield() == AsNormalInline());
+ result2 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
result = result1 && result2;
}
try
{
// These two pinvokes should be inline, except on x64
- result1 = (Thread.Yield() == AsNormalInline());
+ result1 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
}
finally
{
try
{
// These two pinvokes should *not* be inline (finally)
- result2 = (Thread.Yield() == AsNormalInline());
+ result2 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
}
catch (Exception)
{
static bool FromInline()
{
// These two pinvokes should be inline
- bool result = (Thread.Yield() == AsForceInline());
+ bool result = (PInvokeExampleNative.GetConstant() == AsForceInline());
return result;
}
static bool FromInline2()
{
// These four pinvokes should be inline
- bool result1 = (Thread.Yield() == AsNormalInline());
- bool result2 = (Thread.Yield() == AsForceInline());
+ bool result1 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
+ bool result2 = (PInvokeExampleNative.GetConstant() == AsForceInline());
return result1 && result2;
}
static bool FromNoInline()
{
// The only pinvoke should be inline
- bool result = (Thread.Yield() == AsNoInline());
+ bool result = (PInvokeExampleNative.GetConstant() == AsNoInline());
return result;
}
static bool FromNoInline2()
{
// Three pinvokes should be inline
- bool result1 = (Thread.Yield() == AsNormalInline());
- bool result2 = (Thread.Yield() == AsNoInline());
+ bool result1 = (PInvokeExampleNative.GetConstant() == AsNormalInline());
+ bool result2 = (PInvokeExampleNative.GetConstant() == AsNoInline());
return result1 && result2;
}
// These two pinvokes should *not* be inline (filter)
//
// For the first call the jit won't inline the wrapper, so
- // it just calls get_ProcessorCount.
+ // it just calls GetConstant().
//
// For the second call, the force inline works, and the
- // subsequent inline of Thread.Yield exposes a call
- // to the pinvoke YieldInternal. This pinvoke will
+ // subsequent inline of GetConstant() exposes a call
+ // to the pinvoke GetConstantInternal(). This pinvoke will
// not be inline.
- catch (Exception) when (Thread.Yield() == AsForceInline())
+ catch (Exception) when (PInvokeExampleNative.GetConstant() == AsForceInline())
{
result = true;
}
static bool FromColdCode()
{
- bool yield = false;
+ int yield = -1;
bool result1 = false;
bool result2 = false;
try
{
// This pinvoke should not be inline (cold)
- yield = Thread.Yield();
+ yield = PInvokeExampleNative.GetConstant();
throw new Exception("expected");
}
catch (Exception)
// These two pinvokes should not be inline (catch)
//
// For the first call the jit won't inline the
- // wrapper, so it just calls Thread.Yield.
+ // wrapper, so it just calls GetConstant().
//
// For the second call, the force inline works, and
- // the subsequent inline of Thread.Yield exposes
- // a call to the pinvoke YieldInternal. This
+ // the subsequent inline of GetConstant() exposes
+ // a call to the pinvoke GetConstantInternal(). This
// pinvoke will not be inline.
- result1 = (yield == Thread.Yield());
+ result1 = (yield == PInvokeExampleNative.GetConstant());
result2 = (yield == AsForceInline());
}