gpt4 book ai didi

c++ - 在 MSMQ 消息中发送具有 BSTR 值类型的 COM 对象

转载 作者:塔克拉玛干 更新时间:2023-11-03 07:37:37 27 4
gpt4 key购买 nike

我正在尝试通过 C++ 中的 MSMQ 消息发送 COM 对象。这是我的对象:

class ATL_NO_VTABLE CAnalisis :    public CComObjectRootEx,    public CComCoClass,    public ISupportErrorInfo,    public IDispatchImpl,    public IPersistStreamInit{private:    typedef struct {        DOUBLE size;        float color;        float light;        BSTR imgName;        BSTR  uname;    } Image;    Image img;    STDMETHOD(Load)(IStream *pStm);    STDMETHOD(Save)(IStream *pStm,  BOOL fClearDirty);

一切顺利,我可以获得整个对象,但 BSTR 类型除外。正确发送和接收 float 和整数。但是 BSTR 类型不起作用。我正在尝试发送字符串,但找不到方法。我确实尝试使用 VARIANT,但结果也是错误的。不知何故,看起来字符串没有序列化。

这些是我的 ATL 组件的一些获取和设置函数:

这个很好用:

STDMETHODIMP CAnalisis::getLight(FLOAT* light){    *light=img.light;    return S_OK;}STDMETHODIMP CAnalisis::setLight(FLOAT light){    img.light=light;    return S_OK;}

这个没有:

STDMETHODIMP CAnalisis::getImgName(BSTR* imgName){    *imgName = img.imgName;    return S_OK;}STDMETHODIMP CAnalisis::setImgName(BSTR imgName){    img.imgName=imgName;    return S_OK;}

这就是我创建 MSMQ 消息并在我的生产者中填充值的方式:

// For these ActiveX components we need only smart interface pointer        IMSMQQueueInfosPtr  pQueueInfos;         IMSMQQueueInfoPtr   pQueueInfo;         IMSMQQueuePtr       pQueue;        IUnknownPtr         pIUnknown;        // Instanciate the follwing ActiveX components        IMSMQQueryPtr       pQuery(__uuidof(MSMQQuery));        IMSMQMessagePtr     pMessage(__uuidof(MSMQMessage));        IAnalisisPtr pAnalisis(__uuidof(Analisis));                WCHAR *  imagen;                imagen = L"imagen1.jpg";                pAnalisis->setImgName(imagen);                 (...)                pAnalisis->setFruitSize(20.00);                 (...)                pQueueInfo = new IMSMQQueueInfoPtr( __uuidof(MSMQQueueInfo) );        pQueueInfo->PathName = "MYCOMPUTER\\private$\\myprivatequeue";            pQueue = pQueueInfo->Open(MQ_SEND_ACCESS, MQ_DENY_NONE);        pMessage->Body = static_cast(pAnalisis);                pMessage->Send(pQueue);

这是序列化代码

STDMETHODIMP CAnalisis::Load( IStream *pStm ){    ULONG           cb;    HRESULT         hr;    if (NULL==pStm)        return ResultFromScode(E_POINTER);    // Read an object from the stream.    //    hr=pStm->Read(&img, sizeof(Image), &cb);    if (FAILED(hr))        return hr;    if (sizeof(Image) != cb)        return E_FAIL;    return NOERROR;}STDMETHODIMP CAnalisis::Save( IStream *pStm, BOOL bClearDirty ){    ULONG           cb;    HRESULT         hr;    if (NULL==pStm)        return ResultFromScode(E_POINTER);    // Write an object into the stream.    hr=pStm->Write(&img, (ULONG)sizeof(Image), &cb);    if (FAILED(hr) || sizeof(Image)!=cb)       return ResultFromScode(STG_E_WRITEFAULT);    return NOERROR;}

如果我在生产者中获得 BSTR 值(在序列化之前),pAnalisis-getImgName(),它工作正常。相反,当我尝试在消费者中获取它时,从队列中读取消息后,它不会返回任何内容。其他值(例如大小)可以毫无问题地返回。

有谁知道如何通过 MSMQ 在 COM 对象中发送 BSTR 值?

我试图找到一些类似的例子,但完全是徒劳的。

问题是我得到的要么是一个非常奇怪的带有奇怪字符的值,要么是一个十六进制值,这取决于我如何提取该值..问题是我从来没有得到正确的值。

但是我想知道...我们确定可以发送 BSTR 值吗?如果我没记错的话,它是一个指向字符串的指针......我正在运行两个不同的进程(即生产者和消费者),所以它们使用不同的内存块,并且它们应该在不同的机器上运行。 ..

我试图将此信息作为 VARIANT 类型发送.. 但也迷路了。然而,这似乎没有发送 BSTR 那么牵强。

对此有什么想法吗?

最佳答案

问题在于 Image 类的序列化将其视为连续的内存块。由于 BSTR 实际上是一个指针,因此只有指针值被序列化并且 BSTR 有效负载丢失。

相反,您应该将除 BSTR 之外的所有字段写为二进制文件并分别处理 BSTR。例如,您可以先将 BSTR 长度写为整数,然后再写它的有效负载。读取时先读取长度,调用SysAllocStringLen()分配缓冲区,再读取payload。

保持简单字段的序列化(IPersistStreamInit::Save()):

pStm->Write(&(img.color), (ULONG)sizeof(float), &cb);

对于 BSTR,执行此操作:

int length = SysStringLen( img.uname );
pStm->Write(&length, (ULONG)sizeof(int), &cb);
if( length > 0 ) {
pStm->Write( img.uname, (ULONG)(length * sizeof(WCHAR) ), &cb);
}

类似于读取(IPersistStreamInit::Load()):

int length;
pStm->Read(&length, (ULONG)sizeof(int), &cb);
if( length > 0 ) {
img.uname = SysAllocStringLen( 0, length );
pStm->Read( img.uname, (ULONG)( length * sizeof( WCHAR) ), &cb);
} else {
img.uname = 0;
}

请注意,此代码写入/读取字符串长度,然后写入/读取由 Unicode 字符组成的有效负载。每个 Unicode 字符占用超过一个字节 - 因此 IStream 读/写方法调用中的乘法。

关于c++ - 在 MSMQ 消息中发送具有 BSTR 值类型的 COM 对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/627254/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com