当动态库使用静态库的符号时,从静态库打开动态库
dlopen a dynamic library from a static library, when the dynamic library uses symbols of the static one
这个问题与从静态库linux C++中dlopen动态库密切相关,但包含了一个更复杂的问题(使用C++而不是C):
我有一个链接到静态库(.a)的应用程序,该库使用dlopen函数加载动态库(.so)。此外,动态库调用静态库中定义的函数。
有没有一种方法可以在不将动态库与静态库链接的情况下编译它,反之亦然?
以下是我迄今为止尝试的内容,对相关问题的示例进行了轻微修改:
app.cpp:
#include "staticlib.hpp"
#include <iostream>
int main()
{
std::cout << "and the magic number is: " << doSomethingDynamicish() << std::endl;
return 0;
}
staticlib.hpp:
#ifndef __STATICLIB_H__
#define __STATICLIB_H__
int doSomethingDynamicish();
int doSomethingBoring();
#endif
staticlib.cpp:
#include "staticlib.hpp"
#include "dlfcn.h"
#include <iostream>
int doSomethingDynamicish()
{
void* handle = dlopen("./libdynlib.so",RTLD_NOW);
if(!handle)
{
std::cout << "could not dlopen: " << dlerror() << std::endl;
return 0;
}
typedef int(*dynamicfnc)();
dynamicfnc func = (dynamicfnc)dlsym(handle,"GetMeANumber");
const char* err = dlerror();
if(err)
{
std::cout << "could not dlsym: " <<err << std::endl;
return 0;
}
return func();
}
staticb2.cpp:
#include "staticlib.hpp"
#include "dlfcn.h"
#include <iostream>
int doSomethingBoring()
{
std::cout << "This function is so boring." << std::endl;
return 0;
}
dynlib.cpp:
#include "staticlib.hpp"
extern "C" int GetMeANumber()
{
doSomethingBoring();
return 1337;
}
和构建:
g++ -c -o staticlib.o staticlib.cpp
g++ -c -o staticlib2.o staticlib2.cpp
ar rv libstaticlib.a staticlib.o staticlib2.o
ranlib libstaticlib.a
g++ -rdynamic -o app app.cpp libstaticlib.a -ldl
g++ -fPIC -shared -o libdynlib.so dynlib.cpp
当我用./app
运行它时,我得到
could not dlopen: ./libdynlib.so: undefined symbol: _Z17doSomethingBoringv
and the magic number is: 0
来自dlopen
手册页面:
如果可执行文件与标志"-rdynamic"(或同义词"-export-dynamic")链接,则可执行文件中的全局符号也将用于解析动态加载库中的引用。
这意味着应用程序要导出其符号以在动态库中使用,必须使用-rdynamic
标志链接应用程序。
除了上述问题之外,还有另一个问题与静态库有关:问题是,由于主程序中没有调用doSomethingBoring
函数,因此静态库中的对象文件staticlib2.o
没有链接。
答案可以在这个老问题中找到,它告诉您添加--whole-archive
链接器标志:
g++ -rdynamic -o app app.cpp -L.
-Wl,--whole-archive -lstaticlib
-Wl,--no-whole-archive -ldl
相关文章:
- 如果C++类在类方法中具有动态分配,但没有构造函数/析构函数或任何非静态成员,那么它仍然是POD类型吗
- 视觉studo 2019中的漫画和静态/动态绑定
- 静态数组的自由动态数组
- 动态初始化 C 与 C++ 中的静态值
- 以下代码执行哪种内存分配(动态或静态)?
- 将静态内存更改为动态C++
- 如何静态识别动态堆分配?
- 如果包含映射的静态库与可执行文件和动态库链接,静态映射(变量)是否会被多次释放?
- 非类类型表达式的静态类型与动态类型之间的差异
- 如何使用类型级函数动态创建静态类型?
- 静态和动态模板初始化可以交错吗?
- 将基类分配给派生对象,反之亦然,以C++以及静态和动态对象之间的差异
- 虚拟成员函数的定义是否强制在同一转换单元中动态初始化静态数据成员?
- 将静态字符数组中的字符分配给动态分配的字符数组 - 访问冲突
- 动态分配的数组和静态数组之间的区别
- 动态分配对象中的字段-动态分配更好还是静态分配更好?C++
- 如何对以下程序使用静态或动态转换
- 如何使用cmake设置OpenCV以启用动态和静态构建
- 静态分配和动态分配返回不同的答案
- 我应该在这个程序中使用静态内存分配还是动态内存分配