Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add GC.KeepAlive when doing ABI call #1848

Merged
merged 13 commits into from
Oct 28, 2024
19 changes: 19 additions & 0 deletions build/AzurePipelineTemplates/CsWinRT-BuildAndTest-Stage.yml
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,15 @@ stages:
Write-Host "##vso[task.setvariable variable=DOTNET_ROOT;]$env:LOCALAPPDATA\Microsoft\dotnet\"
Write-Host "##vso[task.setvariable variable=DOTNET_ROOT(x86);]$env:LOCALAPPDATA\Microsoft\dotnet\x86\"

# Enable GC stress
- task: PowerShell@2
displayName: Enable GC Stress
condition: and(succeeded(), eq(variables['_RunGCStress'], 'true'))
inputs:
targetType: inline
script: |
Write-Host "##vso[task.setvariable variable=DOTNET_GCStress;]0xC"

# Run Unit Tests
- task: DotNetCoreCLI@2
displayName: Run Unit Tests
Expand Down Expand Up @@ -117,6 +126,16 @@ stages:
set CIBuildReason=CI
set cswinrt_label=functionaltest
build.cmd $(BuildPlatform) $(BuildConfiguration) $(VersionNumber) $(Build.BuildNumber) $(WinRT.Runtime.AssemblyVersion)

# Disable GC stress
- task: PowerShell@2
displayName: Disable GC Stress
condition: and(succeeded(), eq(variables['_RunGCStress'], 'true'))
inputs:
targetType: inline
script: |
Write-Host "##vso[task.setvariable variable=DOTNET_GCStress;]0x0"

