首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >当开一个这样,它的符号是不被主要的符号所覆盖,为什么?

当开一个这样,它的符号是不被主要的符号所覆盖,为什么?
EN

Stack Overflow用户
提问于 2014-12-07 04:25:27
回答 3查看 560关注 0票数 4

libp2.c

代码语言:javascript
复制
#include <stdio.h>
void pixman()
{
    printf("pixman in libp1\n");
}

libc2.c

代码语言:javascript
复制
#include <stdio.h>

void pixman();
void cairo()
{
    printf("cairo2\n");
    pixman();
}

main.c

代码语言:javascript
复制
#include <stdio.h>
#include <dlfcn.h>


void pixman()
{
    printf("pixman in main\n");
}

int main()
{
    pixman();

    void* handle=NULL;
    void (*callfun)();

    handle=dlopen("/home/zpeng/test/so_test/libc2.so",RTLD_LAZY);
    callfun = (void(*)())dlsym(handle, "cairo");
    callfun();
...
}

编译

代码语言:javascript
复制
gcc -c  libp2.c -fPIC   -olibp2.o
rm libp2.a
ar -rs libp2.a libp2.o
gcc -shared -fPIC libc2.c  ./libp2.a -o libc2.so
gcc main.c  -ldl -L.  -g

结果:

代码语言:javascript
复制
pixman in main
cairo2
pixman: libp2

,为什么最后一个不是“主像素”?

我看到符号处理(LD_DEBUG=symbols),它以:

代码语言:javascript
复制
21180:     symbol=pixman;  lookup in file=./a.out
21180:     symbol=pixman;  lookup in file=/lib64/libdl.so.2
21180:     symbol=pixman;  lookup in file=/lib64/tls/libc.so.6
21180:     symbol=pixman;  lookup in file=/lib64/ld-linux-x86-64.so.2
21180:     symbol=pixman;  lookup in file=/home/zpeng/test/so_test/libc2.so

如果我将-lc2或-rdynamic添加到gcc主cmd中,它将生成:

代码语言:javascript
复制
pixman in main
cairo2
pixman in main

我的问题:

为什么在a.out中查找符号却没有得到结果并继续搜索when 2?如果没有-rdynamic和-lc2,那么呢?

EN

回答 3

Stack Overflow用户

发布于 2015-01-03 05:13:02

为什么最后一个不是“主像素”?,这是因为共享库有自己的全局偏移表或GOT。在libc2.so中使用cairo函数时,将调用的像素函数与编译.so文件时解析的函数相同。

这就是:

代码语言:javascript
复制
# creates object file only -- contains first pixman implementation
gcc -c  libp2.c -fPIC   -olibp2.o

# just turns the object file into an archive
ar -rs libp2.a libp2.o

# creates the .so file -- all symbols in libc2.c are resolved here 
# and you passed in the .a file for that purpose. The .a file containing the
# first pixman implementation gets put in libc2.so.
gcc -shared -fPIC libc2.c  ./libp2.a -o libc2.so  

在此之后,任何使用libc2.so的人都将获得存储在libc2.so中的副本。您发布的查找顺序是a.out的,我相信它是对的。它在a.out中查找像素,然后查找libc2.so,依此类推。

为什么在a.out中查找符号,但不能得到结果并继续搜索libc2。因此,当没有-rdynamic和-lc2时,rdynamic选项会将所有符号加载到动态符号表中--而不仅仅是它认为使用的符号表(lc2具有相同的效果)。当你加载所有这些符号时,你会有一个冲突--像素函数。在本例中使用main.c实现。正如其他人所指出的那样,这可能会产生一个警告。

票数 2
EN

Stack Overflow用户

发布于 2017-10-18 07:44:51

您需要用.a编译存档到-fvisibility=hidden文件中的源代码,以表明,尽管它们是全局函数,但它们并不是用于结果库之外的,而是用于解析库中的符号。这将导致.a文件中的符号以nm -a中的限定符“t”出现,而不是“T ",后者用于其他库可用的符号。

票数 1
EN

Stack Overflow用户

发布于 2021-11-07 17:57:36

它只是自动绑定到本地符号

由于libp2.c中没有__attribute__((visibility("default")))显式,编译器自动将此函数绑定到本地.symtab,而不是.dynsym

appendix1:关于ELF标题的更多信息:readelf -s xxx.lib

appendix2: ld参数-Bsymbolic-functions的关键字

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/27339604

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档