简体   繁体   中英

PInvoke marshaling a struct pointer from ANSI C as an IntPtr in C#

So I'm trying to PInvoke an unmanaged DLL in C# from the iniParser library. I'm currently stumbling over the correct way to marshal the struct pointers returned and taken by functions in the unmanaged library.

In C:

__declspec(dllexport) dictionary * iniparser_load(const char * ininame);

In C#:

[DllImport("iniParser.dll")]
private static extern IntPtr iniparser_load(string filename);

The dictionary structure in C:

typedef struct _dictionary_ {
    int             n ;     /** Number of entries in dictionary */
    int             size ;  /** Storage size */
    char        **  val ;   /** List of string values */
    char        **  key ;   /** List of string keys */
    unsigned     *  hash ;  /** List of hash values for keys */
} dictionary ;

I understand that to actually access the structure in C# I need to create a counterpart for the C structure, but I don't need to access the struct in C#.

When the function is called in C#, I get the following error:

A call to PInvoke function 'CacheExplorer!CacheExplorer.iniParser::iniparser_load'
has unbalanced the stack. This is likely because the managed PInvoke signature 
does not match the unmanaged target signature. Check that the calling convention 
and parameters of the PInvoke signature match the target unmanaged signature.

But how does the managed signature not match the unmanaged signature? Does PInvoke require that I make a C# counterpart for the C structure? All I need is essentially a handle to the dictionary in C#, accessing members is totally unnecessary and I'd rather not convert the structure to C#

iniParser库的调用约定可能是cdecl,这意味着您需要更新[DllImport]属性用法:

[DllImport("iniParser.dll", CallingConvention = CallingConvention.Cdecl)]

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM