C#中调用C生成的Dll,总报程序发生异常错误..不懂为什么..
C的代码:
int Sum(int a,int b)
{
return a+b;
}
C#中调用的代码:
class Dll
{
[DllImport("EssDll.dll",EntryPoint="Sum",
CharSet=CharSet.Auto,CallingConvention=CallingConvention.StdCall)]
public static extern int Sum(int a,int b); /// <summary>
/// 应用程序的主入口点。
/// </summary>
[STAThread]
static void Main(string[] args)
{
Console.Write("Dll测试开始\n");
Console.Write(Sum(5,6).ToString());
Console.Write("\n前面调用Dll完成!\n");
string ok = Console.ReadLine();
}
}C生成Dll是用Cywin来生成的,命令如下:
EssDll:
gcc -g -c ./src/EssDll.c -I./include -L./lib
dllwrap -o EssDll.dll EssDll.o --def ./src/EssDll.def
mv ./EssDll.o ./obj/
mv ./EssDll.dll ./bin/*.def文件如下:
LIBRARY EssDll
EXPORTS
Sum
C的代码:
int Sum(int a,int b)
{
return a+b;
}
C#中调用的代码:
class Dll
{
[DllImport("EssDll.dll",EntryPoint="Sum",
CharSet=CharSet.Auto,CallingConvention=CallingConvention.StdCall)]
public static extern int Sum(int a,int b); /// <summary>
/// 应用程序的主入口点。
/// </summary>
[STAThread]
static void Main(string[] args)
{
Console.Write("Dll测试开始\n");
Console.Write(Sum(5,6).ToString());
Console.Write("\n前面调用Dll完成!\n");
string ok = Console.ReadLine();
}
}C生成Dll是用Cywin来生成的,命令如下:
EssDll:
gcc -g -c ./src/EssDll.c -I./include -L./lib
dllwrap -o EssDll.dll EssDll.o --def ./src/EssDll.def
mv ./EssDll.o ./obj/
mv ./EssDll.dll ./bin/*.def文件如下:
LIBRARY EssDll
EXPORTS
Sum
贴出代码来。随便提一下,你加了using System.Runtime.InteropServices;没?
一般仅这样标一个属性就足够了[DllImport("EssDll.dll")]给点建议:
1.不要用GCC编译dll,在linux下,函数的调用过程默认的不是__stdcall,编译dll时生成的代码的参数压栈方式与windows下不同。2.跨系统使用模块时,最好用一下COM的方法。并不是指你一定要用COM规范来做dll,COM提供的一种二进制上的一致性,主要是通过接口来将实现隔离,《COM本质论》中把这些概念解释得很清楚。
用VS.NET编译时没有出错,只是在运行时,程序去调用c的dll中函数时报错,说"出现异常错误"....我是在windows xp 上用cywin来编辑c成dll的,不懂是不是这样不行? 因为没安装VC
不懂什么意思?C#完整调用代码如下:
using System;
using System.Runtime.InteropServices;namespace ConsoleApplication
{
/// <summary>
/// Class1 的摘要说明。
/// </summary>
class Dll
{
[DllImport("EssDll.dll",EntryPoint="Sum",
CharSet=CharSet.Auto,CallingConvention=CallingConvention.StdCall)]
public static extern int Sum(int a,int b);// public static int Sum(int a,int b)
// {
// return a+b;
// }
/// <summary>
/// 应用程序的主入口点。
/// </summary>
[STAThread]
static void Main(string[] args)
{
Console.Write("Dll测试开始\n");
Console.Write(Sum(5,6).ToString());
Console.Write("\n前面调用Dll完成!\n");
string ok = Console.ReadLine();
}
}
}
注意了,Sum返回的是int,还不是System.Int32,
如果你要输出Sum的值,最好格式化一下
这样就可以了
ire = Sum(5,6);
Console.Write("\n前面调用Dll完成!\n");
string ok = Console.ReadLine();
1.在生成dll时,我去掉了static关键字,不去掉,我用VC6编译通不过。至于这个原因,我还不清楚。
同时我在添加了__stdcall关键字,其实VC6编译时默认的就是以__stdcall。2.在类中导入dll中的函数时,必须声明为static。就算dll中那个函数不是静态的也没有关系。