C++ DCOM中的[out]参数SAFEARRAY(BSTR)无法返回字符串
我想编写一个DCOM服务器和一个客户机,以便它们可以交换一些数据。双方都使用MS Visual Studio 2008进行编译,客户端使用纯WinAPI进行连接,代理/存根是一个单独的dll(以防出现任何此类问题)。问题是,我无法返回字符串数组(它已正确填充,但客户端接收到空字符串数组) 服务器:COM接口的IDL声明有以下方法:C++ DCOM中的[out]参数SAFEARRAY(BSTR)无法返回字符串,c++,dcom,bstr,safearray,C++,Dcom,Bstr,Safearray,我想编写一个DCOM服务器和一个客户机,以便它们可以交换一些数据。双方都使用MS Visual Studio 2008进行编译,客户端使用纯WinAPI进行连接,代理/存根是一个单独的dll(以防出现任何此类问题)。问题是,我无法返回字符串数组(它已正确填充,但客户端接收到空字符串数组) 服务器:COM接口的IDL声明有以下方法: [id(7)] HRESULT foo([in] int arg1, [out] SAFEARRAY(int)* arg2, [out] SAFEARRAY(BSTR
[id(7)] HRESULT foo([in] int arg1, [out] SAFEARRAY(int)* arg2, [out] SAFEARRAY(BSTR)* arg3);
实现,标头由Studio生成:
HRESULT STDMETHODCALLTYPE CoClass::foo(int arg1, SAFEARRAY** arg2, SAFEARRAY** arg3){
SAFEARRAYBOUND bounds;
bounds.cElements = arg1;
bounds.lBound = 0;
*arg2 = SafeArrayCreate(VT_INT, 1, &bounds);
*arg3 = SafeArrayCreate(VT_BSTR, 1, &bounds);
for(LONG i=0; i<arg1; ++i){
int int_value = 42;
BSTR string_value = SysAllocString(L"Hello");
//string_value is correct here
SafeArrayPutElement(*arg2, &i, &int_value);
SafeArrayPutElement(*arg3, &i, &string_value);
//string_value isn't destroyed here (explicitly, at least)
}
return ERROR_SUCCESS;
}
呼叫方代码(pInterface
已正确初始化,其他呼叫成功):
其他详细信息:
- IDL文件中没有其他ID为7的方法李>
- 使用
可以正确返回字符串李>[out]BSTR*str
从pInterface
调用接收李>CoCreateInstanceEx
- 系统上没有旧版本的服务器李>
- 该代码将在Windows XP上运行,无需进行一些更新,因此使用Visual Studio 2008是一个很难绕过的限制
有人知道我做错了什么吗?答案由评论部分的提供 答案是:
SAFEARRAY
中添加元素的语法对于int
和BSTR
是不同的:
// SAFEARRAY **intArray, **stringArray; LONG i;
int int_value = 42;
BSTR string_value = SysAllocString(L"Hello");
SafeArrayPutElement(*intArray, &i, &int_value);
//SafeArrayPutElement(*stringArray, &i, &string_value); //WRONG!
SafeArrayPutElement(*stringArray, &i, string_value); //Right
请注意,读取的语法相同:
// SAFEARRAY *intArray, *stringArray; LONG i;
int int_value;
BSTR string_value;
SafeArrayGetElement(intArray, &i, &int_value);
SafeArrayGetElement(stringArray, &i, &string_value);
BSTR已经是一个指针,请传递字符串\u值而不是&string\u值。@HansPassant…这很有效。非常感谢。你想写答案还是我自己写?我很确定你现在知道如何写正确的答案,去做吧。
// SAFEARRAY **intArray, **stringArray; LONG i;
int int_value = 42;
BSTR string_value = SysAllocString(L"Hello");
SafeArrayPutElement(*intArray, &i, &int_value);
//SafeArrayPutElement(*stringArray, &i, &string_value); //WRONG!
SafeArrayPutElement(*stringArray, &i, string_value); //Right
// SAFEARRAY *intArray, *stringArray; LONG i;
int int_value;
BSTR string_value;
SafeArrayGetElement(intArray, &i, &int_value);
SafeArrayGetElement(stringArray, &i, &string_value);