Search code examples
c++windowscomatldcom

COM dll unregister issue


I have a project which has many COM dlls, for a requirement I had to unregister a COM Dll, which I did by calling Regsvr32 -u option and the dll is unregistered.

This de-register operation seems to remove an interface say ICommon interface, which is making other COM objects unusable.

This ICommon interface is implemented by all other COM Components, in the registry script of the unregistered COM Dll, I don't see any code that removes this ICommon interface form registry, how is this getting removed.

How is the interface information removed for a given CoClass, does the BEGIN_COM_MAP and COM_INTERFACE_ENTRY play any role?


Solution

  • COM is rife with DLL Hell problems. The failure mode here is that uninstalling the server will also remove the keys from HKLM\Software\Classes\Interface. Which tells COM which proxy/stub implementation should be used to marshal the interface across apartment boundaries. The ProxyStubClsId32 key for the interface identifies the proxy.

    So that breaks any client program that use other COM servers that implement the interface, they can no longer marshal the interface and they will die at runtime with E_NOINTERFACE. In itself a confuzzling error code, you'd assume that the interface somehow has vanished but it actually complains about the COM object not implementing IMarshal. The last gasp when COM cannot find the key in the registry.

    Not that this is normally hard to fix, you'd simply have to re-register the COM server that fails, it will put the key back.

    There is no real defense against this lossage, you'd have to implement an elaborate reference counting scheme that records how many COM servers have a dependency on the the proxy and only remove the key (and the DLL, if it is a custom proxy) when it counts down to zero. This has been done, it however takes just a single installer that doesn't buy into the scheme, or an unwise Regsvr32.exe /u executed from the command line like you did, to make it fail.