The dynamic loader uses mmap(2)
with MAP_PRIVATE and appropriate permissions. You can see what it does exactly by running a command from strace -e file,mmap
. For instance:
strace -e file,mmap ls
All the magic comes from mmap(2)
. mmap(2)
creates mappings in the calling process, they are usually backed either by a file or by swap (anonymous mappings). In a file-backed mapping, MAP_PRIVATE means that writes to the memory don't update the file, and cause that page to be backed by swap from that point on (copy-on-write).
The dynamic loader gets the info it needs from ELF's program headers, which you can view with:
readelf -l libfoo.so
From these, the dynamic loader determines what to map as code, read-only data, data and bss (zero-filled segment with zero size in file, non-zero size in memory, and a name only matched in crypticness by Lisp's car and cdr).
So, in fact, code and also data is shared, until a write causes copy-on-write. That is why marking constant data as constant is a potentially important space optimization (see DSO howto).
You can get more info on the mmap(2)
manpage, and in Documentation/nommu-mmap.txt (the MMU case, no-MMU is for embedded devices, like ADSL routers and the Nintendo DS).
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…