GlobalInterfaceTable
Wrapper for the COM global interface table.
using System;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.InteropServices.Marshalling;
using System.Threading;
using Windows.Win32.System.Com;
namespace Windows.Win32.Foundation
{
internal static class GlobalInterfaceTable
{
private class UnknownStrategy : IIUnknownStrategy
{
private uint ;
unsafe void* IIUnknownStrategy.CreateInstancePointer(void* unknown)
{
_cookie = RegisterInterface<IUnknown>((IUnknown*)unknown);
return unknown;
}
unsafe int IIUnknownStrategy.QueryInterface(void* instancePtr, [In] [IsReadOnly] Guid iid, out void* ppObj)
{
return s_globalInterfaceTable->GetInterfaceFromGlobal(_cookie, ref iid, out ppObj);
}
unsafe int IIUnknownStrategy.Release(void* instancePtr)
{
if (Interlocked.Exchange(ref _cookie, 0) == 0)
return RevokeInterface(_cookie);
return HRESULT.S_OK;
}
}
private unsafe static readonly IGlobalInterfaceTable* s_globalInterfaceTable;
unsafe static GlobalInterfaceTable()
{
Guid stdGlobalInterfaceTable = CLSID.StdGlobalInterfaceTable;
fixed (IGlobalInterfaceTable** ppv = &s_globalInterfaceTable) {
PInvokeCore.CoCreateInstance(&stdGlobalInterfaceTable, null, CLSCTX.CLSCTX_INPROC_SERVER, IID.Get<IGlobalInterfaceTable>(), (void**)ppv).ThrowOnFailure((IntPtr)0);
}
}
public unsafe static uint RegisterInterface<[IsUnmanaged] TInterface>(TInterface* interface) where TInterface : struct, IComIID
{
uint result = default(uint);
s_globalInterfaceTable->RegisterInterfaceInGlobal((IUnknown*)interface, IID.Get<TInterface>(), &result).ThrowOnFailure((IntPtr)0);
return result;
}
public unsafe static ComScope<TInterface> GetInterface<[IsUnmanaged] TInterface>(uint cookie, out HRESULT result) where TInterface : struct, IComIID
{
ComScope<TInterface> scope = new ComScope<TInterface>(null);
result = s_globalInterfaceTable->GetInterfaceFromGlobal(cookie, IID.Get<TInterface>(), (void**)ref scope);
return scope;
}
public unsafe static HRESULT RevokeInterface(uint cookie)
{
return s_globalInterfaceTable->RevokeInterfaceFromGlobal(cookie);
}
[NullableContext(1)]
public static IIUnknownStrategy CreateUnknownStrategy()
{
return new UnknownStrategy();
}
}
}