我在C#中调用非托管dll中的函数。我对此dll的一个调用是有效的。但是另一个具有更高级的参数,当我在C#代码中执行Funkction时:
[DllImport("IOLUSBIF20.dll", CallingConvention = CallingConvention.StdCall)]
public static extern long IOL_SetTransparentModeExt(long Handle, UInt32 Port, ref TTransparentParameters pTransparentParameters);
我收到以下错误:
“PInvokeStackImbalance”:“调用PInvoke函数'IO-Link设备接口!IO_Link_Device_Interface.IOLUSBIF20Wrapper :: IOL_SetTransparentModeExt'使堆栈失衡。这可能是因为托管PInvoke签名与非托管目标签名不匹配。请检查调用约定PInvoke签名的参数与目标非托管签名匹配。“
在Header中,函数(和结构)的签名定义如下:
LONG __stdcall IOL_SetTransparentModeExt(LONG Handle, DWORD Port, TTransparentParameters * pTransparentParameters);
typedef struct TTransparentParametersStruct
{
BYTE StartPattern[16]; /**< starting pattern */
BYTE ReturnPattern[32]; /**< returning pattern */
} TTransparentParameters;
我作为参数传递的结构如下所示:
[StructLayout(LayoutKind.Sequential)]
public struct TTransparentParameters
{
public Byte[] StartPattern; /**< starting pattern */
public Byte[] ReturnPattern; /**< returning pattern */
}
您的堆栈不平衡,因为非托管数据结构由
BYTE StartPattern[16]; /**< starting pattern */
BYTE ReturnPattern[32]; /**< returning pattern */
占用48个字节,而您对这些字段的管理解释大小错误。如果指定封送器的大小,则应平衡堆栈:
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 16)]
public Byte[] StartPattern; /**< starting pattern */
[MarshalAs(UnmanagedType.ByValArray, SizeConst = 32)]
public Byte[] ReturnPattern; /**< returning pattern */