Marshalling arrays from C# to C++ and back: PInvokeStackImbalance
I have a C++ function that I'd like to access from C#. The problem is I keep getting PInvokeStackImbalance exceptions and I don't know why. Everything runs fine and as expected when checking for that exception is turned off.
The signature of my C++ function is:
extern "C" double solveQP(
int32_t n, int32_t mE, int32_t mI,
double *p_G, double *p_g0,
double *p_CE, double *p_ce0,
double *p_CI, double *p_ci0,
double *p_x)
and what I've been using to access it is:
[DllImport("libQuadProg.dll")]
[return: MarshalAs(UnmanagedType.R8)]
private static extern double solveQP(
[In, MarshalAs(UnmanagedType.I4)] int n,
[In, MarshalAs(UnmanagedType.I4)] int mE,
[In, MarshalAs(UnmanagedType.I4)] int mI,
[In, MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.R8)] double[] p_G,
[In, MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.R8)] double[] p_g0,
[In, MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.R8)] double[] p_CE,
[In, MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.R8)] double[] p_ce0,
[In, MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.R8)] double[] p_CI,
[In, MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.R8)] double[] p_ci0,
[In, MarshalAs(UnmanagedType.LPArray, ArraySubType = UnmanagedType.R8)] double[] p_x);
I've also tried it with just the UnmanagedType.LPArray option and nothing at all. I figure there is one detail abou开发者_StackOverflow社区t PInvoke that I just do not get and I'd appreciate it if someone pointed it out.
You need to use the DllImport's CallingConvention property. Cdecl is required here since you didn't declare the C function as __stdcall. You don't need [MarshalAs], the values you use are already the default. Thus:
[DllImport("libQuadProg.dll", CallingConvention = CallingConvention.Cdecl)]
private static extern double solveQP(
int n, int mE, int mI,
double[] p_G,
// etc...
}
精彩评论