如何使用后期绑定调用本机 C 库?

Posted

技术标签:

【中文标题】如何使用后期绑定调用本机 C 库?【英文标题】:How to call native C library using late binding? 【发布时间】:2015-09-08 01:47:44 【问题描述】:

我一直在寻找加载本地 C 库并使用后期绑定调用其方法的示例。我在加载托管库而不是本地 C 库时看到了很多示例。

原生 C 库定义如下:

#define DllExport __declspec( dllexport )

typedef void (*CALLBACK_T)(long, void *);

CALLBACK_T g_Callback=NULL;

DllExport BOOL GetVersion(char *szVersion)

   AFX_MANAGE_STATE(AfxGetStaticModuleState());
   strcpy( szVersion, GetAppVersion());

   return TRUE;


DllExport void SetCallbackFunction(CALLBACK_T f)

   AFX_MANAGE_STATE(AfxGetStaticModuleState());

   g_Callback = f;

   return;

如何使用后期绑定加载 DLL 并调用这两种方法?

提前致谢。 洛杉矶


我应该提到我需要加载库并从 c# 应用程序调用这些方法。

【问题讨论】:

【参考方案1】:

在 Windows 中获取函数地址只有一种方法:GetProcAddress。您必须自己导入它,然后按名称加载您想要的任何功能。它返回一个IntPtr

获得IntPtr 后,将其转换为带有GCHandle.FromIntPtrGCHandle,然后使用GCHandle.Target 属性获取委托。一旦你有了你的委托,就可以像往常一样称呼它。确保你正确地装饰了你的委托,它仍然必须匹配你的 C 代码中的调用约定。

【讨论】:

或者,如果你已经有一个委托类型,Marshal.GetDelegateForFunctionPointer 哇哦,他们添加了这个! .NET 4.5.1 最低,如果合适,请继续使用它! 在旧的框架版本中还有一个非泛型版本,它需要一个指针和一个类型,AFAIK 已经存在了一段时间。 我认为我正在取得进展,但我收到一个异常,指出我的委托签名可能与库方法的签名不匹配。如何编组 GetVersion(char *version) 方法中返回的字符串。我尝试了以下方法: public delegate bool _GETDLLVERSION ( IntPtr ptr );公共委托 bool _GETDLLVERSION (StringBuilder sb); @user3242337 AFAIK,您不能将StringBuilderchar* 一起使用,因为一个使用unicode 而另一个不使用。将char* 更改为wchar_t*,或在C# 端使用byte[]。这是假设 char* 用于输出字符串。

以上是关于如何使用后期绑定调用本机 C 库?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Xamarin.iOS 中正确包装本机 c 库

如何从 .NET 对 .NET 中定义的 COM 对象执行后期绑定调用(通过 DispID)?

Excel VBA后期绑定Microsoft DAO 3.6对象库

如何使用 javascript 绑定项目从 cocos2d html5 调用本机 ios api?

如何在本机代码中绑定 java 服务?

如何在不循环的情况下将数组(Range.Value)传递给本机 .NET 类型?