C ++静态链接的共享库 [英] C++ Statically linked shared library

查看:497
本文介绍了C ++静态链接的共享库的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个共享库使用的另一个应用程序超出了我的控制,需要* .so对象。我的库使用sqlite3,需要与它静态链接(我绝对需要一个自包含的二进制)。

I have a shared library used by a another application beyond my control which requires *.so objects. My library makes use of sqlite3 which needs to be statically linked with it (I absolutely need a self-contained binary).

当我尝试编译和链接我的库:

When I try to compile and link my library:

-fpic -flto -pthread -m64
-flto -static -shared

我最后出现以下错误:

/usr/bin/ld: /usr/local/lib/gcc/x86_64-unknown-linux-gnu/4.6.1/crtbeginT.o: relocation R_X86_64_32 against `__DTOR_END__' can not be used when making a shared object; recompile with -fPIC
/usr/local/lib/gcc/x86_64-unknown-linux-gnu/4.6.1/crtbeginT.o: could not read symbols: Bad value
collect2: ld returned 1 exit status

与-fPIC重新编译是什么?我的代码或CRT?

What is recompile with -fPIC related to? My code or CRT?

我已经尝试用-fPIC编译我的对象,结果相同。

I have already tried to compile my object with -fPIC with the same result.

谢谢。


EDIT:

问题似乎并不相关到SQLite3。

The problem does not seem to be related to SQLite3.

我写了一个简单的一行无用的库,它编译和链接如下:

I wrote a simple one-line-do-nothing library which compiles and links like this:

g++ -c -fPIC -o bar.o bar.cpp
g++ -shared -o bar.so bar.o

但不是这样:

g++ -c -fPIC -o bar.o bar.cpp
g++ -static -shared -o bar.so bar.o

问题似乎与CRT(crtbeginT.o)有关。我应该重新编译GCC --with-pic或任何东西?

The problem seems to be related to CRT (crtbeginT.o). Am I supposed to recompile GCC --with-pic or anything?

推荐答案

您不应使用 -static flag创建共享库时,用于创建静态链接的可执行文件。

You shouldn't use the -static flag when creating a shared library, it's for creating statically linked executables.

如果您只有一个静态版本的库,使用 -lsqlite3 。但是如果同时存在动态版本(.so)和静态版本,链接器将更喜欢动态版本。

If you only have a static version of the library, you can just link it in using -lsqlite3. But if there's both a dynamic version(.so) and a static version, the linker will prefer the dynamic one.

要指示链接器选择静态版本链接器 -Bstatic 标志,并使它切换回动态链接其他东西(如libc和动态运行时支持)与 -Bdynamic 。也就是说,您使用标志:

To instruct the linker to pick the static one, give the linker the -Bstatic flag, and make it switch back to dynamic linking for other stuff (like libc and dynamic runtime support) with -Bdynamic. That is, you use the flags:

 -Wl,-Bstatic -lsqlite3 -Wl,-Bdynamic 

或者,您只需指定.a文件的完整路径,例如 /usr/lib/libsqlite3.a 而不是任何编译器/链接器标志。

Alternativly, you can just specify the full path of the .a file, e.g. /usr/lib/libsqlite3.a instead of any compiler/linker flags.

也可以使用 -l:libsqlite3.a 而不是 -lsqlite3 。这将强制使用库文件 libsqlite3.a 而不是 libsqlite3.so ,链接器默认使用。

With the GNU ld, you can also use -l:libsqlite3.a instead of -lsqlite3. This will force the use of the library file libsqlite3.a instead of libsqlite3.so, which the linker prefers by default.

请记住确保.a文件已使用 -fpic 标志编译,否则通常可以不会将其嵌入到共享库中。

Remember to make sure the .a file have been compiled with the -fpic flag, otherwise you normally can't embed it in a shared library.

这篇关于C ++静态链接的共享库的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