繁体   English   中英

将C#结构数组传递给C ++

[英]Pass c# structure array to c++

我在c ++ dll上工作,有任何问题! 我的头文件是这样的

struct ST_DevInfo
{
    EN_DevType de_type;        
    int screen_width;          
    int screen_height;         
    char dev_name[256];        
    char id[14];               
    char sboox_version[16];    
    char fpga_version[16];     
};

extern "C" __declspec(dllexport) int CB_GetDeviceList(ST_DevInfo* buff,int length);

和C ++代码

int CB_GetDeviceList(ST_DevInfo* buff,int length)
{
    buff = (ST_DevInfo *)malloc(sizeof(ST_DevInfo) * length);

    return GetDeviceList(buff, length);
}

现在我像这样在C#中使用此功能

[StructLayout(LayoutKind.Sequential)]
        struct ST_DevInfo
        {
            [MarshalAs(UnmanagedType.I4)]
            public EN_DevType de_type;
            [MarshalAs(UnmanagedType.I4)]
            public int screen_width;
            [MarshalAs(UnmanagedType.I4)]
            public int screen_height;
            [MarshalAs(UnmanagedType.ByValArray, ArraySubType = UnmanagedType.I1, SizeConst = 256)]
            public char[] dev_name;
            [MarshalAs(UnmanagedType.ByValArray, ArraySubType = UnmanagedType.I1, SizeConst = 14)]
            public char[]  id;
            [MarshalAs(UnmanagedType.ByValArray, ArraySubType = UnmanagedType.I1, SizeConst = 16)]
            public char[]  sboox_version;
            [MarshalAs(UnmanagedType.ByValArray, ArraySubType = UnmanagedType.I1, SizeConst = 16)]
            public char[]  fpga_version;
        };

[DllImport(dllName, EntryPoint = "CB_GetDeviceList", SetLastError = true, ExactSpelling = true,
            CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Auto)]
        public static extern
            int CB_GetDeviceList([MarshalAs(UnmanagedType.LPArray)] ref ST_DevInfo[] buff, 
                                    int length);

最后我像这样在程序中使用这个功能

ST_DevInfo[] buff = new ST_DevInfo[dev_length];
int ret = BBIA.CB_GetDeviceList( ref buff, dev_length);

但是从CB_GetDeviceList检索后,我的buff变量已分配但没有任何值(包含0x00)。 我在C ++中对其进行测试,效果很好! 我认为这条线有问题

增益=(ST_DevInfo *)malloc(sizeof(ST_DevInfo)*长度);

在您的C#代码中,您正在执行以下操作:

ST_DevInfo[] buff = new ST_DevInfo[dev_length];
int ret = BBIA.CB_GetDeviceList( ref buff, dev_length);

这是分配一个数组,并将其传递给C ++代码(由于有ref ,所以要使用双指针)。

在您的C ++代码中,您正在执行以下操作:

int CB_GetDeviceList(ST_DevInfo* buff,int length)
{
    buff = (ST_DevInfo *)malloc(sizeof(ST_DevInfo) * length);
    return GetDeviceList(buff, length);
}

这需要一个数组(而不是一个双指针)并更改该(本地)指针以指向一些新的内存。 因此,C ++的原始代码永远不会触及C#的原始数组。

首先,完全删除malloc调用。 然后将您的密码更改为:

[DllImport( ... )]
public static extern int CB_GetDeviceList( [In, Out] ST_DevInfo[] buff, int length );

并像以前一样致电,但没有ref In, Out需要告诉您所期望的PInvoke的调用来修改数据编组。 它们并非在每种情况下都是必需的,但是对于您的情况,我不是100%肯定的,因此我会以防万一。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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