none
Include type library in DLL? RRS feed

  • Question

  • Hi,

    I'm writing a managed class that I'm exposing to a COM client.  Everything works.  The only question I have is, right now when I build the project in Visual Studio, I get a DLL and a .tlb as outputs.  I need register both the dll and .tlb with COM (using regasm or regasm + regtlibv2), if my COM client wants to make use of a type library.  

    My question is, is there some way to generate a DLL that contains the type library information embedded, so that I don't need to redistribute the .tlb?

    Thanks,

    Notre

    Wednesday, April 25, 2012 12:05 AM

Answers

  • Hello Notre,

    >> I would think that if the COM client (e.g. a C++ program) just needs the CLSIDs, it could probably get away without a type library...

    1. A C++ program would normally #import a type library in order to obtain C++ type information on COM classes (including those generated from a COM-visible .NET class libraries, i.e. CCWs).

    2. At runtime, information from the type library (generated for a COM-visible class library) is also required for proper marshaling of interfaces and parameter types from the managed world to the unmanaged world.

    3. As far as COM is concerned there are only two types of marshaling :

    3.1 Type library marshaling, i.e. marshaling performed using a registered type library.

    3.2 Proxy-stub DLL marshaling, i.e. marshaling performed using a pair of DLLs (a proxy DLL and a stub DLL).

    Current .NET framework language compilers (e.g. Visual C#) are currently not able to produce proxy and stub DLLs. It can only produce type libraries for COM-visible class libraries.

    4. Hence a type library is essential in the proper runtime usage of COM-visible .NET classes by an unmanaged client (e.g VC++, VB6 programs).

    5. And even if you are able to embed a type library as a resource of an assembly, it will not be very useful as far as COM clients are concerned :

    5.1 regsvr32.exe does not reach for any embedded type libraries, it calls the exported DllRegisterServer() function from a COM DLL, which your class library DLL will not have.

    5.2 regasm.exe will not reach for any embedded type libraries, it generates a type library based on the metadata contained in the assembly.

    - Bio.


    Please visit my blog : http://limbioliong.wordpress.com/

    • Proposed as answer by Mike FengModerator Thursday, April 26, 2012 7:42 AM
    • Marked as answer by Notre Thursday, April 26, 2012 11:41 PM
    Wednesday, April 25, 2012 11:40 PM

All replies

  • Hi, 

    I think you can embed tlb into dll as a resource, please refer to these

    http://support.microsoft.com/kb/122285

    http://stackoverflow.com/questions/417803/how-to-embed-tlb-as-a-resource-file-into-net-assembly-dll

    Does this helps you?


    If this post answers your question, please click "Mark As Answer". If this post is helpful please click "Mark as Helpful".

    Wednesday, April 25, 2012 9:26 AM
  • Hi Kris,

    This is helpful, and I think it gets me part of the way there.  I'd have a DLL with the type library included.  But the next question is, how do I register that DLL with the embedded type library?  If this were strictly a native DLL, I could use regsvr32.  As it is a managed assembly, I need to use regasm.exe, but that won't be aware of the embedded .tlb resource.

    Thanks,

    Notre

    Wednesday, April 25, 2012 5:08 PM
  • COM doesn't understand .NET dll. It can understand only TLB which is a CCW wrapper over .NET DLL. Hence, to make your .NET dll consumable by COM, you must create and districbute TLB.


    Please mark this post as answer if it solved your problem. Happy Programming!

    Wednesday, April 25, 2012 5:30 PM
  • Yeah, I realize that COM doesn't know about .NET.  I would think that if the COM client (e.g. a C++ program) just needs the CLSIDs, it could probably get away without a type library, and rely on what is generated by regasm.exe. In my case, my caller expects to go through a type library, so this won't work for me.

    The idea that Kris suggested is interesting, and I partially tried it.  It does end up embedding a type library as a Win32 resource.  I didn't try using it from a COM client, as I noticed a problem with embedding this type library as a win32 resource - it wiped out version information normally generated from the assembly's metadata.  I don't want to lose that.

    I've got another idea I'm going to try, and then I'll report back on my findings.

    Notre

    Wednesday, April 25, 2012 9:59 PM
  • Hello Notre,

    >> I would think that if the COM client (e.g. a C++ program) just needs the CLSIDs, it could probably get away without a type library...

    1. A C++ program would normally #import a type library in order to obtain C++ type information on COM classes (including those generated from a COM-visible .NET class libraries, i.e. CCWs).

    2. At runtime, information from the type library (generated for a COM-visible class library) is also required for proper marshaling of interfaces and parameter types from the managed world to the unmanaged world.

    3. As far as COM is concerned there are only two types of marshaling :

    3.1 Type library marshaling, i.e. marshaling performed using a registered type library.

    3.2 Proxy-stub DLL marshaling, i.e. marshaling performed using a pair of DLLs (a proxy DLL and a stub DLL).

    Current .NET framework language compilers (e.g. Visual C#) are currently not able to produce proxy and stub DLLs. It can only produce type libraries for COM-visible class libraries.

    4. Hence a type library is essential in the proper runtime usage of COM-visible .NET classes by an unmanaged client (e.g VC++, VB6 programs).

    5. And even if you are able to embed a type library as a resource of an assembly, it will not be very useful as far as COM clients are concerned :

    5.1 regsvr32.exe does not reach for any embedded type libraries, it calls the exported DllRegisterServer() function from a COM DLL, which your class library DLL will not have.

    5.2 regasm.exe will not reach for any embedded type libraries, it generates a type library based on the metadata contained in the assembly.

    - Bio.


    Please visit my blog : http://limbioliong.wordpress.com/

    • Proposed as answer by Mike FengModerator Thursday, April 26, 2012 7:42 AM
    • Marked as answer by Notre Thursday, April 26, 2012 11:41 PM
    Wednesday, April 25, 2012 11:40 PM
  • Hi Bio,

    I guess when I thinking of not using a type library, I was remembering back to C++ where the COM server wasn't in managed code. I'm fairly certainly (although it's been years so my memory may be wrong), that I was able to create instances of COM objects without a type library, assuming I had the appropriate header files in the client C++ application.  I guess the lack of marshalling is what would get me in trouble, once I have one of the COM objects being managed code.

    As far as regsvr32 not working and regasm not working by default, I realize that is the case.  My idea, and this I was successful in doing, was to:

    1) generate a .tlb file

    2) embed the .tlb file as a resource (not win32 resource, but a 'regular' embedded resource) in the assembly

    3) implement custom registration function functions (as per http://social.msdn.microsoft.com/Forums/en-US/clr/thread/487613e6-d0ba-4860-91b4-5fad41f27d88).

    a) In the registration function, I would

    i)serialize the .tlb to disk, if it wasn't already present

    ii) use pinvkoe and LoadTypeLib & RegisterTypeLib to resgister the .tlb with COM

    b) in the unregister function, I would use LoadTypeLib and UnregisterTypeLib to unregister my type lib

    By doing all the above, I didn't have to explicitly redistribute a DLL and .tlb file.  However, it would dynamically create a .tlb file and ultimately register the .tlb file.  I don't think this actually gains me much, if anything, instead of using 

    regasm /codebase MyProject.dll /tlb:MyProject.tlb

    to register and

    regasm /unregister MyProject.dll /tlb:MyProject.tlb

    to unregister.

    Thanks,

    Notre

    Thursday, April 26, 2012 11:39 PM