代码之家  ›  专栏  ›  技术社区  ›  Bosz

cType加载的共享库符号也在glibc中定义;如何选择符号?

  •  1
  • Bosz  · 技术社区  · 6 年前

    使用python ctypes;加载的共享库(a)定义了 sem_init 由链接到库A的后续加载共享库(B)调用的函数。执行(在gdb中)会导致一个分段错误,在该错误中,库B调用 sem_init@@GLIBC_2.4 /lib/libpthread.so.0 (属于glibc?)而不是 扫描电镜初始化 由图书馆A提供。

    为了确认,我重新命名了 扫描电镜初始化 在图书馆A和B,问题就消失了。不幸的是,其他程序依赖于符号 扫描电镜初始化 在库A中,因此这不是一个解决方案。我怎么确认B图书馆的电话 扫描电镜初始化 从A库不更改到A库?

    1 回复  |  直到 6 年前
        1
  •  2
  •   Employed Russian    6 年前

    不幸的是,其他程序依赖库A中的符号sem_init,因此这不是一个解决方案。

    引用自 libB sem_init 解析为内部定义 libpthread.so.0 (格利布的一部分)因为 libpthread.so.0版本 作为主服务器的依赖项加载 python 二元的,因此出现 之前 libA 在符号搜索列表中。所以每一个“正常”的参考 扫描电镜初始化 将决心 libpthread S定义。这是按预期工作的(重写标准库提供的符号是一个非常糟糕的主意(tm))。

    你可以强迫 libB.so 使用 libA.so:sem_init 通过这样做 伦敦银行同业拆借利率 (省略错误检查):

    void *h = dlopen("libA.so", RTLD_NOW|RTLD_GLOBAL)
    void (*p_sem_init)(...) = dlsym(h, "sem_init");
    
    // Call it:
    p_sem_init(...);
    

    这就行了 如果 扫描电镜初始化 是唯一冲突的符号,但如果存在其他符号冲突,则很可能以不明显的方式中断。