1

我有一个 ATL COM 服务器,接口的方法是

STDMETHODIMP CWrapper::RUN(long iDataSize, SAFEARRAY** iData)

这个函数的 MIDL 看起来像

[id(1), helpstring("method RUN")] HRESULT RUN([in] long nSize, [in, size_is(nSize)] SAFEARRAY(_MyDataType*)* iData);

我使用 tlbimp 从这个项目中导入 tlb,所以我可以使用本机数组。然后我从 C# 调用它如下

 m_ServerWrapper.RUN(iInputs.Length,ref iInputs)

其中 Inputs 已经分配并填充了我的 C# 程序内部的另一个 COM 对象。现在,当我调用 C++ 包装器时,我有一个BadPtr用于我的 safearray 并且从后续 COM 对象调用CWrapper::RUN失败,该数组没有进入最终的 dll。它显示为未分配。有谁知道我做错了什么?谢谢

编辑:我应该说该数组在 C# 中看起来很好。

EDIT2:调试器iData显示IDispatch* = 0x0000000 <Bad Ptr>, 5, 0x0000000 <Bad Ptr>({lpvtbl = 0xblahblah},.... 所以看起来我的一些信息正在到达那里。

4

1 回答 1

0

普通的 C# 数组与 SAFEARRAY 不同。我认为您必须自己制作:

[StructLayout(LayoutKind.Sequential)]
struct SafeArray
{
    public ushort   dimensions;  
    public ushort   features;    
    public uint     elementSize; 
    public uint     locks;       
    public IntPtr   dataPtr;     
    public uint     elementCount;
    public int      lowerBound;  
}

然后使用 Marshal.AllocCoTaskMem() 创建内存。填写所有数据,然后传递。

于 2009-03-27T22:08:54.190 回答