在 C# 中调用 DLL 函数时传递结构C++
passing structure when calling C++ DLL function in C#
我需要使用 C# 来控制具有C++ DLL 的测试模块,下面是最初在头文件中定义的结构和 init 函数C++
typedef unsigned char uint8_t;
typedef unsigned long uint32_t;
typedef unsigned short uint16_t;
typedef unsigned char bool_t;
typedef signed short int16_t;
typedef signed char int8_t;
typedef signed long int32_t;
#define ER 0x2
#define BS 0x4000
typedef enum {
nI2C,
nSPI,
nUSB,
nSDIO
} mBus;
typedef uint8_t cAddr;
typedef enum {
nCPHA0=0,
nCPHA1
} mPhase;
typedef enum {
nCPOL0=0,
nCPOL1
} mSpiPol;
typedef struct {
mPhase cPha;
mSpiPol cPol;
} mSpiCfg;
typedef struct {
uint8_t xo;
bool_t init_bus_only;
uint32_t zone;
mBus bustype;
mBus transporttype;
cAddr i2cAddr;
mSpiCfg spiCfg;
bool_t use_pmu;
} mInitCfg;
typedef enum {
OK = 0,
FAIL = -1,
BUS_ALREADY_LOADED = -2,
BUS_TYPE_UNKNOWN = -3,
BUS_LOAD_LIBRARY_FAIL = -4,
BUS_GET_PROC_FAIL = -5,
BUS_INIT_FAIL = -6,
Err_CHIP_INIT = -7
} retCode;
typedef struct {
mInitCfg cfg;
} mDrvIn;
__declspec(dllexport) retCode cp_init(mDrvIn * inp);
在C++中,它被称为如下
static void init(void)
{
mDrvIn di;
retCode rc;
memset(&di, 0, sizeof(mDrvIn));
di.cfg.bustype = nI2C;
di.cfg.init_bus_only = 1;
di.cfg.transporttype = di.cfg.bustype;
di.cfg.zone = ER | BS;
rc = cp_init(&di);
if(rc < 0) {
printf("Failed to initialize. Error code %d: %s", rc, to_string(rc));
return;
}
}
我在调用 DLL 函数时使用以下 C# 结构
using cAddr = System.Byte;
public enum mBus
{
nI2C,
nSPI,
nUSB,
nSDIO
};
public enum mPhase
{
nCPHA0 = 0,
nCPHA1
};
public enum mSpiPol
{
nCPOL0 = 0,
nCPOL1
};
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
public struct mSpiCfg
{
public mPhase cPha;
public mSpiPol cPol;
};
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
public struct mInitCfg
{
public byte xo;
public byte init_bus_only;
public uint zone;
public mBus bustype;
public mBus transporttype;
public cAddr i2cAddr;
public mSpiCfg spiCfg;
public byte use_pmu;
};
public enum retCode
{
OK = 0,
FAIL = -1,
BUS_ALREADY_LOADED = -2,
BUS_TYPE_UNKNOWN = -3,
BUS_LOAD_LIBRARY_FAIL = -4,
BUS_GET_PROC_FAIL = -5,
BUS_INIT_FAIL = -6,
Err_CHIP_INIT = -7
};
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
public struct mDrvIn
{
public mInitCfg cfg;
};
[DllImport("mdrv.dll", CallingConvention = CallingConvention.Cdecl, CharSet = CharSet.Unicode)]
public static extern retCode cp_init(ref mDrvIn inp);
我使用以下代码来初始化
public static void init()
{
mDrvIn di = new mDrvIn();
retCode rc = new retCode();
di.cfg.bustype = mBus.nI2C;
di.cfg.init_bus_only = 1;
di.cfg.transporttype = di.cfg.bustype;
di.cfg.zone = 0x2 | 0x4000;
rc = cp_init(ref di);
if (rc < 0)
{
Console.Write("Failed to initialize. Error code: " + rc);
return;
}
}
问题是使用 C++ 初始化模块可以正常工作,但 C# 不能,它总是会返回错误代码 -5(这意味着总线错误:无法枚举 DLL 内的总线函数),结构的指针似乎被成功传递给 DLL 没有错误,因此我想知道我在 C# 中转换的结构是否有问题, 因此,传递给C++函数的参数已损坏或其他原因,任何人都可以帮助我吗?提前谢谢。
在C++代码中,将bool_t
定义为unsigned char
(8 位),但在 C# 代码中,使用int
(32 位),因此结构在init_bus_only
后停止有效。
编辑:此外,在C++代码中,将init_bus_only
设置为 1,而在 C# 代码中没有,但您应该在没有帮助的情况下找到它。在询问之前仔细检查您的代码。
相关文章:
- 如何循环打印顶点结构
- 通过方法访问结构
- 使用不带参数的函数访问结构元素
- 预处理器:插入结构名称中的前一个行号
- 为什么在没有显式默认构造函数的情况下,将另一个结构封装在联合中作为成员的结构不能编译
- 孤立代码块在结构中引发异常
- 有什么方法可以遍历结构吗
- 如何在 C# 中映射双 C 结构指针?
- 如何在C++中使用结构生成映射
- 无法将结构注册为增强几何体3D点
- 多成员Constexpr结构初始化
- C++将文本文件中的数据读取到结构数组中
- 如何重构类层次结构以避免菱形问题
- 如何在C++中序列化结构数据
- std::vector的包装器,使数组的结构看起来像结构的数组
- 没有为自己的结构调用列表推回方法
- 奇怪的结构&GCC&clang(void*返回类型)
- 在 c++ 中拥有一组结构的正确方法是什么?
- vscode g++链路故障:体系结构x86_64的未定义符号
- C++概念:如何使用'concept'检查模板化结构的属性?