关于C#中调用C++编写的DLL(非托管的DLL)的实现和问题记录

关于C#调用DLL的实现网上可以很容易查到。方法是比较固定的,没有什么可变性。照着做就可以。

下面主要是记录一下在调用实现过程中可能出现的一些问题。为了直观一点,我也把自己的实现部分加了进来。


这里我的实现也是大同小异的。可以根据实际情况选择适合的方式。

调用的实现:

1。。接口的声明

class SPITestInterFace
    {
//接口的声明
        [DllImport("SPITEST.dll", CharSet = CharSet.Auto, CallingConvention = CallingConvention.Cdecl)]
        public static extern int CUI_SetData(uint ulObjectID, uint UlTypeID, uint UlItemID,
            ushort usValueLen, string pValueBuf);



        public static int SPI_FaultImplementSendData()
        {
            try
            {
//接口的调用
                string dataBuf = "0";

                int _result = CUI_SetData(0, 0, 0, 0, dataBuf);


                return _result;
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }
    }


在实现中遇到的问题和报错主要有一下几点:

1.注意类型的匹配问题

函数的源程序中的声明是:

extern "C" __declspec(dllexport) int CUI_SetData(
    unsigned long ulObjectID, unsigned long ulTypeID, unsigned long ulItemID,
    unsigned short usValueLen, unsigned char* pValueBuf)

如果类型匹配有问题的话可能出现以下报错:

1.1. System.AccessViolationException: 尝试读取或写入受保护的内存;

1.2. 输入的值都是null或者0,导致结果有误

2.注意调用模式的设置:CallingConvention = CallingConvention.Cdecl

这个问题报错是比较明显的:对 PInvoke 函数“。。”的调用导致堆栈不对称。原因可能是托管的 PInvoke 签名与非托管的目标签名不匹配

3.注意Dll所需要的其他Dll都存在在所需的文件夹中

这个问题可能的报错是:找不到指定模块,ErrorCode:0x8007007E


以上只是自己的一些经历的记录,及供参考。



猜你喜欢

转载自blog.csdn.net/wasaiheihei/article/details/46412847
今日推荐