templateContext:
outputs:
- output: pipelineArtifact
Expand Down
2 changes: 2 additions & 0 deletions build/AzurePipelineTemplates/CsWinRT-Variables.yml
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@ variables:
value: $[coalesce(variables.IsRelease, '')]
- name: _RunBenchmarks
value: $[coalesce(variables.RunBenchmarks, 'false')]
- name: _RunGCStress
value: $[coalesce(variables.RunGCStress, 'false')]
- name: _DotNetRuntimeVersion
value: $[coalesce(variables.DotNetRuntimeVersion, '6.0.32')]
- name: _WindowsSdkVersionSuffix
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1029,6 +1029,7 @@ private static unsafe void Invoke(IObjectReference objRef, object sender, {{gene
IntPtr abiSender = MarshalInspectable<object>.GetAbi(__sender);
{{GeneratorHelper.GetCreateMarshaler(genericType, abiType, typeKind, "args")}}
global::WinRT.ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, IntPtr, {{abiType}}, int>**)ThisPtr)[3](ThisPtr, abiSender, {{GeneratorHelper.GetAbiFromMarshaler(genericType, abiType, typeKind, "args")}}));
global::System.GC.KeepAlive(objRef);
}
finally
{
Expand Down Expand Up @@ -1086,6 +1087,7 @@ private static unsafe void Invoke(IObjectReference objRef, {{genericParameters[0
{{GeneratorHelper.GetCreateMarshaler(genericParameters[0], "sender")}}
{{GeneratorHelper.GetCreateMarshaler(genericParameters[1], "args")}}
global::WinRT.ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, {{genericParameters[0].AbiType}}, {{genericParameters[1].AbiType}}, int>**)ThisPtr)[3](ThisPtr, {{GeneratorHelper.GetAbiFromMarshaler(genericParameters[0], "sender")}}, {{GeneratorHelper.GetAbiFromMarshaler(genericParameters[1], "args")}}));
global::System.GC.KeepAlive(objRef);
}
finally
{
Expand Down Expand Up @@ -1218,6 +1220,7 @@ private static unsafe void Invoke(IObjectReference objRef, {{asyncInfoInterfaceW
IntPtr abiAsyncInfo = MarshalInspectable<object>.GetAbi(__asyncInfo);
{{GeneratorHelper.GetCreateMarshaler(progressParameter.ProjectedType, progressParameter.AbiType, progressParameter.TypeKind, "progressInfo")}}
global::WinRT.ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, IntPtr, {{progressParameter.AbiType}}, int>**)ThisPtr)[3](ThisPtr, abiAsyncInfo, {{GeneratorHelper.GetAbiFromMarshaler(progressParameter.ProjectedType, progressParameter.AbiType, progressParameter.TypeKind, "progressInfo")}}));
global::System.GC.KeepAlive(objRef);
}
finally
{
Expand Down
4 changes: 3 additions & 1 deletion src/Tests/OOPExe/Program.cs
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,9 @@ static void Main(string[] args)
var asyncAction = MarshalInterface<IAsyncAction>.FromAbi(Marshal.GetIUnknownForObject(obj));
asyncAction.Completed = Completed;

done.WaitOne(5000);
done.WaitOne(30000);

GC.KeepAlive(asyncAction);
}

public static void Completed(IAsyncAction asyncInfo, AsyncStatus asyncStatus)
Expand Down
4 changes: 2 additions & 2 deletions src/Tests/UnitTest/TestComponentCSharp_Tests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2043,7 +2043,7 @@ public void TestAsyncOperation()
var task = InvokeAddAsync(42, 8);
Assert.False(task.Wait(25));
TestObject.CompleteAsync();
Assert.True(task.Wait(5000));
Assert.True(task.Wait(10000));
Assert.Equal(TaskStatus.RanToCompletion, task.Status);
Assert.Equal(50, task.Result);

Expand Down Expand Up @@ -3262,7 +3262,7 @@ public void TestProxiedDelegate()
var launchExePath = $"{currentExecutingDir}\\OOPExe.dll";
var proc = Process.Start("dotnet.exe", launchExePath);
#endif
Thread.Sleep(1000);
Thread.Sleep(5000);
obj.Close();
Assert.True(obj.delegateCalled);

Expand Down
1 change: 1 addition & 0 deletions src/WinRT.Runtime/IInspectable.cs
Original file line number Diff line number Diff line change
Expand Up @@ -159,6 +159,7 @@ public unsafe string GetRuntimeClassName(bool noThrow = false)
{
IntPtr thisPtr = ThisPtr;
var hr = ((delegate* unmanaged[Stdcall]<IntPtr, IntPtr*, int>)(*(void***)thisPtr)[4])(thisPtr, &__retval);
GC.KeepAlive(_obj);
if (hr != 0)
{
if (noThrow)
Expand Down
4 changes: 3 additions & 1 deletion src/WinRT.Runtime/Interop/EventSource{TDelegate}.cs
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,7 @@ public void Subscribe(TDelegate handler)
#else
ExceptionHelpers.ThrowExceptionForHR(_addHandler(_objectReference.ThisPtr, nativeDelegate, out token));
#endif
global::System.GC.KeepAlive(_objectReference);
state.token = token;
}
finally
Expand Down Expand Up @@ -156,7 +157,8 @@ public void Unsubscribe(TDelegate handler)

private void UnsubscribeFromNative(EventSourceState<TDelegate> state)
{
ExceptionHelpers.ThrowExceptionForHR(_removeHandler(_objectReference.ThisPtr, state.token));
ExceptionHelpers.ThrowExceptionForHR(_removeHandler(_objectReference.ThisPtr, state.token));
global::System.GC.KeepAlive(_objectReference);
state.Dispose();
_state = null;
}
Expand Down
12 changes: 9 additions & 3 deletions src/WinRT.Runtime/Interop/IAgileReference.net5.cs
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,8 @@ public static unsafe IObjectReference Resolve(IObjectReference _obj, Guid riid)
var ThisPtr = _obj.ThisPtr;
IntPtr ptr = IntPtr.Zero;
ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr*, int>**)ThisPtr)[3](
ThisPtr, &riid, &ptr));
ThisPtr, &riid, &ptr));
global::System.GC.KeepAlive(_obj);
try
{
return ComWrappersSupport.GetObjectReferenceForInterface(ptr, riid, requireQI: false);
Expand All @@ -60,6 +61,7 @@ public static unsafe ObjectReference<T> Resolve<T>(IObjectReference _obj, Guid r
IntPtr ptr = IntPtr.Zero;
ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr*, int>**)ThisPtr)[3](
ThisPtr, &riid, &ptr));
global::System.GC.KeepAlive(_obj);
try
{
return ComWrappersSupport.GetObjectReferenceForInterface<T>(ptr, riid, requireQI: false);
Expand Down Expand Up @@ -138,7 +140,8 @@ public IntPtr RegisterInterfaceInGlobal(IntPtr ptr, Guid riid)
{
IntPtr thisPtr = ThisPtr;
IntPtr cookie;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr*, int>)(*(void***)thisPtr)[3])(thisPtr, ptr, &riid, &cookie));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr*, int>)(*(void***)thisPtr)[3])(thisPtr, ptr, &riid, &cookie));
global::System.GC.KeepAlive(_obj);
return cookie;

}
Expand All @@ -147,6 +150,7 @@ public void TryRevokeInterfaceFromGlobal(IntPtr cookie)
{
IntPtr thisPtr = ThisPtr;
int hresult = ((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, int>)(*(void***)thisPtr)[4])(thisPtr, cookie);
global::System.GC.KeepAlive(_obj);

if (hresult == ExceptionHelpers.E_INVALIDARG)
{
Expand All @@ -163,7 +167,9 @@ public IObjectReference GetInterfaceFromGlobal(IntPtr cookie, Guid riid)
{
IntPtr thisPtr = ThisPtr;
IntPtr ptr;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr*, int>)(*(void***)thisPtr)[5])(thisPtr, cookie, &riid, &ptr));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr*, int>)(*(void***)thisPtr)[5])(thisPtr, cookie, &riid, &ptr));
global::System.GC.KeepAlive(_obj);

