我总是假定链接器分配了任何库的bss部分并将其映射到进程中。 这部分的大小将取决于图书馆报告的bss的大小。
我查看了进程的/ proc / [PID] / maps文件,并计算了加载库的bss部分的大小。
7f1f5561f000-7f1f55637000 r-xp 00000000 08:01 3018048 /usr/lib/libpthread-2.19.so 7f1f55637000-7f1f55837000 ---p 00018000 08:01 3018048 /usr/lib/libpthread-2.19.so 7f1f55837000-7f1f55838000 r--p 00018000 08:01 3018048 /usr/lib/libpthread-2.19.so 7f1f55838000-7f1f55839000 rw-p 00019000 08:01 3018048 /usr/lib/libpthread-2.19.so 7f1f55839000-7f1f5583d000 rw-p 00000000 00:00 0 7f1f5583d000-7f1f55851000 r-xp 00000000 08:01 3017945 /usr/lib/libresolv-2.19.so 7f1f55851000-7f1f55a50000 ---p 00014000 08:01 3017945 /usr/lib/libresolv-2.19.so 7f1f55a50000-7f1f55a51000 r--p 00013000 08:01 3017945 /usr/lib/libresolv-2.19.so 7f1f55a51000-7f1f55a52000 rw-p 00014000 08:01 3017945 /usr/lib/libresolv-2.19.so 7f1f55a52000-7f1f55a54000 rw-p 00000000 00:00 0
在这里,我们可以看到libpthread的bss位于地址范围7f1f55839000-7f1f5583d000中,并将它们相减,得到了16384字节的大小。
使用size命令或readelf,libpthread的bss部分的大小是16848字节。
如何在共享库(.so)中使用共享库的同一进程的实例共享全局variables?
为什么要重新编译整个程序来更新库?
未定义的符号:在Linux中的JNI_CreateJavaVM
关于共享库的问题
这是有道理的,他们是不同的,因为虚拟地址范围需要排列到页面边界,但虚拟尺寸如何能够比由精灵文件报告的尺寸小? 没有足够的空间来适应所有的variables。
链接器是否能够确定某些在bss中的variables对于特定的加载可执行文件是不必要的? 如果是的话,这是怎么做的?
铿锵的ubsan&function指针:这是非法的吗?
为什么不使用静态链接更多?
在运行时更改库加载顺序(如LD_PRELOAD,但在执行期间)
C Linux:全局variables位于共享库中作为单例
设置Wsgi应用程序时,PCRE问题
在这里,我们可以看到libpthread的bss位于地址范围7f1f55839000-7f1f5583d000中,并将它们相减,得到了16384字节的大小。
这个困难源于陈述并不完全准确的事实。 ELF链接器和Linux加载器实际上并不保证段,段和映射之间的一对一关系。 结果是高亮的映射实际上并不代表所有的.bss (就像你发现的那样)。
通常,使用默认链接描述文件的ELF链接器将创建两个LOAD段:一个R / E(用于文本和只读数据)和一个R / W(用于可写入数据,包括.bss )。 它将安排.bss出现在段的末尾,以便它可以设置相关的ELF程序头 p_filesz ,只覆盖初始化的数据,同时将p_memsz设置为一个较大的值,为.bss添加足够的空间。
当加载器处理这个段时,它将创建一个或两个映射。 第一个映射将从p_offset为p_offset “文件支持”。 因此,初始访问时的页面错误将保证必要的初始值。 在第一个映射的最后一页中留下的任何空间都将被memset设置为零(访问本身首先出现任何初始值)。 如果剩余的p_memsz适合新填满的空间,那么装载程序需要做的就是这些。 否则,如果需要更多的空间,加载器将创建一个匿名映射(由/dev/zero )来覆盖其余部分。
因此,内存中.bss的大小实际上是第二个匿名映射和前一个映射的“尾部”的总和。 可能最简单的方法是根据各种适用的ELF,POSIX和Linux标准,对内存中的.bss进行估计(在由链接器,加载器和内核应用的各种对齐约束内),使用例如 readelf --program-headers获取适用的段的readelf --program-headers和p_memsz ,并从后者中减去前者。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。