`[stack]`,`[vdso]`和`[vsyscall]`mmaps来自哪里?

And*_*zos 4 linux x86 linux-kernel vdso

考虑以下针对Linux x86_64的程序:

inf.s:

    .global _start
    .text
_start:
    jmp _start
Run Code Online (Sandbox Code Playgroud)

这基本上是一个无限循环.

如果我链接并删除它,我得到一个ELF可执行文件:

$ gcc -nostdlib inf.s

$ ./a.out &

[1] 15862

$ cat /proc/15862/maps

00400000-00401000 r-xp 00000000 fc:00 11404632           a.out
7fffacdb8000-7fffacdd9000 rwxp 00000000 00:00 0          [stack]
7fffacddd000-7fffacdde000 r-xp 00000000 00:00 0          [vdso]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0  [vsyscall]
Run Code Online (Sandbox Code Playgroud)

在ELF可执行文件中,第一个程序头LOAD包含占上述mmaps(a.out)中第一个条目的映射.(即使我删除每个,但是这个头和代码都会观察到相同的映射.) execve(2)调用ELF处理程序,fs/binfmt_elf.c其中读取程序头并在文件上调用mmap.

我不明白的是其他三个来自哪里(stack,vdso,vsyscall).它们未在ELF文件中提及,因此Linux内核必须默认设置这三个"匿名"或"特殊"映射.

我的问题是内核代码(或如何)Linux内核创建其他三个映射?他们是否继承了这个人?我似乎无法看到fs/exec.c它们的创建地点.

Tom*_*omH 6

它们是在将文件加载到内存中以运行它时由内核自动创建的.

精确的控制流程[vdso]并且[vsyscall]很难遵循,因为根据内核是32位还是64位,有一些函数名称的定义和重新定义,因为一些相关的例程包括:

  • load_elf_binaryfs/binfmt_elf.c哪个电话arch_setup_additional_pages
  • arch_setup_additional_pagesarch/x86/vdso/vma.c
  • arch_setup_additional_pagesarch/x86/vdso/vdso32-setup.c

所述[stack]映射不是ELF特定,并创建由__bprm_mm_initfs/exec.c其由称为execve代码它调用格式特定装载机之前.