3

I am trying to call a C# COM object from C#. I created a class library in C# and exported a Type Library using tlbexe.exe. I then registered the type library using regtlibv12.exe. However when I add a reference to my COM object in Visual Studio I get an error saying:

"The Active X type library ... was exported from a .NET assembly and cannot be added as a reference. Add a reference to the .NET assembly instead."

Any assistance would be greatly appreciated.

Reflux
  • 2,929
  • 4
  • 26
  • 27
  • 2
    The answer is in your error message. Add the. NET assembly as a .NET assembly; no need to go through COM – Andrew Barber Dec 23 '11 at 17:58
  • 1
    Why is this important? There's no point in doing this the hard way, just add the assembly reference like it says. The DLL, not the TLB. The only way to fool the machine is by using late binding. Easiest in C# with the *dynamic* keyword. – Hans Passant Dec 23 '11 at 18:06
  • 1
    The reason I am trying to do this is because I want to be able to access a 32bit DLL from 64bit code by creating a COM object which exposes the DLL interface as a COM interface. As explained here http://blog.mattmags.com/2007/06/30/accessing-32-bit-dlls-from-64-bit-code/ – Reflux Dec 23 '11 at 18:14
  • Like the Error message states, Add the Assembly by right clicking on References and click Add and search for that Assembly .. does this help ? – MethodMan Dec 23 '11 at 18:18
  • 1
    @Reflux - Does the COM interop assembly reference a 32-bit native DLL? Is that the problem you're trying to solve? – M.Babcock Dec 23 '11 at 18:24
  • @M.Babcock What I am trying to do is create a COM Object which will be a wrapper for my 32bit dll that will exist as a separate process and I can communicate from my 64bit app. What I think I did wrong is I'm supposed to create a DCOM not a COM. – Reflux Dec 23 '11 at 18:59
  • Another possible scenario is: the dll/tlb is not "mine", but I should use the one installed on the user's machine. As I would do with, let's say, Excel. If I link the DLL directly then I am bounded to the version I am linking, which is not the COM scope. So the question is licit IMHO – Adhara Nov 08 '16 at 11:28

2 Answers2

4

A 64bit process cannot access the 32bit unmanage code directly. There are 2 domains for COM objects on a 64bit system. One for 64bit processes and one for 32bit processes. They have different registration areas in the registry, so if you regsiter a 32bit only Com object, as far as a 64bit process is concerned is does not exist. Now if you have an assembly that is target for ANY_CPU it can be loaded into either a 64bit or 32bit process by the CLR. However, if ANY_CPU assembly is loaded into a 64bit process, it still is not goign to be able to load any 32bit unmaged code. The solution metioned in the artical uses DCOM and IPC to create an out of process call from 64bit to 32bit code.

You can do the same thing a lot easyer in .Net with WCF. You create a WCF server process that is 32bit that acesses your 32bit managed code. Your 64bit process is a WCF client and makes calls to the 32bit server. You can avoid the network stack by using the Named Pipes protical supported by WCF.

user957902
  • 3,010
  • 14
  • 18
  • Yea.. I got DCOM and COM mixed up. I am wondering what kind of performance hit will I be getting if I used WCF with Named Pipes compared to if I managed to get a hold of a 64bit version of my dll? – Reflux Dec 23 '11 at 19:57
  • 1
    Its obviously not going to be as fast as the dll loaded directly into you process space. I would think speed is going to be directly related to the size of the parameter data in your method calls. It going to take longer to serialize and transfer a huge struct trhough the pipe than it will an int. – user957902 Dec 23 '11 at 20:18
2

The article mentioned in your comment above applies to unmanaged (or native) code. This is not a problem in .NET provided that you compile the host application as AnyCPU (and I think there may be a problem using x64 assemblies on x86 machines, not sure though). You can ignore the COM interop stuff in your 32-bit DLL (assuming you don't need it for anything else) and just reference it from your 64-bit assembly (just make sure to change the target architecture to AnyCPU).

M.Babcock
  • 18,753
  • 6
  • 54
  • 84
  • The 32bit dll I want to reference is unmanaged code. Is a 64bit assembly able to reference it? I currently have access to a 64bit machine to test it, but other developers on my team said they had issues. – Reflux Dec 23 '11 at 19:23
  • @Reflux - Even assemblies complied as x86 (32-bit) can run on 64-bit machines. And that would be my recommendation, compile your "host" program as an x86 assembly and then use the standard P/Invoke API's to access your unmanaged 32-bit DLL. – M.Babcock Dec 23 '11 at 19:36