I just finished building my new COM project (C#, .NET 3.5). This project will be called by a VFP application. It's working great on my development machine, but now I need to know how to deploy it on the user's machine. Click Once isn't available for this kind of project, so I guess I'm stuck with manually distributing the DLL.
So, where should I put the DLL and how do I register it?
BTW, the 3.5 framework is already installed on the user's machine.
TIA
I've really never used RegSvr32 with .Net assemblies, rather I use the regasm with the /codebase option:
C:\Windows\Microsoft.NET\Framework\v2.0.50727\regasm.exe /codebase mydll.dll
You can also use the /tlb option to export the type library and register it.
Of course the easiest way, just create an installer with vstudio and it will do this for you.
Creating a Description of the COM class and Interfaces
.Net assemblies don't include information in Type Library compatible format. So it is necessary for the programmer to run one of two .Net-supplied utilities to extract the assembly description of a class into a Type Library file.
One utility is TLBEXP.EXE, the .Net Type Library Exporter. This command line utility takes as input the name of an assembly DLL file to be converted to a Type Library. The programmer can also specify the name of a Type Library file to be created.
tlbexp ComServer.dll /out:ComServer.tlb
Assembly exported to C:\Magellan\Source\Output\Debug\ComServer.tlb
Once a Type Library has been created, it can be referenced by a COM client to obtain the information necessary for the COM client to bind to the interfaces of the COM class, and activate the COM class at runtime.
Registration of the COM Class and Interfaces
For a COM class to be accessible by the client at runtime, the COM infrastructure must know how to locate the code that implements the COM class. The following command accomplishes this:
regasm ComServer.dll
Your DLL can be put anywhere you wish, but a good choice is C:\Program Files\MyApplication.
http://www.csharphelp.com/archives/archive190.html
Related
I'm trying to register my Classlib.dll for using COM interop with the regasm.exe tool.
In general this is not a problem.
like this: > regasm.exe MyAsm.dll /tlb: MyAsm.tlb
But now I use a .dll reference in my classlib project. The general registration still works but then the dll reference gets lost and the functions are useless.
I'm sure there is a simple solution for this as the automatic registration via VisualStudio Build settings works fine.
So how can I manually adjust my script?
My current approaches are:
uing the option: regasm /asmpath
use of the tools: Tlbexp.exe, Tlbimp.exe
My current information sources:
Regasm.exe (Assembly Registration Tool)
Registration free COM interop. assembly B reference assembly A?
Registration-Free COM Interop and Dependent Assemblies
Since the documentaries are unfortunately very limited and I am new to the COM topic it would be great if you could help me.
In Visual Studio 2015 if I create a "class library" C# project and then add a reference to a custom COM DLL (created using VB6), VS will then also automatically add all (?) the COM references that the VB6 DLL depends on.
How does it do this? How can it statically figure out what those references are?
Note -- Our VB6 DLL uses "early binding", but even still there is no equivalent of an imports table for COM items like you would see in a traditional "C" style DLL.
You are actually adding a reference to a type library. It is embedded inside the DLL as a resource. You can see it when you use File > Open > File, select the DLL, open the TYPELIB node. It plays the exact same role as metadata in a .NET assembly, listing the type definitions of the exposed interfaces and classes. It has a binary format, you can decompile it with the OleView.exe utility.
And has dependency info as well, the registry helps to find such dependent type libraries (HKLM\Software\Wow6432Node\Classes\Typelib key). Roughly the same role that the GAC plays in .NET. COM just isn't as different from .NET as everybody assumes :) The first version of the CLR was created by the COM+ group at Microsoft. Eliminating the registration and DLL Hell problems associated with COM were on the top of the todo list.
Type libraries are not exactly legacy, they still play a pivotal role in the brand-new WinRT (aka UWP, aka Modern UI). Which is COM-based at its core, very well hidden. But the olden format was retired because of limitations, replaced by the .winmd format. Which is exactly the same as the .NET metadata format. Any .NET decompiler can show their content.
The reason that Visual Studio type library importer chases type library dependencies is to gather type information to map to .NET.
A type library doesn't have direct dependency information. So this is a very good question: how to track type library dependencies?
The only feasible way to detect type library dependencies is by referring to a type which states the declaring type library.
For instance, if your type library references IXMLDOMDocument in a method's signature, it'll be recorded in a type info record.
You can crawl a type library, by loading one, getting a ITypeLib from it and enumerating ITypeInfos recursively.
You'll eventually see this record. Then, you can get the type's containing type library ID through ITypeInfo::GetContainingTypeLib. If it refers to another type library, you found a dependency.
A crawler may track dependencies all the way until it has no more type libraries to load.
You don't have to crawl every type of every type library to find the strictly necessary set of types, but the job of the type library importer is to mirror type library information to .NET type info and metadata assemblies, so it imports type libraries in full. It's easier to implement, to explain/understand what it's doing and the output is reusable outside the context of the root type library.
If you didn't use early binding, your type library would instead mention IDispatch, IUnknown and/or VARIANT, which would make it impossible to detect any dependency.
You may use registration-free COM in isolated applications to have the dependencies sorted out, but it still doesn't have to be a proper dependency tree, e.g. you may state all dependencies in one manifest.
And remember that type library != DLL. A type library may be embedded as a resource in a DLL or in its own TLB file.
So, this whole talk is about type dependencies, not class/component or other runtime dependencies.
I don't think it is actually statically analyzing all the dependencies.
I think it is just adding the COM references which are part of the public API of the DLL. These would be plainly visible in the typelib which is part of the DLL, as far as I understand it.
Probably other dependencies which are used internally but not in the public interface are neglected.
I am currently trying to reference a .NET COM library in my Visual Basic 6 application. I have registered it, using Regasm and I have set ComVisible to true within my class. However when I try to run my application i get the following error:
ActiveX component can't create object.
My library consists of a very simple function (since I just wanted to test if I could even run it), it just returns the string "Hello World".
I had to use a different machine (machine 1) to create my C# .Net class and then copy that class onto another machine (machine 2) and from there register the dll and reference it in my project. I then tested my project on a separate machine (machine 3) which is were I received the error.
I really need help with this, I have already tried to un-register and re-register it and still to no avail.
Try this.
From an elevated command prompt:
RegAsm /codebase /tlb AssemblyName.dll. Take note of the .tlb file generated.
RegTlib File.tlb
Open your VB6 project and reference the .tlb file.
tlb file(using regasm) is made from a dll(using c# code), and i can use this in c++ using #import. and everything is working fine.
Is there a way, i can use this in C language? I just found that #import is c++ specific. So, can someone please tell me how can i use in my C program?
my main intention is to use COM DLL developed in C# in my C program.
Thanks & Rgds,
~calvin
COM programming in C is very painful, but not impossible. The buck stops here though. The point of a type library is to have a tool auto-generate the COM interface and co-class declarations so that you can use them in your code. Quite similar to a .h file, but language independent. The .NET equivalent is the metadata in an assembly.
Problem is, the tooling isn't available to convert a .tlb to C declarations. I'm sure you are familiar with #import, that's what gets used in MSVC. But it generates C++ code, smart pointers that help you create the COM object, call its interface methods and deal with errors. If there is a tool available that generates C then it is a very well hidden secret.
One trick jumps to mind, you can use OleView.exe, File + View TypeLib to view the contents of the type library. This view is decompiled into IDL, the interface definition language. You can copy and paste this text into an .idl file and compile it with midl.exe with the /header command line option. This generates a .h file that contains both C++ and the C declarations for the interfaces. Ought to get you close, just make sure that the type library is reasonably stable so you don't have to do this very often.
I also faced the same problem as I need to use tlb file in C. And I think you can check the below link which helps
How to call a COM component in C
Thanks,
sveerap
Neither C nor C++ have an #import preprocessor directive.
You can use regasm with /tlb option to register the types in windows registry. After that, you can create your instances like regular COM calls from C++ code.
From MSDN:
When you specify the /tlb option, Regasm.exe generates and registers a type library describing the types found in the assembly. Regasm.exe places the generated type libraries in the current working directory or the directory specified for the output file. Generating a type library for an assembly that references other assemblies may cause several type libraries to be generated at once. You can use the type library to provide type information to development tools like Visual Studio 2005. You should not use the /tlb option if the assembly you are registering was produced by the Type Library Importer (Tlbimp.exe). You cannot export a type library from an assembly that was imported from a type library. Using the /tlb option has the same effect as using the Type Library Exporter (Tlbexp.exe) and Regasm.exe, with the exception that Tlbexp.exe does not register the type library it produces. If you use the /tlb option to registered a type library, you can use /tlb option with the /unregister option to unregistered the type library. Using the two options together will unregister the type library and interface entries, which can clean the registry considerably.
I am building a C# UI to interact with a COM Service (.exe). The VS2005 COM project outputs a valid typelib (TLB), which is referenced by the C# project. However, the VS2005 C# project insists that the service be registered in order to build the C# project, even though the typelib appears perfectly valid when examined with the OLE Object Viewer.
We would rather not register the service on the build server, if possible. Further, debug builds cannot register the COM object as a service, since this makes debugging in general, and startup code in particular, more difficult (can't use F5 - Start Debugging).
What should I look for in order to get this working? Do I need to register just the TypeLib? If so, why would COMInterop insist on having the service or TLB registered in order to build correctly (and, is there a command-line tool for this on Win2003 with VS2005)?
If I recall correctly, once apon a time I built a C# web service which referenced the Win2003 firewall COM object, but we built it on Win2000 (which does not have such a thing) simply by referencing the TLB file with no registration required, so I don't understand why this should be a problem now.
You need to create interop assembly using tlbimp.exe tool. And add reference to this assembly in your project instead of typelib. In this case building will not require registered com server.
If you do not want to ship yet another assembly, you can extract interface description from generated interop assembly using Reflector and include them into project as source files.
Solved this by adding a -regtypelib command to the COM service, which calls the AtlRegisterTypeLib function but does not register the service. Suboptimal because it will leave registery entries on the build server, but quick and it works.