问题描述
我正在从这里得到的示例中的类创建共享库。我想从创建的共享库中调用另一个共享库,然后在主程序中使用它。因此,我有myclass.so库,我想从myclass.so库中调用另一个库,例如anotherclass.so,然后在主程序中使用此myclass.so库。关于如何执行此操作的任何想法。
I am creating a shared library from a class from an example I got here C++ Dynamic Shared Library on Linux. I would like to call another shared library from the shared library created and then use it in the main program. So I have the myclass.so library and I want to call another library say anotherclass.so from the myclass.so library and then use this myclass.so library in the main program. Any idea on how I can do this please.
推荐答案
可以使用多种方法将多个共享库添加到
是程序的链接,如果您正在构建所有库,则程序自己是
。
There is more than one way in which multiple shared libraries may be added tothe linkage of a program, if you are building all the libraries, and the program,yourself.
基本方法是简单地显式将所有库添加到程序链接的
中,这是通常的方法,如果您仅构建
程序并链接由另一方构建的库。
The elementary way is simply to explicitly add all of the libraries to thethe linkage of the program, and this is the usual way if you are building only theprogram and linking libraries built by some other party.
如果链接中的对象文件 foo.o
取决于库 libA.so
,然后
foo.o
在链接序列中应位于 libA.so
之前。同样,如果 libA.so
取决于 libB.so
,则 libA.so
应该在 libB.so
之前。这是一个例子。
If an object file foo.o
in your linkage depends on a library libA.so
, thenfoo.o
should precede libA.so
in the linkage sequence. Likewise if libA.so
depends on libB.so
then libA.so
should precede libB.so
. Here's an illustration.
我们将从文件中创建一个共享库 libsquare.so
:
We'll make a shared library libsquare.so
from the files:
square.h
#ifndef SQUARE_H
#define SQUARE_H
double square(double d);
#endif
和
square.cpp
#include <square.h>
#include <cmath>
double square(double d)
{
return pow(d,2);
}
请注意,函数 square
调用 pow
,该声明在
标准头文件< cmath>
中声明,并在数学库 libm
。
Notice that the function square
calls pow
, which is declared in theStandard header <cmath>
and defined in the math library, libm
.
编译源文件 square.cpp
到与位置无关的目标文件
square.o
:
Compile the source file square.cpp
to a position-independent object filesquare.o
:
$ g++ -Wall -fPIC -I. -c square.cpp
然后链接 square.o
进入共享库 libsquare.so
:
$ g++ -shared -o libsquare.so square.o
接下来,我们将创建另一个共享库<$ c $这些文件中的c> libcube.so :
Next we'll make another shared library libcube.so
from these files:
cube.h
#ifndef CUBE_H
#define CUBE_H
double cube(double d);
#endif
和
cube.cpp
#include <cube.h>
#include <square.h>
double cube(double d)
{
return square(d) * d;
}
请参见函数 cube
调用 square
,因此 libcube.so
要转到
取决于 libsquare.so
。像以前一样构建库:
See that the function cube
calls square
, so libcube.so
is going todepend on libsquare.so
. Build the library as before:
$ g++ -Wall -fPIC -I. -c cube.cpp
$ g++ -shared -o libcube.so cube.o
即使 libcube $ c,我们也不想将
libsquare
与 libcube
链接。 $ c>
取决于 libsquare
,即使我们可以,因为我们正在构建 libcube
。
因此,我们不必费心将 libm
与 libsquare
链接。默认情况下,
链接器将使我们链接包含未定义引用的共享库,并且
是完全正常的。它不会让我们将程序与未定义的引用链接起来。
We haven't bothered to link libsquare
with libcube
, even though libcube
depends on libsquare
, and even though we could have, since we're building libcube
.For that matter, we didn't bother to link libm
with libsquare
. By default thelinker will let us link a shared library containing undefined references, and itis perfectly normal. It won't let us link a program with undefined references.
最后,让我们使用这些文件制作程序库,来自此文件:
Finally let's make a program, using these libraries, from this file:
main.cpp
#include <cube.h>
#include <iostream>
int main()
{
std::cout << cube(3) << std::endl;
return 0;
}
首先,将该源文件编译为 main.o
:
First, compile that source file to main.o
:
$ g++ -Wall -I. -c main.cpp
然后链接 main.o
具有所有三个必需的库,请确保按依赖性顺序列出
链接器输入: main.o
, libcube.so
, libsquare.so
, libm.so
:
Then link main.o
with all three required libraries, making sure to listthe linker inputs in dependency order: main.o
, libcube.so
, libsquare.so
, libm.so
:
$ g++ -o prog main.o -L. -lcube -lsquare -lm
libm
是系统库,因此无需告诉链接器在哪里寻找
。但是 libcube
和 libsquare
不是,所以我们需要告诉链接器在其中寻找
。当前目录(。
),因为它们在那里。 -L。
做到了。
libm
is a system library so there's no need to tell the linker where to look forit. But libcube
and libsquare
aren't, so we need to tell the linker to look forthem in the current directory (.
), because that's where they are. -L.
does that.
我们已成功链接 ./ prog
,但:
$ ./prog
./prog: error while loading shared libraries: libcube.so: cannot open shared object file: No such file or directory
它不运行。这是因为运行时 loader 不知道在哪里找到 libcube.so
(或 libsquare.so
,尽管距离还远)。
It doesn't run. That's because the runtime loader doesn't know where to find libcube.so
(or libsquare.so
, though it didn't get that far).
通常,当我们构建共享库时,我们会将它们安装在加载程序的默认
中搜索目录(与链接器的默认搜索目录相同),这些目录可用于任何程序,因此不会发生。但是我不是
要在我的系统上安装这些玩具库,因此,作为一种解决方法,我将通过设置 LD_LIBRARY_PATH提示装载程序在哪里寻找
在我的外壳中。
Normally, when we build shared libraries we then install them in one of the loader's defaultsearch directories (the same ones as the linker's default search directories), where they're available to any program, so this wouldn't happen. But I'm notgoing to install these toy libraries on my system, so as a workaround I'll prompt the loader where to lookfor them by setting the LD_LIBRARY_PATH
in my shell.
$ export LD_LIBRARY_PATH=.
$ ./prog
27
好。 3 cubed = 27。
Good. 3 cubed = 27.
将程序与标准系统库目录中未位于
的共享库链接的另一种更好的方法是链接程序使用链接器的
-rpath = DIR
选项。这会将一些信息写入可执行文件,以告知加载器
在尝试将
设置为默认位置之前,应在 DIR
中搜索所需的共享库。
Another and better way to link a program with shared libraries that aren't locatedin standard system library directories is to link the program using the linker's-rpath=DIR
option. This will write some information into the executable to tellthe loader that it should search for required shared libraries in DIR
before it triesthe default places.
以这种方式重新链接 ./ prog
(首先删除 LD_LIBRARY_PATH
,因此不再有效):
Let's relink ./prog
that way (first deleting the LD_LIBRARY_PATH
from the shell so that it's not effective any more):
$ unset LD_LIBRARY_PATH
$ g++ -o prog main.o -L. -lcube -lsquare -lm -Wl,-rpath=.
然后重新运行:
$ ./prog
27
要使用 -rpath
与g ++,在其前面加上 -Wl
前缀,因为它是链接器 ld $的选项c $ c>,
g ++
前端无法识别: -Wl
告诉 g ++
只是将
选项直接传递给 ld
。
To use -rpath
with g++, prefix it with -Wl
, because it's an option for linker, ld
,that the g++
frontend doesn't recognise: -Wl
tells g++
just to pass theoption straight through to ld
.
这篇关于在另一个共享库中使用共享库的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!