윤제균*_*윤제균 2 c windows dll shared-libraries dlopen
我写了一个为 linux 平台设计的 c 代码。现在,我想让它跨平台,以便在 Windows 中使用。在我的代码中,我 dlopen 一个 so 文件并使用其中的函数。下面是我的代码的样子。但是我才发现,在windows中,加载和使用动态库的方式大不相同。
void *mydynlib
mydynlib= dlopen("/libpath/dynlib.so",RTLD_LAZY);
void (*dynfunc1)() = dlsym(mydynlib,"dynfunc1");
void (*dynfunc2)(char*, char*, double) = dlsym(mydynlib,"dynfunc2");
int (*dynfunc3)() = dlsym(mydynlib,"dynfunc3");
Run Code Online (Sandbox Code Playgroud)
根据我的发现,我需要使用 LoadLibrary&GetProcAddress 而不是 dlopen&dlsym。但是,我不知道如何使用这些为 Windows 转换上面的行。我试图搜索一些示例几个小时,但找不到确切的解决方案。如果有人有这种经历,请给我一个提示。如果这是太明显的问题,请原谅。我对 C 很陌生。我通常用 python 编写我的程序。
您可以使用一组根据您的目标操作系统而变化的宏:
#ifdef __linux__
#define LIBTYPE void*
#define OPENLIB(libname) dlopen((libname), RTLD_LAZY)
#define LIBFUNC(lib, fn) dlsym((lib), (fn))
#elif defined(WINVER)
#define LIBTYPE HINSTANCE
#define OPENLIB(libname) LoadLibraryW(L ## libname)
#define LIBFUNC(lib, fn) GetProcAddress((lib), (fn))
#endif
Run Code Online (Sandbox Code Playgroud)
在我年轻的时候,我创造了这样的东西:
/* dlfcn.h */
#ifndef DLFCN_H
#define DLFCN_H
#define RTLD_GLOBAL 0x100 /* do not hide entries in this module */
#define RTLD_LOCAL 0x000 /* hide entries in this module */
#define RTLD_LAZY 0x000 /* accept unresolved externs */
#define RTLD_NOW 0x001 /* abort if module has unresolved externs */
/*
How to call in Windows:
void *h = dlopen ("path\\library.dll", flags)
void (*fun)() = dlsym (h, "entry")
*/
#ifdef __cplusplus
extern "C" {
#endif
void *dlopen (const char *filename, int flag);
int dlclose (void *handle);
void *dlsym (void *handle, const char *name);
const char *dlerror (void);
#ifdef __cplusplus
}
#endif
#endif
Run Code Online (Sandbox Code Playgroud)
和dlfcn.c:
/* dlfcn.c */
#include <inttypes.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <windows.h>
static struct {
long lasterror;
const char *err_rutin;
} var = {
0,
NULL
};
void *dlopen (const char *filename, int flags)
{
HINSTANCE hInst;
hInst= LoadLibrary (filename);
if (hInst==NULL) {
var.lasterror = GetLastError ();
var.err_rutin = "dlopen";
}
return hInst;
}
int dlclose (void *handle)
{
BOOL ok;
int rc= 0;
ok= FreeLibrary ((HINSTANCE)handle);
if (! ok) {
var.lasterror = GetLastError ();
var.err_rutin = "dlclose";
rc= -1;
}
return rc;
}
void *dlsym (void *handle, const char *name)
{
FARPROC fp;
fp= GetProcAddress ((HINSTANCE)handle, name);
if (!fp) {
var.lasterror = GetLastError ();
var.err_rutin = "dlsym";
}
return (void *)(intptr_t)fp;
}
const char *dlerror (void)
{
static char errstr [88];
if (var.lasterror) {
sprintf (errstr, "%s error #%ld", var.err_rutin, var.lasterror);
return errstr;
} else {
return NULL;
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
2453 次 |
| 最近记录: |