Fabius Wiesner
Fabius Wiesner

Reputation: 926

Visual Basic COM DLL does not load COM .NET assembly at version upgrade

I used to have a Visual Basic (VB6) COM DLL (let's call it "dllouter") which referenced another Visual Basic (VB6) COM DLL (let's call it "dllinner") with an interface "Interface". "dllouter" loaded "dllinner" in the following way:

Public objCom As dllinner.Interface

Set objCom = New dllinner.Interface

When "dllinner" version changed, without changes in "Interface", "dllouter" was able to load it without problems, without needing to recompile it.

After that, I replaced "dllinner" with a C# .NET assembly (VS2015) with [assembly: ComVisible(true)], and recompiling "dllouter" everything was fine and working.

But if I change [assembly: AssemblyVersion("1.0.0")] to a newer version then Set objCom = New dllinner.Interface fails. I need to recompile "dllouter" after updating the reference to the new "dllinner" to make it work.

I have noticed that comparing the .vbp files with references to Visual Basic "dllinner" and .NET "dllinner" there is a difference in the version listed after the GUID:

Reference=*\G{6B0651C5-5225-42A6-841F0322797E5018}#1.0#0#...

The value in bold is updated for the .NET assembly with the new assembly version (e.g. 2.0) while it remains unchanged for the Visual Basic DLL reference (always 1.0, no matter what the "dllinner" version is).

Thus I tried to add the property [assembly: TypeLibVersion(1,0)] to assemblyinfo.cs and doing this "fixes" the reference in the .vbp meaning that the bold value is kept to 1.0 no matter what the AssemblyVersion is. However, the problem is not solved: "dllouter" still fails to load "dllinner".

Is there a way to fix this problem, avoiding to recompile "dllouter" any time "dllinner" version changes?

Upvotes: 3

Views: 192

Answers (1)

Ben
Ben

Reputation: 35613

If you wish a COM visible assembly to be compatible with a previous release, you must:

1) Make sure that there are no changes visible in the interface. If there are changes to deployed interfaces, then your new object is not compatible, and you will have to generate new CLSIDs, IIDs and a new type library.

2) Make sure that every visible class is annotated with an IID which is the same as the previous version. If you forgot to do this on the previous version, the compiler will generate one for you, so you need to find out what it was so the new version can be the same. You can use TlbView or the registry to find this out.

3) make sure every creatable class is annotated with a CLSID which is the same as the previous version.

It's also a good idea to check the type library is the same. You can decompile the previous version of the type library using TlbView or a similar tool, then do the same with the new version. You should not see any importand differences.

Note: If you want to add additional functions, you can do this but you need to create a new IID for the new interface, which should inherit from the old interface (which should be tagged with the old IID).

Upvotes: 1

Related Questions