ldd 可执行输出中缺少动态加载的库

vra*_*en1 3 c++ linux shared-libraries dynamic-loading ldd

为什么给ldd可执行文件名时不出现动态加载的库?这是真的吗?因为我找不到什么时候给的。这可能是因为动态加载和动态链接。

请帮我解决这个问题,如果您需要任何进一步的细节,请告诉我。

输出如下。

ldd example6 

    linux-vdso.so.1 =>  (0x00007ffe63369000)
    libdl.so.2 => /lib/x86_64-linux-gnu/libdl.so.2 (0x00007f56a2676000)
    libstdc++.so.6 => /usr/lib/x86_64-linux-gnu/libstdc++.so.6 (0x00007f56a2372000)
    libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f56a1fa9000)
    /lib64/ld-linux-x86-64.so.2 (0x00007f56a287a000)
    libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007f56a1ca3000)
    libgcc_s.so.1 => /lib/x86_64-linux-gnu/libgcc_s.so.1 (0x00007f56a1a8d000)
Run Code Online (Sandbox Code Playgroud)

我只能看到 libdl.so...但我的可执行文件,example6 依赖于 libtriangle.so,它是为某些测试而创建的。

如果您在没有 dlopen 命令的情况下访问共享库,我可以在可执行文件中找到 .so 详细信息,因为我觉得它是静态加载和动态链接。

程序的结构

这里可执行,main 调用共享库,libtriangle.so。共享库,triangle.so 调用另一个共享库,man.so.. man.so 调用 pthread api

Makefile 出现在最后

man.so 是使用 livingbeing.hpp,man.cpp 获得的,man.cpp 使用 pthread apis.man.so 取决于 -lpthread

triangle.so 使函数调用 man.so。triangle.so 访问共享库,man.so 使用 dlopen,dlsym 命令。

Executable,main 依赖于triangle.so。主要访问triangle.so 使用dlopen,dlsym 函数。

ldconfig 也适用于 /usr/local/lib/MYDIR 中的 .so 文件

请找到以下文件。

生物.hpp

 #ifndef LIVINGBEING_HPP

 #define LIVINGBEING_HPP

  #include <iostream>

using namespace std;

class livingbeing {
protected:
    double side_length_;




public:
    livingbeing()
        : side_length_(0) {}

    virtual ~livingbeing() {}
    void set_length(double side_length) {
        side_length_ = side_length;
    }

    virtual void eat() = 0;
};

typedef livingbeing* get_instance_t();
typedef void destroy_instance_t(livingbeing*);

 #endif
Run Code Online (Sandbox Code Playgroud)

man.cpp

 #include "livingbeing.hpp"
 #include <stdio.h>
 #include <stdlib.h>
 #include <pthread.h>
void *print_message_function( void *ptr );
class man : public livingbeing {
public:
man()
{
cout<<"man constructor\n";

}
~man()
{
cout<<"man destructor\n";
}

    virtual void eat() {
        cout<<"man eating\n";

        pthread_t thread1, thread2;
    int  iret1;

   /* Create independent threads each of which will execute function */

    iret1 = pthread_create( &thread1, NULL, print_message_function, (void*) NULL);

    pthread_join( thread1, NULL);

    }
};

void *print_message_function( void *ptr )
{
        cout<<"hello thread1 created";
}
extern "C" livingbeing * get_instance()
{
return new man;
}
extern "C" void destroy_instance(livingbeing *lb)
{
delete lb;
}
Run Code Online (Sandbox Code Playgroud)

三角形.cpp

#include "polygon.hpp"
 #include "livingbeing.hpp"
 #include <cmath>

#include <dlfcn.h>
//#include <iostream>

class triangle : public polygon {
public:
    virtual double area() const {

    // load the triangle library
    void* man = dlopen("/usr/local/lib/ramu/libman.so", RTLD_LAZY);
    if (!man) {
        cerr << "Cannot load library: " << dlerror() << '\n';
        return 1;
    }

    // reset errors
    dlerror();

    // load the symbols
    get_instance_t* get_instance_man = (get_instance_t*) dlsym(man, "get_instance");
    const char* dlsym_error = dlerror();
    if (dlsym_error) {
        cerr << "Cannot load symbol create: " << dlsym_error << '\n';
        return 1;
    }

    destroy_instance_t* destroy_instance_man = (destroy_instance_t*) dlsym(man, "destroy_instance");
    dlsym_error = dlerror();
    if (dlsym_error) {
        cerr << "Cannot load symbol destroy: " << dlsym_error << '\n';
        return 1;
    }

    // create an instance of the class
    livingbeing* living = get_instance_man();

    // use the class
    living->set_length(7);
    cout << "The livingbeing is: ";

    living->eat();
    cout<<"\n";


    // destroy the class
        destroy_instance_man(living);

    // unload the triangle library
    dlclose(man);


        return side_length_ * side_length_ * sqrt(3) / 2;
    }
};

// the class factories
extern "C" polygon* create() {
    return new triangle;
}

extern "C" void destroy(polygon* p) {
    delete p;
}
Run Code Online (Sandbox Code Playgroud)

主程序

#include "polygon.hpp"

#include <iostream>
#include <dlfcn.h>

int main() {
    using std::cout;
    using std::cerr;

    // load the triangle library
//    void* triangle = dlopen("./triangle.so", RTLD_LAZY);
    void* triangle = dlopen("/usr/local/lib/rakesh/libtriangle.so", RTLD_LAZY);
    if (!triangle) {
        cerr << "Cannot load library: " << dlerror() << '\n';
        return 1;
    }

    // reset errors
    dlerror();

    // load the symbols
    create_t* create_triangle = (create_t*) dlsym(triangle, "create");
    const char* dlsym_error = dlerror();
    if (dlsym_error) {
        cerr << "Cannot load symbol create: " << dlsym_error << '\n';
        return 1;
    }

    destroy_t* destroy_triangle = (destroy_t*) dlsym(triangle, "destroy");
    dlsym_error = dlerror();
    if (dlsym_error) {
        cerr << "Cannot load symbol destroy: " << dlsym_error << '\n';
        return 1;
    }

    // create an instance of the class
    polygon* poly = create_triangle();

    // use the class
    poly->set_side_length(7);
        cout << "The area is: " << poly->area() << '\n';

    // destroy the class
    destroy_triangle(poly);

    // unload the triangle library
    dlclose(triangle);
Run Code Online (Sandbox Code Playgroud)

生成文件

example6: main.cpp triangle
        $(CXX) $(CXXFLAGS) main.cpp -o example6 -L/usr/local/lib/roh -ltriangle -ldl

triangle: man triangle.cpp polygon.hpp
        $(CXX) $(CXXFLAGS) -shared -fPIC triangle.cpp -o libtriangle.so

man: man.cpp livingbeing.hpp
        $(CXX) $(CXXFLAGS) -shared -fPIC -o man.so man.cpp -lpthread

clean:
        rm -f example6 *.so *.o

.PHONY: clean
Run Code Online (Sandbox Code Playgroud)

use*_*670 5

Executablemain不依赖于在其导入表libtriangle中包含libtriangle符号的意义。ldd不知道在运行时加载的库,dlopen因为它不运行或无论如何分析代码。它只查看符号表。请注意,即使您libtriangle在构建可执行文件时显式链接,它也无效。如果可执行文件中有一些未解析的符号位于该库中,但在main可执行文件中没有,则链接器只会真正链接库。