我正在尝试使用以下命令在运行时在用C编写的Mac OS X应用程序中加载框架:
dlopen("/System/Library/Frameworks/JavaVM.framework/JavaVM",RTLD_LAZY);
如果我从主线程中调用dlopen()
,它会按预期工作。
当我从另一个线程调用它时,应用程序退出并显示错误:Trace/BPT trap
这是从主线程调用dlopen()
的代码(并且有效):
int main(int argc, char** argv)
{
void *result = dlopen("/System/Library/Frameworks/JavaVM.framework/JavaVM",RTLD_LAZY);
if (!result) {
printf("can't open library JavaVM: %s\n", dlerror());
}
else {
printf("library JavaVM loaded\n");
}
return 0;
}
输出为:库JavaVM加载
这是从另一个线程调用dlopen()
的代码(并在调用该函数期间退出):
void *loadJava(void* arg)
{
void *result = dlopen("/System/Library/Frameworks/JavaVM.framework/JavaVM",RTLD_LAZY);
if (!result) {
printf("can't open library JavaVM: %s\n", dlerror());
}
else {
printf("library JavaVM loaded\n");
}
}
int main(int argc, char** argv)
{
pthread_t vmthread;
struct rlimit limit;
size_t stack_size = 0;
int rc = getrlimit(RLIMIT_STACK, &limit);
if (rc == 0) {
if (limit.rlim_cur != 0LL) {
stack_size = (size_t)limit.rlim_cur;
}
}
pthread_attr_t thread_attr;
pthread_attr_init(&thread_attr);
pthread_attr_setscope(&thread_attr, PTHREAD_SCOPE_SYSTEM);
pthread_attr_setdetachstate(&thread_attr, PTHREAD_CREATE_DETACHED);
if (stack_size > 0) {
pthread_attr_setstacksize(&thread_attr, stack_size);
}
pthread_create(&vmthread, &thread_attr, loadJava, NULL);
pthread_attr_destroy(&thread_attr);
pthread_exit(NULL);
return 0;
}
输出为:跟踪/ BPT陷阱
错误在哪里? 对不起,如果这是一个愚蠢的问题,但我还是新手
答案 0 :(得分:1)
似乎dlopen()只是不是线程安全的,所以你不应该在多个线程下调用它 或者可能,它不是dlopen(),它不是线程安全的,而是你的库的初始化代码,它在加载时运行。
没有理由在线程下调用dlopen,因为它不会多次加载库
当你多次加载同一个文件时,第二次没有做任何事情(除了增加一些refcount),只返回相同的句柄。因此,每个线程加载它就没有任何好处。
您可以使用dlmopen()多次真正加载库。但它仅限于15次 即便如此,你应该在启动线程之前在main()中执行它(并为每个线程提供其库句柄),而不是在线程内。