// constructor public WebBrowserSiteEx(WebBrowserEx host) : base(host) { // This code causes problems on XP if (host.Version.Major >= 9) { _host = host; // get the CCW object for this _unkOuter = Marshal.GetIUnknownForObject(this); Marshal.AddRef(_unkOuter); try { // aggregate the CCW object with the helper Inner object _inner = new Inner(this); _unkInnerAggregated = Marshal.CreateAggregatedObject(_unkOuter, _inner); // obtain private WebBrowserSite COM interfaces _baseIDocHostUIHandler = (NativeMethods.IDocHostUIHandler)Marshal.GetTypedObjectForIUnknown(_unkInnerAggregated, typeof(NativeMethods.IDocHostUIHandler)); } finally { Marshal.Release(_unkOuter); } } }
public void CreateAggregatedInstance( string assemblyName, string typeName, IComAggregator outerObject) { IntPtr pOuter = IntPtr.Zero; IntPtr pInner = IntPtr.Zero; try { // We use Marshal.CreateAggregatedObject to create a CCW where // the inner object (the target managed add-in) is aggregated // with the supplied outer object (the shim). pOuter = Marshal.GetIUnknownForObject(outerObject); object innerObject = AppDomain.CurrentDomain.CreateInstanceAndUnwrap( assemblyName, typeName); pInner = Marshal.CreateAggregatedObject(pOuter, innerObject); // Make sure the shim has a pointer to the add-in. outerObject.SetInnerPointer(pInner); } finally { if (pOuter != IntPtr.Zero) { Marshal.Release(pOuter); } if (pInner != IntPtr.Zero) { Marshal.Release(pInner); } } }
public void CreateAggregatedObject_NonGeneric_ReturnsExpected() { var original = new object(); IntPtr ptr = Marshal.GetIUnknownForObject(original); try { int toAggregate = 1; IntPtr aggregatedObject1 = Marshal.CreateAggregatedObject(ptr, (object)toAggregate); try { Assert.NotEqual(IntPtr.Zero, aggregatedObject1); IntPtr aggregatedObject2 = Marshal.CreateAggregatedObject(ptr, (object)toAggregate); Assert.NotEqual(IntPtr.Zero, aggregatedObject2); Assert.NotEqual(aggregatedObject1, aggregatedObject2); } finally { Marshal.Release(aggregatedObject1); } } finally { Marshal.Release(ptr); } }
int Native.IClassFactory.CreateInstance(IntPtr pUnkOuter, Guid riid, out IntPtr ppvObject) { // query the current instance for a given interface ppvObject = IntPtr.Zero; var pUnk = pUnkOuter != IntPtr.Zero ? Marshal.CreateAggregatedObject(pUnkOuter, this) : Marshal.GetIUnknownForObject(this); try { return(Marshal.QueryInterface(pUnk, ref riid, out ppvObject)); } finally { Marshal.Release(pUnk); } }
public IntPtr Create(string typeName, IntPtr outer) { var type = Type.GetType(typeName); if (type == null) { throw new InvalidOperationException("Invalid type name."); } return(Marshal.CreateAggregatedObject(outer, Activator.CreateInstance(type))); }
/// <summary> /// Creates a new instance of fullQualifiedTypeName and call outerObject to publish the instance /// to the outer caller. /// </summary> /// <param name="assemblyName">name or strong name where the target type is located</param> /// <param name="fullQualifiedTypeName">type to create</param> /// <param name="outerAggregator">caller as outer aggregator</param> /// <param name="shimHost">outer shim host</param> /// <exception cref="ArgumentNullException">argument is null or empty</exception> /// <exception cref="MissingMethodException">no matching public constructor was found</exception>/param> /// <exception cref="TypeLoadException">typename was not found in assemblyName</exception>/param> /// <exception cref="FileNotFoundException">assemblyName was not found</exception>/param> /// <exception cref="MethodAccessException">the caller does not have permission to call this constructor</exception>/param> /// <exception cref="AppDomainUnloadedException">the operation is attempted on an unloaded application domain.</exception>/param> /// <exception cref="BadImageFormatException">assemblyName is not a valid assembly</exception> /// <exception cref="FileLoadException">an assembly or module was loaded twice with two different evidences</exception> /// <exception cref="InvalidOperationException">unexpected error</exception> public void CreateAggregatedInstance(string assemblyName, string fullQualifiedTypeName, IOuterComAggregator outerAggregator, IShimHost shimHost) { if (String.IsNullOrWhiteSpace(assemblyName)) { throw new ArgumentNullException("assemblyName"); } if (String.IsNullOrWhiteSpace(fullQualifiedTypeName)) { throw new ArgumentNullException("fullQualifiedTypeName"); } if (null == outerAggregator) { throw new ArgumentNullException("outerAggregator"); } IntPtr pOuter = IntPtr.Zero; IntPtr pInner = IntPtr.Zero; try { pOuter = Marshal.GetIUnknownForObject(outerAggregator); if (IntPtr.Zero != pOuter) { object innerObject = AppDomain.CurrentDomain.CreateInstanceAndUnwrap(assemblyName, fullQualifiedTypeName); TrySetShimHost(innerObject, shimHost); pInner = Marshal.CreateAggregatedObject(pOuter, innerObject); if (IntPtr.Zero != pInner) { outerAggregator.SetInnerAddin(pInner); } } if (IntPtr.Zero == pOuter || IntPtr.Zero == pInner) { throw new InvalidOperationException("Unexpected result while getting IUnkown Pointer."); } } catch (Exception exception) { NetOffice.DebugConsole.Default.WriteException(exception); throw; } finally { if (IntPtr.Zero != pOuter) { Marshal.Release(pOuter); } if (IntPtr.Zero != pInner) { Marshal.Release(pInner); } Marshal.ReleaseComObject(outerAggregator); } }
public ImprovedClass() { var typeBaseIComInterface = typeof(OldLibrary.BaseClass).GetInterfaces().First((t) => t.GUID == typeof(IComInterface).GUID); // get OldLibrary.BaseClass.IComInterface this.unkBaseIComInterface = Marshal.GetComInterfaceForObject(this, typeBaseIComInterface, CustomQueryInterfaceMode.Ignore); this.unkBaseShim = Marshal.CreateAggregatedObject(this.unkBaseIComInterface, new Inner(this.unkBaseIComInterface)); this.baseComInterface = (IComInterface)Marshal.GetTypedObjectForIUnknown(this.unkBaseShim, typeof(IComInterface)); ((IComInterface)this).ComMethod(this); // works! }
private static object CreateAggregatedObject(object pUnkOuter, object comObject) { IntPtr outerPtr = Marshal.GetIUnknownForObject(pUnkOuter); try { IntPtr innerPtr = Marshal.CreateAggregatedObject(outerPtr, comObject); return(Marshal.GetObjectForIUnknown(innerPtr)); } finally { // Decrement the above 'Marshal.GetIUnknownForObject()' Marshal.Release(outerPtr); } }
public object CreateAggregatedObject(object managedObject) { Contract.ThrowIfNull(managedObject, "managedObject"); // 1. Create our native COM object that will aggregate "managedObject" var wrapperUnknown = BlindAggregatorFactory.CreateWrapper(); // AddRef'ed try { // 2. Ask the CLR to create an object supporting aggregation for "managedObject" var innerUnknown = Marshal.CreateAggregatedObject(wrapperUnknown, managedObject); // AddRef'ed try { // 3. Create a GC Handle to the managed object for later retrieval var handle = GCHandle.Alloc(managedObject, GCHandleType.Normal); var freeHandle = true; try { // 4. Now, link our native (aggregator) with the IUnknown of the CLR inner object, the // GC Handle managed and the GC handle of the managed object. // GC handle will be free by the native wrapper. BlindAggregatorFactory.SetInnerObject(wrapperUnknown, innerUnknown, GCHandle.ToIntPtr(handle)); freeHandle = false; } finally { if (freeHandle) { handle.Free(); } } OnAggregatedObjectCreated(); // 5. All done: Ask the CLR to create an RCW for the native aggregator object wrapperRCW = Marshal.GetObjectForIUnknown(wrapperUnknown); return((IComWrapper)wrapperRCW); } finally { Marshal.Release(innerUnknown); } } finally { Marshal.Release(wrapperUnknown); } }
public static object CreateAggregatedObject(object pUnkOuter, object comObject) { Debug.Assert(pUnkOuter != null && comObject != null); IntPtr outerPtr = Marshal.GetIUnknownForObject(pUnkOuter); try { IntPtr innerPtr = Marshal.CreateAggregatedObject(outerPtr, comObject); return(Marshal.GetObjectForIUnknown(innerPtr)); } finally { // Decrement the above 'Marshal.GetIUnknownForObject()' Marshal.ReleaseComObject(pUnkOuter); } }
IntPtr _unkAggregated; // aggregated proxy public BaseClassComProxy(object outer) { _outer = new WeakReference(outer); _interfaces = outer.GetType().BaseType.GetInterfaces(); var unkOuter = Marshal.GetIUnknownForObject(outer); try { // CreateAggregatedObject does AddRef on this // se we provide IDispose for proper shutdown _unkAggregated = Marshal.CreateAggregatedObject(unkOuter, this); } finally { Marshal.Release(unkOuter); } }
internal static ComProxy Create(IntPtr outer, object obj, IDisposable disp) { if (outer == IntPtr.Zero) { throw Fx.AssertAndThrow("Outer cannot be null"); } IntPtr zero = IntPtr.Zero; zero = Marshal.CreateAggregatedObject(outer, obj); int num = Marshal.AddRef(zero); if (3 == num) { Marshal.Release(zero); } Marshal.Release(zero); return(new ComProxy(zero, disp)); }
// constructor public ImprovedClass() { // get OldLibrary.BaseClass.IComInterface via reflection var typeBaseIComInterface = typeof(OldLibrary.BaseClass).GetInterfaces().First((t) => t.GUID == typeof(NewLibrary.IComInterface).GUID); // get the COM interface for OldLibrary.BaseClass.IComInterface _unkBaseIComInterface = Marshal.GetComInterfaceForObject(this, typeBaseIComInterface, CustomQueryInterfaceMode.Ignore); Marshal.AddRef(_unkBaseIComInterface); // protect _unkBaseIComInterface // aggregate it with a helper Inner object _inner = new Inner(_unkBaseIComInterface); _unkInnerAggregated = Marshal.CreateAggregatedObject(_unkBaseIComInterface, _inner); // turn private OldLibrary.BaseClass.IComInterface into NewLibrary.IComInterface _baseIComInterface = (IComInterface)Marshal.GetTypedObjectForIUnknown(_unkInnerAggregated, typeof(NewLibrary.IComInterface)); Marshal.Release(_unkBaseIComInterface); }
public DCWebBrowserSite(WebBrowser host) : base(host) { // get the CCW object for this _unkOuter = Marshal.GetIUnknownForObject(this); Marshal.AddRef(_unkOuter); try { // aggregate the CCW object with the helper Inner object _inner = new Inner(this); _unkInnerAggregated = Marshal.CreateAggregatedObject(_unkOuter, _inner); // obtain private WebBrowserSite COM interfaces _baseIDocHostUIHandler = (UnsafeNativeMethods.IDocHostUIHandler)Marshal.GetTypedObjectForIUnknown(_unkInnerAggregated, typeof(UnsafeNativeMethods.IDocHostUIHandler)); } finally { Marshal.Release(_unkOuter); } }
internal static ComProxy Create(IntPtr outer, object obj, IDisposable disp) { if (outer == IntPtr.Zero) { throw Fx.AssertAndThrow("Outer cannot be null"); } IntPtr inner = IntPtr.Zero; inner = Marshal.CreateAggregatedObject(outer, obj); int refCount = Marshal.AddRef(inner); // Workaround for the CLR ref count issue. if (3 == refCount) { Marshal.Release(inner); } Marshal.Release(inner); return(new ComProxy(inner, disp)); }
public void CreateInstance( [MarshalAs(UnmanagedType.Interface)] object pUnkOuter, ref Guid riid, [MarshalAs(UnmanagedType.Interface)] out object ppvObject) { if (riid != Marshal.IID_IUnknown) { bool found = false; // Verify the class implements the desired interface foreach (Type i in this.classType.GetInterfaces()) { if (i.GUID == riid) { found = true; break; } } if (!found) { // E_NOINTERFACE throw new InvalidCastException(); } } ppvObject = Activator.CreateInstance(this.classType); if (pUnkOuter != null) { try { IntPtr outerPtr = Marshal.GetIUnknownForObject(pUnkOuter); IntPtr innerPtr = Marshal.CreateAggregatedObject(outerPtr, ppvObject); ppvObject = Marshal.GetObjectForIUnknown(innerPtr); } finally { // Decrement the above 'Marshal.GetIUnknownForObject()' Marshal.ReleaseComObject(pUnkOuter); } } }
// constructor public ImprovedWebBrowserSite(WebBrowser host) : base(host) { // get WebBrowserSiteBase.IOleClientSite via reflection var typeBaseIOleClientSite = typeof(WebBrowserSiteBase).GetInterfaces().First((t) => t.GUID == typeof(IOleClientSite).GUID); // get the COM interface for WebBrowserSiteBase.IOleClientSite _unkBaseIOleClientSite = Marshal.GetComInterfaceForObject(this, typeBaseIOleClientSite, CustomQueryInterfaceMode.Ignore); Marshal.AddRef(_unkBaseIOleClientSite); // protect _unkBaseIOleClientSite // aggregate it with the helper Inner object _inner = new Inner(_unkBaseIOleClientSite); _unkInnerAggregated = Marshal.CreateAggregatedObject(_unkBaseIOleClientSite, _inner); // turn private WebBrowserSiteBase.IOleClientSite into our own IOleClientSite _baseIOleClientSite = (IOleClientSite)Marshal.GetTypedObjectForIUnknown(_unkInnerAggregated, typeof(IOleClientSite)); Marshal.Release(_unkBaseIOleClientSite); }
// constructor public ImprovedWebBrowserSite(WebBrowser host) : base(host) { // get the CCW object for this _unkOuter = Marshal.GetIUnknownForObject(this); Marshal.AddRef(_unkOuter); try { // aggregate the CCW object with the helper Inner object _inner = new Inner(this); _unkInnerAggregated = Marshal.CreateAggregatedObject(_unkOuter, _inner); // turn private WebBrowserSiteBase.IOleClientSite into our own IOleClientSite _baseIOleClientSite = (IOleClientSite)Marshal.GetTypedObjectForIUnknown(_unkInnerAggregated, typeof(IOleClientSite)); } finally { Marshal.Release(_unkOuter); } }
public void CreateAggregatedObject_ObjectNotCollectible_ReturnsExpected() { var original = new object(); IntPtr ptr = Marshal.GetIUnknownForObject(original); try { AssemblyBuilder assemblyBuilder = AssemblyBuilder.DefineDynamicAssembly(new AssemblyName("Assembly"), AssemblyBuilderAccess.RunAndCollect); ModuleBuilder moduleBuilder = assemblyBuilder.DefineDynamicModule("Module"); TypeBuilder typeBuilder = moduleBuilder.DefineType("Type"); Type type = typeBuilder.CreateType(); object o = Activator.CreateInstance(type); Assert.Throws <NotSupportedException>(() => Marshal.CreateAggregatedObject(ptr, o)); Assert.Throws <NotSupportedException>(() => Marshal.CreateAggregatedObject <object>(ptr, o)); } finally { Marshal.Release(ptr); } }
/// <summary> /// Constructor /// </summary> /// <param name="outerObject">The object that needs interface requests filtered</param> /// <param name="queryForType">determines whether we call QueryInterface for the interface or not</param> /// <remarks>if the passed in outerObject is known to point to the correct vtable for the interface, then queryForType can be false</remarks> /// <returns>if outerObject is IntPtr.Zero, then a null wrapper, else an aggregated wrapper</returns> public RestrictComInterfaceByAggregation(IntPtr outerObject, bool queryForType = true) { if (queryForType) { var IID = typeof(T).GUID; if (ComHelper.HRESULT_FAILED(Marshal.QueryInterface(outerObject, ref IID, out _outerObject))) { // allow null wrapping here return; } } else { _outerObject = outerObject; Marshal.AddRef(_outerObject); } var aggObjPtr = Marshal.CreateAggregatedObject(_outerObject, this); WrappedObject = (T)Marshal.GetObjectForIUnknown(aggObjPtr); // when this CCW object gets released, it will free the aggObjInner (well, after GC) Marshal.Release(aggObjPtr); // _wrappedObject holds a reference to this now }
public void CreateAggregatedInstance( string assemblyName, string typeName, IComAggregator outerObject) { IntPtr pOuter = IntPtr.Zero; IntPtr pInner = IntPtr.Zero; try { // We use Marshal.CreateAggregatedObject to create a CCW where // the inner object (the target managed add-in) is aggregated // with the supplied outer object (the shim). pOuter = Marshal.GetIUnknownForObject(outerObject); object innerObject = AppDomain.CurrentDomain.CreateInstanceAndUnwrap( assemblyName, typeName); pInner = Marshal.CreateAggregatedObject(pOuter, innerObject); // Make sure the shim has a pointer to the add-in. outerObject.SetInnerPointer(pInner); } finally { if (pOuter != IntPtr.Zero) { Marshal.Release(pOuter); } if (pInner != IntPtr.Zero) { Marshal.Release(pInner); } // FIX: Bug discovered after release of 2.3.1.0. // We call ReleaseComObject on the outer object (ConnectProxy) // to make sure we delete the RCW, and prevent the CLR from // holding onto it indefinitely (and keeping the host alive). Marshal.ReleaseComObject(outerObject); } }
public void CreateAggregatedObject_AlreadyHasContainer_ThrowsArgumentException() { var o1 = new object(); IntPtr ptr1 = Marshal.GetIUnknownForObject(o1); try { var o2 = new object(); IntPtr ptr2 = Marshal.GetIUnknownForObject(o2); try { AssertExtensions.Throws<ArgumentException>("o", () => Marshal.CreateAggregatedObject(ptr1, o1)); AssertExtensions.Throws<ArgumentException>("o", () => Marshal.CreateAggregatedObject(ptr1, o2)); } finally { Marshal.Release(ptr2); } } finally { Marshal.Release(ptr1); } }
int IVsAggregatableProjectFactoryCorrected.PreCreateForOuter(IntPtr outerProjectIUnknown, out IntPtr projectIUnknown) { projectIUnknown = IntPtr.Zero; // always initialize out parameters of COM interfaces! var newProject = PreCreateForOuter(outerProjectIUnknown); var newProjectIUnknown = IntPtr.Zero; var localRegistry = (ILocalRegistryCorrected)this._serviceProvider.GetService(typeof(SLocalRegistry)); Debug.Assert(localRegistry != null, "Could not get the ILocalRegistry object"); if (localRegistry == null) { throw new InvalidOperationException(); } var clsid = typeof(Microsoft.VisualStudio.ProjectAggregator.CProjectAggregatorClass).GUID; var riid = VSConstants.IID_IUnknown; var dwClsCtx = (uint)CLSCTX.CLSCTX_INPROC_SERVER; var aggregateProjectIUnknown = IntPtr.Zero; IVsProjectAggregator2 vsProjectAggregator2 = null; try { ErrorHandler.ThrowOnFailure(localRegistry.CreateInstance(clsid, outerProjectIUnknown, ref riid, dwClsCtx, out aggregateProjectIUnknown)); // If we have a non-NULL punkOuter then we need to create a COM aggregated object with that punkOuter, // if not then we are the top of the aggregation. if (outerProjectIUnknown != IntPtr.Zero) { newProjectIUnknown = Marshal.CreateAggregatedObject(outerProjectIUnknown, newProject); } else { newProjectIUnknown = Marshal.CreateAggregatedObject(aggregateProjectIUnknown, newProject);; } vsProjectAggregator2 = (IVsProjectAggregator2)Marshal.GetObjectForIUnknown(aggregateProjectIUnknown); if (vsProjectAggregator2 != null) { vsProjectAggregator2.SetMyProject(newProjectIUnknown); } // We return the native ProjectAggregator COM object as the project created by our project // factory. This ProjectAggregator main purpose is to manage the fact that the punkInner pointer // for the project aggregation is not known until after IVsAggregateProject::SetInnerProject is // called. This native object has a special implementation of QueryInterface that can handle // the SetInnerProject mechanism. The ProjectAggregator will first delegate QueryInterface // calls to our managed project and then delegates to the inner Project. // Note: we need to return an AddRef'ed IUnknown (AddRef comes from CreateInstance call). projectIUnknown = aggregateProjectIUnknown; aggregateProjectIUnknown = IntPtr.Zero; } finally { if (newProjectIUnknown != IntPtr.Zero) { Marshal.Release(newProjectIUnknown); } if (aggregateProjectIUnknown != IntPtr.Zero) { Marshal.Release(aggregateProjectIUnknown); } } if (projectIUnknown == IntPtr.Zero) { return(VSConstants.E_FAIL); } return(VSConstants.S_OK); }
public void CreateAggregateObject_NullObject_ThrowsArgumentNullException() { AssertExtensions.Throws <ArgumentNullException>("o", () => Marshal.CreateAggregatedObject((IntPtr)1, null)); }
public void CreateAggregateObject_ZeroPointer_ThrowsArgumentNullException() { AssertExtensions.Throws <ArgumentNullException>("pOuter", () => Marshal.CreateAggregatedObject(IntPtr.Zero, 1)); }
public void CreateAggregatedObject_Unix_ThrowsPlatformNotSupportedException() { Assert.Throws <PlatformNotSupportedException>(() => Marshal.CreateAggregatedObject(IntPtr.Zero, 1)); }
/// <summary> /// Aggregate the com server which exposes the specified interface, the Guid of the interface that exposed to /// client is the specified guid. /// </summary> /// <param name="guid">Guid of the interface that specified the interface</param> /// <param name="interfaceType">Interface that exposed to client</param> /// <param name="classType">Server class that implement the interface</param> private void Aggregate(Guid guid, Type interfaceType, Type classType) { if (guid == null || interfaceType == null || classType == null) { throw new ArgumentNullException("Parameter should not be null"); } // if already have interface registered with same Guid, action fails if (guidTypeDictionary.ContainsKey(guid)) { throw new InvalidOperationException(String.Format("Interface with Guid {0} has already been registered" + " in the server, please unregister the interface before registration!", guid)); } guidTypeDictionary.Add(guid, interfaceType); if (interfaceClassDictionary.ContainsKey(interfaceType)) { Type tmpClassType = interfaceClassDictionary[interfaceType]; // if alreay have another registered class that implements and exposes the same interfae, action fails if (tmpClassType != classType) { // roll back, remove the previous registration of GUID/Interface guidTypeDictionary.Remove(guid); string errorMsg = String.Format("Can not register the interface {0} which is already exposed and implemented by Class {1} .", interfaceType.ToString(), tmpClassType.ToString()); throw new InvalidOperationException(errorMsg); } // have already created the instance of the type and maintained the dictionaries. return; } // <Interface Guid, Interface Type> interfaceClassDictionary.Add(interfaceType, classType); // <Class Type, Instance> // construct a new object instance if do not have, aggreate the object and store the mapping object o = null; if (!classInstanceDictionary.ContainsKey(classType)) { // create the new instance ConstructorInfo ci = classType.GetConstructor(Type.EmptyTypes); o = ci.Invoke(new Object[0]); classInstanceDictionary.Add(classType, o); // Set the aggregator IInnerHoldingOuterReference ins = o as IInnerHoldingOuterReference; if (ins != null) { Console.WriteLine("Set Aggregator for " + o.GetType()); ins.Outer = this; } // Aggregate the object IntPtr pUnk = Marshal.GetIUnknownForObject(this); IntPtr pInnerIUnkPtr = Marshal.CreateAggregatedObject(pUnk, o); // This release is to ensure that ‘this’ don’t hold a ref-count on itself, // which could prevent GC from collecting ‘this’ instance at the end Marshal.Release(pUnk); innerHORCCWList.AddLast(pInnerIUnkPtr); // Inform the aggregated objects who have subscribed to the UnAggregation event if (aggregationEvent != null) { aggregationEvent(guid, interfaceType, classType); } } }
private IntPtr Initialize(Func <object> createInnerObject) { try { // implement IUnknown methods _queryInterfaceMethod = delegate(IntPtr pUnk, ref Guid iid, out IntPtr ppv) { lock (this) { // delegate anything but IID_IUnknown to the aggregated object if (IID_IUnknown == iid) { ppv = _outerObject; Marshal.AddRef(_outerObject); return(S_OK); } return(Marshal.QueryInterface(_aggregatedObject, ref iid, out ppv)); } }; _addRefMethod = delegate(IntPtr pUnk) { lock (this) { return(++_refCount); } }; _releaseMethod = delegate(IntPtr pUnk) { lock (this) { if (0 == --_refCount) { Free(); } return(_refCount); } }; // create the IUnknown vtable var vtable = new UnkVtable(); vtable.pQueryInterface = Marshal.GetFunctionPointerForDelegate(_queryInterfaceMethod); vtable.pAddRef = Marshal.GetFunctionPointerForDelegate(_addRefMethod); vtable.pRelease = Marshal.GetFunctionPointerForDelegate(_releaseMethod); _pVtable = Marshal.AllocCoTaskMem(Marshal.SizeOf(vtable)); Marshal.StructureToPtr(vtable, _pVtable, false); // create the IUnknown object var unkObject = new UnkObject(); unkObject.pVtable = _pVtable; _outerObject = Marshal.AllocCoTaskMem(Marshal.SizeOf(unkObject)); Marshal.StructureToPtr(unkObject, _outerObject, false); // pin the managed ComWrapper instance _gcHandle = GCHandle.Alloc(this, GCHandleType.Normal); // create and aggregate the inner object _aggregatedObject = Marshal.CreateAggregatedObject(_outerObject, createInnerObject()); return(_outerObject); } catch { Free(); throw; } }
public void CreateAggregatedObject_T_ThrowsNotSupportedException() { object value = new object(); Assert.Throws <NotSupportedException>(() => Marshal.CreateAggregatedObject <object>(IntPtr.Zero, value)); }
// CreateAggregatedWrapper returns a reference counted COM pointer to the aggregated object // When it gets released in COM, it should in turn release the internal CCW reference on our AggregationHelper object public static IntPtr CreateAggregatedWrapper(object objectToWrap, Type[] supportedTypes) { return(Marshal.CreateAggregatedObject(Marshal.GetIUnknownForObject(objectToWrap), // aggregated object will own this COM reference, but this is fine, as it is really a managed object new AggregationHelper(objectToWrap, supportedTypes))); }