Skip to content

Commit

Permalink
Merge pull request #1375 from jlaanstra/user/jlaans/1112-5
Browse files Browse the repository at this point in the history
Add Context checks to factory caching and simplify factory caching between factories and statics.
  • Loading branch information
manodasanW authored Nov 10, 2023
2 parents 7bd11ec + 7d917ac commit 5d34730
Show file tree
Hide file tree
Showing 16 changed files with 677 additions and 495 deletions.
1 change: 1 addition & 0 deletions nuget/Microsoft.Windows.CsWinRT.targets
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,7 @@ $(CsWinRTInternalProjection)

<ItemGroup Condition="'$(CsWinRTComponent)' != 'true' and Exists('$(CsWinRTResponseFile)')">
<UpToDateCheckInput Include="@(CsWinRTInputs)" Set="WinMDs" />
<UpToDateCheckInput Include="$(CsWinRTExe)" Set="WinMDs" />
<UpToDateCheckBuilt Include="$(CsWinRTResponseFile)" Set="WinMDs" />
</ItemGroup>

Expand Down
145 changes: 104 additions & 41 deletions src/Tests/UnitTest/TestComponentCSharp_Tests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
using Windows.Devices.Enumeration.Pnp;
using System.Diagnostics;
using Windows.Devices.Enumeration;
using Windows.UI.Notifications;

#if NET
using WeakRefNS = System;
Expand Down Expand Up @@ -76,12 +77,12 @@ public void TestLongClassNameEventSource()

