0

我正在尝试调用一个为字符串分配内存然后对字符串执行某些操作的函数。这是说明问题的基本示例:

C++:

    STDMETHODIMP CFunctionsCollection::Function2 (  
        BSTR leftString, BSTR rightString, BSTR * conString
    )
{
    int leftLen = lstrlen(leftString);
    int rightLen = lstrlen(rightString);

    *conString = new TCHAR[leftLen+rightLen+1];

    for (int i=0 ; i<leftLen ; ++i)
        (*conString)[i] = leftString[i];
    for (int i=0 ; i<rightLen ; ++i)
        (*conString)[leftLen+i] = rightString[i];
    (*conString)[leftLen+rightLen] = 0;

    return S_OK;
}

来自 C++ 程序的以下调用可以正常工作:

BSTR leftString = SysAllocString(L"Left String");
BSTR rightString = SysAllocString(L"Right String");
BSTR conString;
hr = pFunctionsCollection->Function2 ( leftString, rightString, & conString);

C# 声明:

Int32 Function2([In, MarshalAs(UnmanagedType.BStr)] String leftString,
                [In, MarshalAs(UnmanagedType.BStr)] String rightString,
                [In, Out] ref IntPtr conStr);

C# 调用:

try
{
    String leftString = "Left String"; 
    String rightString = "Right String";
    IntPtr outStr = IntPtr.Zero;
    pFunctionsCollection.Function2(leftString, rightString, ref outStr);
    String outString = Marshal.PtrToStringUni(outStr);
    Console.WriteLine("Out String = {0}", outString);
}
catch (Exception e)
{
    Console.WriteLine("Call to Function2 failed with {0}", e.Message);
}

该程序失败

调用 Function2 失败,内存不足,无法继续执行程序。

有谁知道如何从 C# 进行这样的调用?

4

1 回答 1

1

conString 是一个 BSTR,因此必须这样对待。请参阅http://msdn.microsoft.com/en-us/library/ms221069.aspx

  1. 您应该使用 SysStringLen 来获取 BSTR 的长度
  2. C# 中的最后一个参数应该是编组为 BSTR 的输出字符串

    [In, Out, MarshalAs(UnmanagedType.BStr)] 输出字符串 conStr

  3. 您需要使用 SysAllocString 或 SysAllocStringLen 为 conStr 分配内存

  4. 项目清单

您不能使用“new”分配内存并将其转换为 BSTR。BSTR 对内存管理和布局有您不满意的特定要求。您必须始终遵循这些约定。互操作失败,因为它希望您遵循 BSTR 的约定,但您没有。

于 2011-04-01T00:46:24.717 回答