mirror of
https://github.com/LuaJIT/LuaJIT.git
synced 2025-02-12 17:24:09 +00:00
FFI: Resolve ld script redirection in ffi.load().
This commit is contained in:
parent
e1aa8d0d97
commit
6c43767c23
@ -22,6 +22,7 @@
|
|||||||
#if LJ_TARGET_DLOPEN
|
#if LJ_TARGET_DLOPEN
|
||||||
|
|
||||||
#include <dlfcn.h>
|
#include <dlfcn.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
#if defined(RTLD_DEFAULT)
|
#if defined(RTLD_DEFAULT)
|
||||||
#define CLIB_DEFHANDLE RTLD_DEFAULT
|
#define CLIB_DEFHANDLE RTLD_DEFAULT
|
||||||
@ -59,11 +60,41 @@ static const char *clib_extname(lua_State *L, const char *name)
|
|||||||
return name;
|
return name;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Quick and dirty solution to resolve shared library name from ld script. */
|
||||||
|
static const char *clib_resolve_lds(lua_State *L, const char *name)
|
||||||
|
{
|
||||||
|
FILE *fp = fopen(name, "r");
|
||||||
|
if (fp) {
|
||||||
|
char *p, *e, buf[256];
|
||||||
|
if (fgets(buf, sizeof(buf), fp) && !strncmp(buf, "/* GNU ld script", 16)) {
|
||||||
|
while (fgets(buf, sizeof(buf), fp)) {
|
||||||
|
if (!strncmp(buf, "GROUP", 5) && (p = strchr(buf, '('))) {
|
||||||
|
while (*++p == ' ') ;
|
||||||
|
for (e = p; *e && *e != ' ' && *e != ')'; e++) ;
|
||||||
|
fclose(fp);
|
||||||
|
return strdata(lj_str_new(L, p, e-p));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fclose(fp);
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
static void *clib_loadlib(lua_State *L, const char *name, int global)
|
static void *clib_loadlib(lua_State *L, const char *name, int global)
|
||||||
{
|
{
|
||||||
void *h = dlopen(clib_extname(L, name),
|
void *h = dlopen(clib_extname(L, name),
|
||||||
RTLD_LAZY | (global?RTLD_GLOBAL:RTLD_LOCAL));
|
RTLD_LAZY | (global?RTLD_GLOBAL:RTLD_LOCAL));
|
||||||
if (!h) clib_error_(L);
|
if (!h) {
|
||||||
|
const char *e, *err = dlerror();
|
||||||
|
if (*err == '/' && (e = strchr(err, ':')) &&
|
||||||
|
(name = clib_resolve_lds(L, strdata(lj_str_new(L, err, e-err))))) {
|
||||||
|
h = dlopen(name, RTLD_LAZY | (global?RTLD_GLOBAL:RTLD_LOCAL));
|
||||||
|
if (h) return h;
|
||||||
|
err = dlerror();
|
||||||
|
}
|
||||||
|
lj_err_callermsg(L, err);
|
||||||
|
}
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user