سؤال

This problem has been causing me a headache for a few days, and I cannot find a reason for it. I'm pretty sure this is an environmental issue particular to my machine, but still its causing me problems with testing.

I'm creating a DLL in C# using Visual Studio 2010 Professional. Version one is below;

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;

namespace TestCOM
{
    [ClassInterface(ClassInterfaceType.AutoDual)]
    [System.Runtime.InteropServices.ComVisible(true)]
    [System.Runtime.InteropServices.ProgId("TestCOM.Class1")]
    [System.Runtime.InteropServices.Guid("803A1B2F-1CDA-4571-9084-87500388693B")]
    public class Class1
    {
        public void showMessage()
        {
            MessageBox.Show("Hello from TextCom");
        }

    }
}

This assembly compiles fine, and everything is good. I run the following script to register it as a COM object (first for 32-bit, then for 64-bit);

C:\Windows\Microsoft.NET\Framework\v4.0.30319\regasm.exe TestCOM.dll /codebase /nologo /tlb:TestCOM32.tlb
C:\Windows\Microsoft.NET\Framework64\v4.0.30319\regasm.exe TestCOM.dll /codebase /nologo /tlb:TestCOM64.tlb

And then use the following script to test it;

dim tc 
set tc = CreateObject("TestCOM.Class1")
tc.showMessage()

I use csript to test the script, so I can control which bit depth it uses - I test it once with 32-bit and once with 64-bit. So far everything is good.

Now, when I modify the original assembly to add a function, as follows

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;

namespace TestCOM
{
    [ClassInterface(ClassInterfaceType.AutoDual)]
    [System.Runtime.InteropServices.ComVisible(true)]
    [System.Runtime.InteropServices.ProgId("TestCOM.Class1")]
    [System.Runtime.InteropServices.Guid("803A1B2F-1CDA-4571-9084-87500388693B")]
    public class Class1
    {
        public void showMessage()
        {
            MessageBox.Show("Hello from TextCom");
        }

        public void HelloWorld()
        {
            MessageBox.Show("Hello World!!");
        }

    }
}

Before the modification, I unregistered the library using "regasm /unregister" and it reported all types unregistered successfully.

When i register the library, now with changes, the original test script works perfectly. If I extend the test script to call the new HelloWorld function;

In 32-bit scripts, it works perfectly. In 64-bit scripts, it complains that no such function exists for the TestCOM.Class1 object

I've tried this every which way I can, but I cannot identify why the new function is available to the 32-bit callers, but not the 64-bit calls.

What am I doing wrong ? is there a cache somewhere for the 64-bit stuff I'm not aware of, or a registry setting that needs changed?

To be clear; 1. Build assembly 2. Register using regasm, once for 32 and once for 64 3. Test using script - everything works 4. Unregister library 5. Make modifications, rebuild 6. Register as per Step 2 7. Tests work in 32-bit, but not 64. Wtf ?

هل كانت مفيدة؟

المحلول

Clearly you are suffering from DLL Hell, always around with COM, it is loading an old version of your DLL. Your GAC could have gotten polluted by earlier experiments, it will always find the GACed version first. You are making it worse by specifying the [Guid], making your new class look the same as the old one, even though it is not identical. Preventing COM from telling you that it cannot find the new version of the class.

The most reliable, although noisy, way to see where the DLL came from is by using SysInterals' ProcMon utility. You'll see it reading the registry key and loading the DLL. You can see what directory it came from. Make sure it is not the GAC, remove it with gacutil /u if that's the case, and make sure that you got it rebuilt by checking the timestamp on the file.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top