try
{
return ComWrappersSupport.GetObjectReferenceForInterface(ptr, riid, requireQI: false);
Expand Down
17 changes: 12 additions & 5 deletions src/WinRT.Runtime/Interop/IAgileReference.netstandard2.0.cs
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,9 @@ public static unsafe IObjectReference Resolve(IObjectReference _obj, Guid riid)
var ThisPtr = _obj.ThisPtr;
IntPtr ptr = IntPtr.Zero;
ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr*, int>**)ThisPtr)[3](
ThisPtr, &riid, &ptr));
ThisPtr, &riid, &ptr));
global::System.GC.KeepAlive(_obj);

try
{
return ComWrappersSupport.GetObjectReferenceForInterface(ptr, riid, requireQI: false);
Expand All @@ -68,7 +70,9 @@ public static unsafe ObjectReference<T> Resolve<T>(IObjectReference _obj, Guid r
var ThisPtr = _obj.ThisPtr;
IntPtr ptr = IntPtr.Zero;
ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr*, int>**)ThisPtr)[3](
ThisPtr, &riid, &ptr));
ThisPtr, &riid, &ptr));
global::System.GC.KeepAlive(_obj);

try
{
return ComWrappersSupport.GetObjectReferenceForInterface<T>(ptr, riid, requireQI: false);
Expand Down Expand Up @@ -230,19 +234,22 @@ public IGlobalInterfaceTable(ObjectReference<Vftbl> obj)

public IntPtr RegisterInterfaceInGlobal(IntPtr ptr, Guid riid)
{
ExceptionHelpers.ThrowExceptionForHR(_obj.Vftbl.RegisterInterfaceInGlobal(ThisPtr, ptr, ref riid, out IntPtr cookie));
ExceptionHelpers.ThrowExceptionForHR(_obj.Vftbl.RegisterInterfaceInGlobal(ThisPtr, ptr, ref riid, out IntPtr cookie));
global::System.GC.KeepAlive(_obj);
return cookie;

}

public void RevokeInterfaceFromGlobal(IntPtr cookie)
{
ExceptionHelpers.ThrowExceptionForHR(_obj.Vftbl.RevokeInterfaceFromGlobal(ThisPtr, cookie));
ExceptionHelpers.ThrowExceptionForHR(_obj.Vftbl.RevokeInterfaceFromGlobal(ThisPtr, cookie));
global::System.GC.KeepAlive(_obj);
}

public IObjectReference GetInterfaceFromGlobal(IntPtr cookie, Guid riid)
{
ExceptionHelpers.ThrowExceptionForHR(_obj.Vftbl.GetInterfaceFromGlobal(ThisPtr, cookie, ref riid, out IntPtr ptr));
ExceptionHelpers.ThrowExceptionForHR(_obj.Vftbl.GetInterfaceFromGlobal(ThisPtr, cookie, ref riid, out IntPtr ptr));
global::System.GC.KeepAlive(_obj);
try
{
return ComWrappersSupport.GetObjectReferenceForInterface(ptr, riid, requireQI: false);
Expand Down
3 changes: 2 additions & 1 deletion src/WinRT.Runtime/Interop/IContextCallback.cs
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,8 @@ public IContextCallback(ObjectReference<Vftbl> obj)
public unsafe void ContextCallback(PFNCONTEXTCALL pfnCallback, ComCallData* pParam, Guid riid, int iMethod)
{
var callback = Marshal.GetFunctionPointerForDelegate(pfnCallback);
var result = _obj.Vftbl.ContextCallback_4(ThisPtr, callback, pParam, &riid, iMethod, IntPtr.Zero);
var result = _obj.Vftbl.ContextCallback_4(ThisPtr, callback, pParam, &riid, iMethod, IntPtr.Zero);
GC.KeepAlive(_obj);
GC.KeepAlive(pfnCallback);
Marshal.ThrowExceptionForHR(result);
}
Expand Down
18 changes: 12 additions & 6 deletions src/WinRT.Runtime/Interop/IMarshal.net5.cs
Original file line number Diff line number Diff line change
Expand Up @@ -215,37 +215,43 @@ public IMarshal(IObjectReference obj)
public unsafe void GetUnmarshalClass(Guid* riid, IntPtr pv, MSHCTX dwDestContext, IntPtr pvDestContext, MSHLFLAGS mshlFlags, Guid* pCid)
{
IntPtr thisPtr = ThisPtr;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr, MSHCTX, IntPtr, MSHLFLAGS, Guid*, int>)(*(void***)thisPtr)[3])(thisPtr, riid, pv, dwDestContext, pvDestContext, mshlFlags, pCid));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr, MSHCTX, IntPtr, MSHLFLAGS, Guid*, int>)(*(void***)thisPtr)[3])(thisPtr, riid, pv, dwDestContext, pvDestContext, mshlFlags, pCid));
GC.KeepAlive(_obj);
}

