C# 使用PInvoke接口C/C+;调试断言失败+;动态链接库

C# 使用PInvoke接口C/C+;调试断言失败+;动态链接库,c#,c++,c,dll,pinvoke,C#,C++,C,Dll,Pinvoke,我有一个C/C++dll,并试图使用PInvoke与C应用程序接口。 我得到调试断言失败错误。DLL在与C++应用程序接口时工作,问题只在C语言应用程序接口。 我的DLL的.h和.cpp文件是 头文件 #include <string> #include <fstream> #include <iostream> #ifdef DLL_EXPORTS #define DLL_EXPORTS __declspec(dllexport) #else #defi

我有一个C/C++dll,并试图使用PInvoke与C应用程序接口。 我得到
调试断言失败
错误。DLL在与C++应用程序接口时工作,问题只在C语言应用程序接口。 我的DLL的.h和.cpp文件是

头文件

#include <string>
#include <fstream>
#include <iostream>

#ifdef DLL_EXPORTS
#define DLL_EXPORTS __declspec(dllexport) 
#else
#define DLL_EXPORTS __declspec(dllimport) 
#endif

#define   PASS              0
#define   FILECREATE_FAIL   1
#define   CAMERA_ERROR      2
#define   MAX_NUM_FRAMES    10000

using namespace std;

#ifdef __cplusplus
extern "C"
{
#endif

    // Returns pass  0
    //         Fails 1
    // Open the file at the path and start acquisition
    DLL_EXPORTS int start_acquisition(string path); 
    DLL_EXPORTS int stop_acquisition();

#ifdef __cplusplus
}
#endif
编辑1: 我展示了一个使用的示例。和我的有什么不同

class PlatformInvokeTest
{
   [DllImport("user32.dll")]
   public static extern int MessageBoxA(
      int h, string m, string c, int type);

   public static int Main() 
   {
      return MessageBoxA(0, "Hello World!", "My Message Box", 0);
   }
}

您没有显示p/invoke声明,但有100%的可能是您弄错了,因为没有正确的声明。这些函数不能直接从C#调用,因为它们的签名是C++特有的

调试断言TRIP,因为C++函数试图将其参数用作 STD::String ,实际上它不是一个。

std::string
析构函数在作用域的末尾运行,试图释放内存。。。并且由于
std::string
构造函数未分配内存而失败,因为此处不存在
std::string
对象

您可以添加一个包装器,该包装器接受一些p/invoke兼容的字符串类型,例如
const char*
BSTR
,创建一个
std::string
,然后调用实际函数


实际上,从其他C++编译器或版本调用它也会有困难。

头文件中的YPLCPLUS PLUS 测试完全没有用,因为这些函数使用C中不存在的类型。p/invoke的默认值是stdcall。我已在编辑1中进行了更新。我觉得我明白你想解释什么。但是根据我更新的例子,和我的区别是什么?不同之处在于,不是C++ <代码> STD::String 。C#中没有任何东西可以调用使用
std::string
参数的函数。现在有点奇怪。现在我没有任何关于DLL调用的参数,路径是“c:\\\\\\NY201201\Tab\\WaveNththyTest\\Test1.txt”,它是用C++ DLL代码分配的。所以C代码只调用dll,而不传递参数。对于DLL,如果从C语言应用程序调用,它会有“附加信息:试图读取或写入受保护的内存”的错误。这通常是其他内存损坏的指示。但是从C++应用程序调用时没有错误。背后的想法是什么?现在你在问为什么我们看不到的代码是错误的。你为什么不坚持你问的问题呢?本给了你正确的答案。你现在可以接受他的答案,然后为你的新问题担忧。
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;

namespace WindowsFormsApplication1
{
    public partial class Form1 : Form
    {
        [DllImport("C:\\WindowsFormsApplication1\\WindowsFormsApplication1\\Wavelength_MaxIntensityDll.dll")]
        public static extern int start_acquisition(string path);
        [DllImport("C:\\WindowsFormsApplication1\\Wavelength_MaxIntensityDll.dll")]
        public static extern int stop_acquisition();
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            int ret = start_acquisition("C:\\Users\\nyan2012\\Desktop\\Wavelength_test\\test1.txt");
        }
    }
}
class PlatformInvokeTest
{
   [DllImport("user32.dll")]
   public static extern int MessageBoxA(
      int h, string m, string c, int type);

   public static int Main() 
   {
      return MessageBoxA(0, "Hello World!", "My Message Box", 0);
   }
}