不知道为什么会这样,但是当我执行我的一个 C# 函数时,该函数可以由以下 C# 接口定义:
[ComImport, Guid("EA5435EA-AA5C-455d-BF97-5F19DC9C29AD"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IClosedCaptionsDecoder2
{
[PreserveSig]
int SetConfig([In] ref ClosedCaptionsDecoderConfig config);
[PreserveSig]
int GetConfig([Out] out ClosedCaptionsDecoderConfig config);
}
和 C++ 接口:
interface __declspec(uuid("{EA5435EA-AA5C-455d-BF97-5F19DC9C29AD}"))
IClosedCaptionsDecoder2 : public IClosedCaptionsDecoder
{
STDMETHOD(SetConfig)(IN CLOSEDCAPTIONSDECODERCONFIG& config) PURE;
STDMETHOD(GetConfig)(OUT CLOSEDCAPTIONSDECODERCONFIG* pConfig) PURE;
};
IM 重定向到由"先前"接口声明的另一个函数。例如,当我尝试执行以下命令时:config->SetConfig(....).函数im重定向到(或下一个要执行的命令)由IClosedCaptionsDecoder2的基类实现,称为IClosedCaptionsDecoder。
此接口的 C++ 降级为:
interface __declspec(uuid("{26B8D7F1-7DD8-4a59-9663-8D00C03135F7}"))
IClosedCaptionsDecoder : public IUnknown
{
STDMETHOD(xxx)(IExternalCCObserver* pObserver, LONG lFlags) PURE;
};
所以config->SetConfig()实际上调用了config->xxx(),我的猜测是函数的缺点有问题。
我什至尝试在 C# 端定义整个关系(继承等),但这也没有奏效。
我将不胜感激任何帮助。谢谢!
编辑:当我尝试调用GetConfig()时,它实际上执行了SetConfig()。 所以我肯定有指针偏移量等问题。 每个函数,按降级顺序调用前一个函数,怎么可能??
编辑2:我设法通过将所有功能添加到IClosedCaptionsDecoder2接口来解决这种情况。
这是 CLR 中实现 COM 互操作的方式中存在缺陷的副作用。 当接口派生自 IUnknown 或 IDispatch 以外的其他接口时,它不会将接口的方法正确映射到对向表槽。 它将第一个方法映射到第一个可用插槽,即使它已经被具体 coclass 实现中继承接口的方法占用。 不支持多重继承的副作用。 所以出错的是,当客户端代码调用IClosedCaptionsDecoder::xxx()时,它最终会调用IClosedCaptionsDecoder2::SetConfig()。
解决方法很简单,尽管令人不快,但您必须扁平化界面,使其包含继承的方法。 在您的情况下,这将是:
[ComImport, Guid("EA5435EA-AA5C-455d-BF97-5F19DC9C29AD"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IClosedCaptionsDecoder2
{
// Methods inherited from IClosedCaptionsDecoder:
[PreserveSig]
int xxx(whatever...);
// Methods specific to IClosedCaptionsDecoder2
[PreserveSig]
int SetConfig([In] ref ClosedCaptionsDecoderConfig config);
[PreserveSig]
int GetConfig([Out] out ClosedCaptionsDecoderConfig config);
}
这在美国于 9 月 30 日成为法律,仅剩 6 周即可获得此工作;)