public unsafe void GetMarshalSizeMax(Guid* riid, IntPtr pv, MSHCTX dwDestContext, IntPtr pvDestContext, MSHLFLAGS mshlflags, uint* pSize)
{
IntPtr thisPtr = ThisPtr;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr, MSHCTX, IntPtr, MSHLFLAGS, uint*, int>)(*(void***)thisPtr)[4])(thisPtr, riid, pv, dwDestContext, pvDestContext, mshlflags, pSize));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr, MSHCTX, IntPtr, MSHLFLAGS, uint*, int>)(*(void***)thisPtr)[4])(thisPtr, riid, pv, dwDestContext, pvDestContext, mshlflags, pSize));
GC.KeepAlive(_obj);
}

public unsafe void MarshalInterface(IntPtr pStm, Guid* riid, IntPtr pv, MSHCTX dwDestContext, IntPtr pvDestContext, MSHLFLAGS mshlflags)
{
IntPtr thisPtr = ThisPtr;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr, MSHCTX, IntPtr, MSHLFLAGS, int>)(*(void***)thisPtr)[5])(thisPtr, pStm, riid, pv, dwDestContext, pvDestContext, mshlflags));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr, MSHCTX, IntPtr, MSHLFLAGS, int>)(*(void***)thisPtr)[5])(thisPtr, pStm, riid, pv, dwDestContext, pvDestContext, mshlflags));
GC.KeepAlive(_obj);
}

public unsafe void UnmarshalInterface(IntPtr pStm, Guid* riid, IntPtr* ppv)
{
IntPtr thisPtr = ThisPtr;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr*, int>)(*(void***)thisPtr)[6])(thisPtr, pStm, riid, ppv));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, Guid*, IntPtr*, int>)(*(void***)thisPtr)[6])(thisPtr, pStm, riid, ppv));
GC.KeepAlive(_obj);
}

public unsafe void ReleaseMarshalData(IntPtr pStm)
{
IntPtr thisPtr = ThisPtr;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, int>)(*(void***)thisPtr)[7])(thisPtr, pStm));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, IntPtr, int>)(*(void***)thisPtr)[7])(thisPtr, pStm));
GC.KeepAlive(_obj);
}

public unsafe void DisconnectObject(uint dwReserved)
{
IntPtr thisPtr = ThisPtr;
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, uint, int>)(*(void***)thisPtr)[8])(thisPtr, dwReserved));
Marshal.ThrowExceptionForHR(((delegate* unmanaged[Stdcall]<IntPtr, uint, int>)(*(void***)thisPtr)[8])(thisPtr, dwReserved));
GC.KeepAlive(_obj);
}
}
}
18 changes: 12 additions & 6 deletions src/WinRT.Runtime/Interop/IMarshal.netstandard2.0.cs
Original file line number Diff line number Diff line change
Expand Up @@ -282,32 +282,38 @@ internal IMarshal(ObjectReference<Vftbl> obj)