[Fact]
public void TestEventArgsVector()
{
{
var eventArgsVector = TestObject.GetEventArgsVector();
Assert.Equal(1, eventArgsVector.Count);
foreach (var dataErrorChangedEventArgs in eventArgsVector)
{
var propName = dataErrorChangedEventArgs.PropertyName;
var propName = dataErrorChangedEventArgs.PropertyName;
Assert.Equal("name", propName);
}
}
Expand All @@ -92,7 +93,7 @@ public void TestNonGenericDelegateVector()
var provideUriVector = TestObject.GetNonGenericDelegateVector();

Assert.Equal(1, provideUriVector.Count);

foreach (var provideUri in provideUriVector)
{
Uri delegateTarget = provideUri.Invoke();
Expand Down Expand Up @@ -197,11 +198,11 @@ public void TestManyBufferExtensionMethods()
Assert.True(buffLen4.Length == 4);
Assert.Throws<ArgumentException>(() => buffLen4.GetByte(5)); // shouldn't have a 5th element
Assert.True(buffLen4.GetByte(0) == 0x02); // make sure we got the 2nd element of the array

arrayLen3.CopyTo(buffLen4); // Array to Buffer copying
Assert.True(buffLen4.Length == 4);
Assert.True(buffLen4.GetByte(0) == 0x01); // make sure we updated the first few
Assert.True(buffLen4.GetByte(1) == 0x02);
Assert.True(buffLen4.GetByte(1) == 0x02);
Assert.True(buffLen4.GetByte(2) == 0x03);
Assert.True(buffLen4.GetByte(3) == 0x14); // and kept the last one

Expand Down Expand Up @@ -263,14 +264,14 @@ public void TestIsSameDataUsingToArray()
public void TestBufferAsStreamUsingAsBuffer()
{
var arr = new byte[] { 0x01, 0x02 };
Stream stream = arr.AsBuffer().AsStream();
Stream stream = arr.AsBuffer().AsStream();
Assert.True(stream != null);
Assert.True(stream.Length == 2);
}

[Fact]
public void TestBufferAsStreamWithEmptyBuffer1()
{
{
var buffer = new Windows.Storage.Streams.Buffer(0);
Stream stream = buffer.AsStream();
Assert.True(stream != null);
Expand Down Expand Up @@ -392,7 +393,7 @@ public void TestWinRTBufferWithZeroLength()

[Fact]
public void TestEmptyBufferCopyTo()
{
{
var buffer = new Windows.Storage.Streams.Buffer(0);
byte[] array = { };
buffer.CopyTo(array);
Expand Down Expand Up @@ -527,7 +528,7 @@ public void TestBuffer()
{
var arr1 = new byte[] { 0x01, 0x02 };
var buff = arr1.AsBuffer();
var arr2 = buff.ToArray(0,2);
var arr2 = buff.ToArray(0, 2);
Assert.True(arr1[0] == arr2[0]);
Assert.True(arr1[1] == arr2[1]);
}
Expand Down Expand Up @@ -576,7 +577,7 @@ async Task InvokeWriteBufferAsync()
[Fact]
public void TestWriteBuffer()
{
Assert.True(InvokeWriteBufferAsync().Wait(1000));
Assert.True(InvokeWriteBufferAsync().Wait(1000));
}

[Fact]
Expand Down Expand Up @@ -900,10 +901,10 @@ public void TestValueSet()
public void TestValueSetArrays()
{
var map = new Dictionary<string, long[]>
{
{
["foo"] = new long[] { 1, 2, 3 },
["hello"] = new long[0],
["world"] = new long[] { 1, 2, 3 },
["hello"] = new long[0],
["world"] = new long[] { 1, 2, 3 },
["bar"] = new long[0]
};
var valueSet = new Windows.Foundation.Collections.ValueSet();
Expand All @@ -924,10 +925,10 @@ public void TestFactories()
var cls1 = new Class();

var cls2 = new Class(42);
Assert.Equal(42, cls2.IntProperty);
Assert.Equal(42, cls2.IntProperty);

var cls3 = new Class(42, "foo");
Assert.Equal(42, cls3.IntProperty);
Assert.Equal(42, cls3.IntProperty);
Assert.Equal("foo", cls3.StringProperty);
}

Expand Down Expand Up @@ -1975,11 +1976,25 @@ public void TestRepeatBehaviorTypeMapping()
[Fact]
public void TestMatrix3DTypeMapping()
{
var matrix3D = new Matrix3D {
M11 = 11, M12 = 12, M13 = 13, M14 = 14,
M21 = 21, M22 = 22, M23 = 23, M24 = 24,
M31 = 31, M32 = 32, M33 = 33, M34 = 34,
OffsetX = 41, OffsetY = 42, OffsetZ = 43,M44 = 44 };
var matrix3D = new Matrix3D
{
M11 = 11,
M12 = 12,
M13 = 13,
M14 = 14,
M21 = 21,
M22 = 22,
M23 = 23,
M24 = 24,
M31 = 31,
M32 = 32,
M33 = 33,
M34 = 34,
OffsetX = 41,
OffsetY = 42,
OffsetZ = 43,
M44 = 44
};

TestObject.Matrix3DProperty = matrix3D;
Assert.Equal(matrix3D.M11, TestObject.Matrix3DProperty.M11);
Expand Down Expand Up @@ -2028,10 +2043,22 @@ public void TestMatrix4x4TypeMapping()
{
var matrix4x4 = new Matrix4x4
{
M11 = 11, M12 = 12, M13 = 13, M14 = 14,
M21 = 21, M22 = 22, M23 = 23, M24 = 24,
M31 = 31, M32 = 32, M33 = 33, M34 = 34,
M41 = 41, M42 = 42, M43 = 43, M44 = 44
M11 = 11,
M12 = 12,
M13 = 13,
M14 = 14,
M21 = 21,
M22 = 22,
M23 = 23,
M24 = 24,
M31 = 31,
M32 = 32,
M33 = 33,
M34 = 34,
M41 = 41,
M42 = 42,
M43 = 43,
M44 = 44
};
TestObject.Matrix4x4Property = matrix4x4;
Assert.Equal(matrix4x4.M11, TestObject.Matrix4x4Property.M11);
Expand Down Expand Up @@ -2307,7 +2334,7 @@ public void TestDelegateUnboxing()
{
var del = Class.BoxedDelegate;
Assert.IsType<ProvideUri>(del);
var provideUriDel = (ProvideUri) del;
var provideUriDel = (ProvideUri)del;
Assert.Equal(new Uri("http://microsoft.com"), provideUriDel());
}

Expand Down Expand Up @@ -2438,8 +2465,6 @@ public void AcquireObject()
// Object gets proxied to the apartment.
Assert.Equal(2, proxyObject.Commands.Count);
agileReference.Dispose();

proxyObject2 = agileReference2.Get();
}

public void CheckValue()
Expand All @@ -2448,9 +2473,6 @@ public void CheckValue()
Assert.Equal(ApartmentState.MTA, Thread.CurrentThread.GetApartmentState());
proxyObject = agileReference.Get();
Assert.Equal(2, proxyObject.Commands.Count);

nonAgileObject2 = new Windows.UI.Popups.PopupMenu();
agileReference2 = nonAgileObject2.AsAgile();

valueAcquired.Set();
}
Expand All @@ -2462,8 +2484,8 @@ public void CallProxyObject()
Assert.ThrowsAny<System.Exception>(() => proxyObject.Commands);
}

private Windows.UI.Popups.PopupMenu nonAgileObject, nonAgileObject2;
private Windows.UI.Popups.PopupMenu proxyObject, proxyObject2;
private Windows.UI.Popups.PopupMenu nonAgileObject;
private Windows.UI.Popups.PopupMenu proxyObject;
private AgileReference<Windows.UI.Popups.PopupMenu> agileReference, agileReference2;
private readonly AutoResetEvent objectAcquired = new AutoResetEvent(false);
private readonly AutoResetEvent valueAcquired = new AutoResetEvent(false);
Expand Down Expand Up @@ -2533,8 +2555,8 @@ static Object MakeObject()

static void TestObject() => MakeObject();

static (IInitializeWithWindow, IWindowNative) MakeImports()
{
static (IInitializeWithWindow, IWindowNative) MakeImports()
{
var obj = MakeObject();
var initializeWithWindow = obj.As<IInitializeWithWindow>();
var windowNative = obj.As<IWindowNative>();
Expand All @@ -2544,7 +2566,7 @@ static Object MakeObject()
static void TestImports()
{
var (initializeWithWindow, windowNative) = MakeImports();

GC.Collect();
GC.WaitForPendingFinalizers();

Expand Down Expand Up @@ -2856,7 +2878,7 @@ public void TestProxiedDelegate()
{
proc.Kill();
}
catch(Exception)
catch (Exception)
{
}
}
Expand Down Expand Up @@ -2935,7 +2957,7 @@ private void TestSupportedOSPlatformWarnings()
// Types
var a = new WarningAttribute(); // warning CA1416
Assert.NotNull(a);
var w = new WarningStruct{ i32 = 0 }; // warning CA1416
var w = new WarningStruct { i32 = 0 }; // warning CA1416
Assert.Equal(0, w.i32); // warning CA1416
var v = WarningEnum.Value;
Assert.NotEqual(WarningEnum.WarningValue, v); // warning CA1416
Expand Down Expand Up @@ -3046,17 +3068,17 @@ public void TestWeakReferenceEventsFromMultipleContexts()
Assert.True(Thread.CurrentThread.GetApartmentState() == ApartmentState.STA);
watcher = DeviceInformation.CreateWatcher();
var exception = Record.Exception(() => {
watcher.Added += OnDeviceAdded;
var exception = Record.Exception(() => {
watcher.Added += OnDeviceAdded;
});
Assert.Null(exception);
Thread mtaThread = new Thread(() =>
{
Assert.True(Thread.CurrentThread.GetApartmentState() == ApartmentState.MTA);
exception = Record.Exception(() => {
watcher.Updated += OnDeviceUpdated;
exception = Record.Exception(() => {
watcher.Updated += OnDeviceUpdated;
});
Assert.Null(exception);
});
Expand All @@ -3069,6 +3091,47 @@ public void TestWeakReferenceEventsFromMultipleContexts()
staThread.Join();
}

#if NET
[Fact]
public void TestActivationFactoriesFromMultipleContexts()
{
Exception exception = null;

Thread staThread = new Thread(() =>
{
Assert.True(Thread.CurrentThread.GetApartmentState() == ApartmentState.STA);
exception = Record.Exception(() =>
{
var xmlDoc = ToastNotificationManager.GetTemplateContent(ToastTemplateType.ToastText01);
_ = new ToastNotification(xmlDoc);
});
});
staThread.SetApartmentState(ApartmentState.STA);
staThread.Start();
staThread.Join();

Assert.Null(exception);

Thread mtaThread = new Thread(() =>
{
Assert.True(Thread.CurrentThread.GetApartmentState() == ApartmentState.MTA);
exception = Record.Exception(() =>
{
var xmlDoc = ToastNotificationManager.GetTemplateContent(ToastTemplateType.ToastText01);
_ = new ToastNotification(xmlDoc);
});
});
mtaThread.SetApartmentState(ApartmentState.MTA);
mtaThread.Start();
mtaThread.Join();

Assert.Null(exception);
}
#endif

[Fact]
public void TestDictionary()
{
Expand Down
16 changes: 8 additions & 8 deletions src/WinRT.Runtime/ComWrappersSupport.cs
Original file line number Diff line number Diff line change
Expand Up @@ -69,16 +69,16 @@ public static void MarshalDelegateInvoke<T>(IntPtr thisPtr, Action<T> invoke)
// This can either be if the object implements IAgileObject or the free threaded marshaler.
internal unsafe static bool IsFreeThreaded(IObjectReference objRef)
{
if (objRef.TryAs(ABI.WinRT.Interop.IAgileObject.IID, out var agilePtr) >= 0)
if (objRef.TryAs(InterfaceIIDs.IAgileObject_IID, out var agilePtr) >= 0)
{
Marshal.Release(agilePtr);
return true;
}
else if (objRef.TryAs(ABI.WinRT.Interop.IMarshal.IID, out var marshalPtr) >= 0)
else if (objRef.TryAs(InterfaceIIDs.IMarshal_IID, out var marshalPtr) >= 0)
{
try
{
Guid iid_IUnknown = IUnknownVftbl.IID;
Guid iid_IUnknown = InterfaceIIDs.IUnknown_IID;
Guid iid_unmarshalClass;
Marshal.ThrowExceptionForHR((**(ABI.WinRT.Interop.IMarshal.Vftbl**)marshalPtr).GetUnmarshalClass_0(
marshalPtr, &iid_IUnknown, IntPtr.Zero, MSHCTX.InProc, IntPtr.Zero, MSHLFLAGS.Normal, &iid_unmarshalClass));
Expand Down Expand Up @@ -229,7 +229,7 @@ internal static List<ComInterfaceEntry> GetInterfaceTableEntries(
Vtable = (IntPtr)ifaceAbiType.GetAbiToProjectionVftblPtr()
});

if (!hasCustomIMarshalInterface && iid == ABI.WinRT.Interop.IMarshal.IID)
if (!hasCustomIMarshalInterface && iid == InterfaceIIDs.IMarshal_IID)
{
hasCustomIMarshalInterface = true;
}
Expand Down Expand Up @@ -298,7 +298,7 @@ internal static List<ComInterfaceEntry> GetInterfaceTableEntries(

entries.Add(new ComInterfaceEntry
{
IID = ABI.WinRT.Interop.IWeakReferenceSource.IID,
IID = InterfaceIIDs.IWeakReferenceSource_IID,
Vtable = ABI.WinRT.Interop.IWeakReferenceSource.AbiToProjectionVftablePtr
});

Expand All @@ -308,15 +308,15 @@ internal static List<ComInterfaceEntry> GetInterfaceTableEntries(
{
entries.Add(new ComInterfaceEntry
{
IID = ABI.WinRT.Interop.IMarshal.IID,
IID = InterfaceIIDs.IMarshal_IID,
Vtable = ABI.WinRT.Interop.IMarshal.Vftbl.AbiToProjectionVftablePtr
});
}

// Add IAgileObject to all CCWs
entries.Add(new ComInterfaceEntry
{
IID = ABI.WinRT.Interop.IAgileObject.IID,
IID = InterfaceIIDs.IAgileObject_IID,
Vtable = IUnknownVftbl.AbiToProjectionVftblPtr
});

Expand All @@ -329,7 +329,7 @@ internal static List<ComInterfaceEntry> GetInterfaceTableEntries(
// This should be the last entry as it is included / excluded based on the flags.
entries.Add(new ComInterfaceEntry
{
IID = IUnknownVftbl.IID,
IID = InterfaceIIDs.IUnknown_IID,
Vtable = IUnknownVftbl.AbiToProjectionVftblPtr
});

Expand Down
Loading

0 comments on commit 5d34730

Please sign in to comment.