“---p”是什么意思? /proc/self/maps 中的权限意味着什么?
我理解 rwxps 位的含义。 r-xp 代表 .text。 rw-p 用于.data/.bss/heap/stack。仅仅 ---p
页面有什么用?
例如,请参阅 cat /proc/self/maps
的输出
00400000-0040b000 r-xp 00000000 08:03 827490 /bin/cat 0060b000-0060c000 rw-p 0000b000 08:03 827490 /bin/cat 0060c000-0062d000 rw-p 00000000 00:00 0 [heap] 3819a00000-3819a1e000 r-xp 00000000 08:03 532487 /lib64 ld-2.11.2.so 3819c1d000-3819c1e000 r--p 0001d000 08:03 532487 /lib64/ld-2.11.2.so 3819c1e000-3819c1f000 rw-p 0001e000 08:03 532487 /lib64/ld-2.11.2.so 3819c1f000-3819c20000 rw-p 00000000 00:00 0 3819e00000-3819f70000 r-xp 00000000 08:03 532490 /lib64/libc-2.11.2.so 3819f70000-381a16f000 ---p 00170000 08:03 532490 /lib64/libc-2.11.2.so 381a16f000-381a173000 r--p 0016f000 08:03 532490 /lib64/libc-2.11.2.so 381a173000-381a174000 rw-p 00173000 08:03 532490 /lib64/libc-2.11.2.so 381a174000-381a179000 rw-p 00000000 00:00 0 7fb859c49000-7fb85fa7a000 r--p 00000000 08:03 192261 /usr/lib/locale/locale-archive 7fb85fa7a000-7fb85fa7d000 rw-p 00000000 00:00 0 7fb85fa95000-7fb85fa96000 rw-p 00000000 00:00 0 7fff64894000-7fff648a9000 rw-p 00000000 00:00 0 [stack] 7fff649ff000-7fff64a00000 r-xp 00000000 00:00 0 [vdso] ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
I understand the meaning of rwxps bits. r-xp is for .text. rw-p is for .data/.bss/heap/stack. What is the use of just ---p
pages?
For example see this output of cat /proc/self/maps
00400000-0040b000 r-xp 00000000 08:03 827490 /bin/cat 0060b000-0060c000 rw-p 0000b000 08:03 827490 /bin/cat 0060c000-0062d000 rw-p 00000000 00:00 0 [heap] 3819a00000-3819a1e000 r-xp 00000000 08:03 532487 /lib64 ld-2.11.2.so 3819c1d000-3819c1e000 r--p 0001d000 08:03 532487 /lib64/ld-2.11.2.so 3819c1e000-3819c1f000 rw-p 0001e000 08:03 532487 /lib64/ld-2.11.2.so 3819c1f000-3819c20000 rw-p 00000000 00:00 0 3819e00000-3819f70000 r-xp 00000000 08:03 532490 /lib64/libc-2.11.2.so 3819f70000-381a16f000 ---p 00170000 08:03 532490 /lib64/libc-2.11.2.so 381a16f000-381a173000 r--p 0016f000 08:03 532490 /lib64/libc-2.11.2.so 381a173000-381a174000 rw-p 00173000 08:03 532490 /lib64/libc-2.11.2.so 381a174000-381a179000 rw-p 00000000 00:00 0 7fb859c49000-7fb85fa7a000 r--p 00000000 08:03 192261 /usr/lib/locale/locale-archive 7fb85fa7a000-7fb85fa7d000 rw-p 00000000 00:00 0 7fb85fa95000-7fb85fa96000 rw-p 00000000 00:00 0 7fff64894000-7fff648a9000 rw-p 00000000 00:00 0 [stack] 7fff649ff000-7fff64a00000 r-xp 00000000 00:00 0 [vdso] ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
根据手册页,它的意思是私有(写时复制)。但是,如果无法读取/写入/执行其中的任何内容,则不知道这种映射有什么用处。
可能它是 libc 私有的,允许它修改访问它的权限,而不会被用户程序意外地搞乱。
According to the man page, it means private (copy on write). No idea what the usefulness of such a mapping is without being able to read/write/execute anything in it, though.
Possibly it is private to libc, allowing it to modify the permissions to access it without a user program accidentally mucking it up.
私有映射(MAP_PRIVATE):对映射内容的修改对其他进程不可见。
对于文件映射,它们不会传递到底层文件。然而,对映射内容的更改对于每个进程来说都是私有的。
内核通过使用写时复制技术来实现这一点。这意味着每当进程尝试修改页面的内容时,内核首先会为该进程创建该页面的新的单独副本(并调整进程的页表)。
因此,MAP_PRIVATE 映射有时称为私有、写时复制映射。 (来源:《Linux 编程接口》一书)
Private mapping (MAP_PRIVATE): Modifications to the contents of the mapping are not visible to other processes.
For file mapping they are not carried through to the underlying file. Changes to the contents of the mapping are nevertheless private to each process.
The kernel accomplishes this by using the copy-on-write technique. This means that whenever a process attempts to modify the contents of a page, the kernel first creates a new, separate copy of that page for the process (and adjusts the process’s page tables).
For this reason, a MAP_PRIVATE mapping is sometimes referred to as a private, copy-on-write mapping. (Source: The Linux Programming Interface book)
这也是我想知道的具体细节。它直到最近几年的某个时候才出现,但我不确定是 GNU binutils 还是 glibc 动态链接器 (
ld-linux.so.2
) 造成了这一变化。起初我认为这是动态链接器创建的一种保护区,用于防止对库数据段的越界访问,但它这么大是没有意义的。它可能是 while 库文件的完整映射,以便动态链接器可以在将来的某个时间(可能在
dlopen
或dlsym
调用期间)再次读取它。访问通常不需要映射的 ELF 元数据。无论如何,它都是令人讨厌的膨胀,特别是在虚拟地址空间是宝贵资源的 32 位计算机上。它还会使内核页表膨胀,从而增加进程使用的内核空间资源。
PS 抱歉,这不是真正的答案。我知道这只是可能有助于找到答案的随机点点滴滴,但对于评论来说太长了。
This is something I've wondered about the specifics of too. It didn't appear until sometime in the last few years, but I'm unsure whether GNU binutils or the glibc dynamic linker (
ld-linux.so.2
) is responsible for the change.At first I thought it was a sort of guard region created by the dynamic linker to protect against out of bounds access to a library's data segment, but it makes no sense for it to be so large. It's possible that it's a complete map of the while library file so that the dynamic linker can make it readable again at some time in the future (perhaps during
dlopen
ordlsym
calls) to access ELF metadata that doesn't normally need to be mapped.In any case, it's nasty bloat, especially on 32-bit machines where virtual address space is a precious resource. It also bloats the kernel page tables, increasing the kernelspace resources used by a process.
P.S. Sorry this isn't really an answer. I know it's just random bits and pieces that might help lead to an answer, but it was way too long for a comment.