public unsafe void GetUnmarshalClass(Guid* riid, IntPtr pv, global::WinRT.Interop.MSHCTX dwDestContext, IntPtr pvDestContext, global::WinRT.Interop.MSHLFLAGS mshlFlags, Guid* pCid)
{
Marshal.ThrowExceptionForHR(_obj.Vftbl.GetUnmarshalClass_0(ThisPtr, riid, pv, dwDestContext, pvDestContext, mshlFlags, pCid));
Marshal.ThrowExceptionForHR(_obj.Vftbl.GetUnmarshalClass_0(ThisPtr, riid, pv, dwDestContext, pvDestContext, mshlFlags, pCid));
GC.KeepAlive(_obj);
}

public unsafe void GetMarshalSizeMax(Guid* riid, IntPtr pv, global::WinRT.Interop.MSHCTX dwDestContext, IntPtr pvDestContext, global::WinRT.Interop.MSHLFLAGS mshlflags, uint* pSize)
{
Marshal.ThrowExceptionForHR(_obj.Vftbl.GetMarshalSizeMax_1(ThisPtr, riid, pv, dwDestContext, pvDestContext, mshlflags, pSize));
Marshal.ThrowExceptionForHR(_obj.Vftbl.GetMarshalSizeMax_1(ThisPtr, riid, pv, dwDestContext, pvDestContext, mshlflags, pSize));
GC.KeepAlive(_obj);
}

public unsafe void MarshalInterface(IntPtr pStm, Guid* riid, IntPtr pv, global::WinRT.Interop.MSHCTX dwDestContext, IntPtr pvDestContext, global::WinRT.Interop.MSHLFLAGS mshlflags)
{
Marshal.ThrowExceptionForHR(_obj.Vftbl.MarshalInterface_2(ThisPtr, pStm, riid, pv, dwDestContext, pvDestContext, mshlflags));
Marshal.ThrowExceptionForHR(_obj.Vftbl.MarshalInterface_2(ThisPtr, pStm, riid, pv, dwDestContext, pvDestContext, mshlflags));
GC.KeepAlive(_obj);
}

public unsafe void UnmarshalInterface(IntPtr pStm, Guid* riid, IntPtr* ppv)
{
Marshal.ThrowExceptionForHR(_obj.Vftbl.UnmarshalInterface_3(ThisPtr, pStm, riid, ppv));
Marshal.ThrowExceptionForHR(_obj.Vftbl.UnmarshalInterface_3(ThisPtr, pStm, riid, ppv));
GC.KeepAlive(_obj);
}

public unsafe void ReleaseMarshalData(IntPtr pStm)
{
Marshal.ThrowExceptionForHR(_obj.Vftbl.ReleaseMarshalData_4(ThisPtr, pStm));
Marshal.ThrowExceptionForHR(_obj.Vftbl.ReleaseMarshalData_4(ThisPtr, pStm));
GC.KeepAlive(_obj);
}

public unsafe void DisconnectObject(uint dwReserved)
{
Marshal.ThrowExceptionForHR(_obj.Vftbl.DisconnectObject_5(ThisPtr, dwReserved));
Marshal.ThrowExceptionForHR(_obj.Vftbl.DisconnectObject_5(ThisPtr, dwReserved));
GC.KeepAlive(_obj);
}
}

Expand Down
4 changes: 3 additions & 1 deletion src/WinRT.Runtime/Interop/IWeakReferenceSource.net5.cs
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,8 @@ static class IWeakReferenceSourceMethods
IntPtr objRef = IntPtr.Zero;
try
{
ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, IntPtr*, int>**)ThisPtr)[3](ThisPtr, &objRef));
ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, IntPtr*, int>**)ThisPtr)[3](ThisPtr, &objRef));
GC.KeepAlive(_obj);
return MarshalInterface<global::WinRT.Interop.IWeakReference>.FromAbi(objRef);
}
finally
Expand Down Expand Up @@ -185,6 +186,7 @@ private static int Do_Abi_Resolve(IntPtr thisPtr, Guid* riid, IntPtr* objectRefe

IntPtr objRef;
ExceptionHelpers.ThrowExceptionForHR((*(delegate* unmanaged[Stdcall]<IntPtr, Guid*, IntPtr*, int>**)ThisPtr)[3](ThisPtr, &riid, &objRef));
GC.KeepAlive(_obj);
try
{
return ComWrappersSupport.GetObjectReferenceForInterface(objRef, riid, requireQI: false);
Expand Down
Loading