使用libtool来从一个共享库加载重复的函数名
-
19-09-2019 - |
题
我试图创建一个“调试”共享库(即,的.so或.dll文件)调用具有相同C API作为调试文库(在这种情况下,另一“真实”共享库,来模拟在PKCS#11 API)。不过,我跑了麻烦,其中调试库的链接映射与真正的图书馆的碰撞,导致调试库调用自身职能,而不是相应的功能在真实库。我发现了一个解决这个问题,通过使用POSIX dlmopen命令,但想了解如果同样可能使用GNU的libtool的。
在我的Solaris 10系统,下面的代码失败断言时测试应用程序静态链接到调试库:
#include <dlfcn.h>
int MyFunctionName() {
int (*function_ptr)();
void *handle = dlopen("realsharedlibrary.so", RTDL_LAZY);
*(void **)(&function_ptr) = dlsym(handle, "MyFunctionName");
ASSERT(function_ptr != MyFunctionName); // Fails
return (*function_ptr)();
}
在这种情况下,得到了一个函数指针到本地“MyFunctionName”(在调试库中),而不是MyFunctionName真正共享库中。
我发现,它可能通过,而不是“dlopen的” dlmopen“的命令,并加载实库时告诉dlmopen创建一个新的链接图(与LM_ID_NEWLM
参数)来解决这个问题:
int MyFunctionName() {
int (*function_ptr)();
void *handle = dlmopen(LM_ID_NEWLM, "realsharedlibrary.so", RTDL_LAZY);
*(void **)(&function_ptr) = dlsym(handle, "MyFunctionName");
ASSERT(function_ptr != MyFunctionName); // succeeds
return function_ptr(); // call real function
}
不幸的是,dlmopen似乎没有被包括的libtool内(即,我没有看到在libtool的一个lt_dlmopen功能)。
是否有可能使用libtool的命令做同样的事情 - 那就是,加载新的库时创建一个新的连接图,以便它不与调试库的链接图
碰撞?解决方案
我还没有发现使用libtool来尚未解决这个问题的好办法,但有一种方法,通过使用dlopen这些标志,以避免特定于Solaris的“dlmopen”功能:
void *handle = dlopen("realsharedlibrary.so", RTLD_NOW | RTLD_GROUP | RTLD_LOCAL)
显然,符号碰撞的问题是通过使用RTLD_NOW
代替RTLD_LAZY
并通过加入RTLD_GROUP
解决。该RTLD_LOCAL
是因为有POSIX要求使用任何RTLD_LOCAL
或RTLD_GLOBAL
,或行为是不确定的。对于Solaris,行为是默认为RTLD_LOCAL
。
在开放的问题,不过,是是否有可能通过这些类型的标志来lt_dlopen。