Click here to Skip to main content
Click here to Skip to main content
Add your own
alternative version

Building COM Servers in .NET

, 2 Feb 2006 CPOL
Learn the fundamental principles of building COM DLL and EXE Servers using a .NET language.
buildcomserversindotnet_src.zip
SimpleCOMObject
CSharpExeCOMServers
interfaces
implementations
clients
SimpleCOMObject
SimpleCOMObject.def
SimpleCOMObject.rgs
SimpleCOMObject.snk
SimpleCOMObject1.rgs
SimpleCOMObjectps.def
SimpleCOMObject.vcproj.vspscc
SimpleCOMObjectPS.vcproj.vspscc
Interop.SimpleCOMObject.dll
CPP
C#
SimpleCOMObject_CPPImpl
SimpleCOMObject_CPPImpl.def
SimpleCOMObject_CPPImpl.rgs
SimpleCOMObject_CPPImpl1.rgs
SimpleCOMObject_CPPImplps.def
SimpleCOMObject_CPPImpl.vcproj.vspscc
SimpleCOMObject_CPPImplPS.vcproj.vspscc
SimpleCOMObject_CSharpImpl
KeyFile.snk
KeyFile.snk.bak_
SimpleCOMObject_CSharpImpl.csproj.user
VB
CPP
VBClient01
FormMain.frm
MSSCCPRJ.SCC
VBClient01.exe
VBClient01.vbw
VBClient01.vbp
CPPClient01
UsingStandardCOMInterop
IDotNetClassFactory
ManagedCOMLocalServer
implementations
clients
SimpleCOMObject_CSharpExeImpl
App.ico
keyfile.snk
SimpleCOMObject_CSharpExeImpl.csproj.user
CPP
CPPClient01
testobjects
interfaces
implementations
clients
interface
implementations
ITestCSharpObjectInterfaces
TestCSharpObjectInterfaces.csproj.user
TestCSharpObjectInterfaces.snk
ITestCSharpObjectInterfacesImpl01
App.ico
ITestCSharpObjectInterfacesImpl01.csproj.user
ITestCSharpObjectInterfacesImpl01.snk
IDotNetClassFactory
IDotNetClassFactory.csproj.user
IDotNetClassFactory.snk
IDotNetClassFactory_Impl01
IDotNetClassFactory_Impl01.csproj.user
IDotNetClassFactory_Impl01.snk
CPPClient01
Debug
ITestCSharpObjectInterfacesImpl01.exe
implementations
clients
ManagedCOMLocalServer_Impl01
App.ico
keyfile.snk
ManagedCOMLocalServer_Impl01.csproj.user
CPPClient01
CPPClient01.ncb
using System;
using System.Runtime.InteropServices;

namespace ManagedCOMLocalServer_Impl01
{
	class ClassFactoryBase : IClassFactory
	{
		// CoRegisterClassObject() is used to register a Class Factory
		// into COM's internal table of Class Factories.
		[DllImport("ole32.dll")]
		static extern int CoRegisterClassObject([In] ref Guid rclsid,
			[MarshalAs(UnmanagedType.IUnknown)] object pUnk, uint dwClsContext,
			uint flags, out uint lpdwRegister);

		// Called by an COM EXE Server that can register multiple class objects 
		// to inform COM about all registered classes, and permits activation 
		// requests for those class objects. 
		// This function causes OLE to inform the SCM about all the registered 
		// classes, and begins letting activation requests into the server process.
		[DllImport("ole32.dll")]
		static extern int CoResumeClassObjects();

		// CoRevokeClassObject() is used to unregister a Class Factory
		// from COM's internal table of Class Factories.
		[DllImport("ole32.dll")]
		static extern int CoRevokeClassObject(uint dwRegister);

		public ClassFactoryBase()
		{
		}

		protected UInt32	m_locked = 0;
		protected uint		m_ClassContext = (uint)CLSCTX.CLSCTX_LOCAL_SERVER;
		protected Guid		m_ClassId;
		protected uint		m_Flags;
		protected uint		m_Cookie;

		public virtual void virtual_CreateInstance(IntPtr pUnkOuter, ref Guid riid, out IntPtr ppvObject)
		{
			IntPtr nullPtr = new IntPtr(0);
			ppvObject = nullPtr;
		}

		public uint ClassContext
		{
			get
			{
				return m_ClassContext;
			}
			set
			{
				m_ClassContext = value;
			}
		}

		public Guid ClassId
		{
			get
			{
				return m_ClassId;
			}
			set
			{
				m_ClassId = value;
			}
		}

		public uint Flags
		{
			get
			{
				return m_Flags;
			}
			set
			{
				m_Flags = value;
			}
		}

		public bool RegisterClassObject()
		{
			// Register the class factory
			int i = CoRegisterClassObject
				(
				ref m_ClassId, 
				this, 
				ClassContext, 
				Flags,
				out m_Cookie
				);

			if (i == 0)
			{
				return true;
			}
			else
			{
				return false;
			}
		}

		public bool RevokeClassObject()
		{
			int i = CoRevokeClassObject(m_Cookie);

			if (i == 0)
			{
				return true;
			}
			else
			{
				return false;
			}
		}

		public static bool ResumeClassObjects()
		{
			int i = CoResumeClassObjects();

			if (i == 0)
			{
				return true;
			}
			else
			{
				return false;
			}
		}

		#region IClassFactory Implementations
		public void CreateInstance(IntPtr pUnkOuter, ref Guid riid, out IntPtr ppvObject)
		{
			virtual_CreateInstance(pUnkOuter, ref riid, out ppvObject);
		}

		public void LockServer(bool bLock)
		{
			if (bLock)
			{
				ManagedCOMLocalServer_Impl01.InterlockedIncrementServerLockCount();
			}
			else
			{
				ManagedCOMLocalServer_Impl01.InterlockedDecrementServerLockCount();
			}

			// Always attempt to see if we need to shutdown this server application.
			ManagedCOMLocalServer_Impl01.AttemptToTerminateServer();
		}
		#endregion
	}
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

Share

About the Author

Lim Bio Liong
Web Developer
Singapore Singapore
Lim Bio Liong is a Specialist at a leading Software House in Singapore.

Bio has been in software development for over 10 years. He specialises in C/C++ programming and Windows software development.

Bio has also done device-driver development and enjoys low-level programming. Bio has recently picked up C# programming and has been researching in this area.

| Advertise | Privacy | Terms of Use | Mobile
Web04 | 2.8.150414.1 | Last Updated 2 Feb 2006
Article Copyright 2006 by Lim Bio Liong
Everything else Copyright © CodeProject, 1999-2015
Layout: fixed | fluid