关于C#:CoMarshalInterThreadInterfaceInStream为Visual Basic 6类返回0x800A0062

CoMarshalInterThreadInterfaceInStream returns 0x800A0062 for Visual Basic 6 classes

我有一个基于C / ATL的COM对象,该对象带有接受接口以允许回调的方法:

MIDL

1
2
3
4
5
6
7
8
9
10
[object, uuid(...), dual, nonextensible, oleautomation, pointer_default(unique)]
interface IAsyncEvents : IDispatch{
    [id(1)]
    HRESULT OnProgress([in]BSTR message);
};

[object, uuid(...), dual, nonextensible, pointer_default(unique)]
interface IAsyncWorker : IDispatch{
    HRESULT CallMe(BSTR message, IAsyncEvents* events);
};

COM对象实现IAsyncWorker接口。唯一的方法" CallMe"期望客户端应传递"事件"接口,以允许从工作线程进行回调。" CallMe"实现如下所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
STDMETHOD(CallMe)(BSTR message, IAsyncEvents* events)
    {                      
        IStream *pStm = NULL;
        HRESULT hRes = CoMarshalInterThreadInterfaceInStream(IID_IAsyncEvents, events, &pStm);
        if (hRes != S_OK)
        {
            ATL::CAtlString str;
            str.Format(_T("Failed CoMarshallInterThread... %i"), hRes);
            MessageBox(0, str, NULL, MB_TOPMOST);
            return E_FAIL;
        }

        m_hThread = ::CreateThread(NULL, 0, WorkerFunc, (LPVOID)pStm, 0, &m_dwThreadId);
        return ::GetLastError();
    }

然后我尝试从Visual Basic中像这样调用" CallMe":

MyCallBack类

1
2
3
4
5
6
Option Explicit
Implements AsyncDllLib.IAsyncEvents

Public Sub IAsyncEvents_OnProgress(ByVal message As String)
    MsgBox (message)
End Sub

VB6 com-object调用代码

1
2
3
4
5
6
Dim obj As Object
Set obj = CreateObject("C++ Com Object ProgID")

Dim callback As New MyCallbackClass

obj.CallMe"123", callback

一切正常,但突然MyCallback类实例无法编组到流中。同时,我可以在同一线程中使用C实现中的"事件"接口指针。

CoMarshalInterThreadInterfaceInStream失败,出现未记录的错误:0x800A0062

我在这里做错了什么?

先谢谢您!


您无法封送私有类,标准封送处理需要类型库来跨线程传输参数。

您可以在VB6中的ActiveX DLL项目上将MyCallbackClass作为公共(多用途或不可创建的公共类)实现,以便封送工作或更好地在ATL组件中实现回调代理。

您的CallMe将在传递原始VB6接口的调用线程上创建代理,然后将代理对象的IAsyncEvents接口封送给工作线程。