c - 为什么我无法加载 0x201.000 以下的可执行文件(哪个线性地址空间在 linux 进程中被视为可用?它记录在哪里?)

标签 c linux memory-management

我在 linux 3.16.0-29-generic 上使用 gcc。 我设法使用 gcc -Wl,--section-start=.text=0x201000 选项指示 gcc 编译器设置为我正在编译的代码的加载地址 0x201.000(似乎ELF 的 header 需要 0x1000,所以我不能低于 0x201.000)。

而不是在其他测试中使用 mmap,我已经能够分配较低的地址,例如有时 0x10.000 从不从 0x0.000 到 0xF.000,并且总是所有其他地址达到和超过 0x800.000 )。 因此,我要问的是,从操作系统用户的角度来看,哪些地址可用于通用进程,以及为什么可执行文件不能加载到 0x200.000 以下?

它在哪里记录或我应该在哪里查看。 是否保证某些虚拟内存应该始终存在?在任何请求的地址(除非物理内存不足?)。 本质上,问题是“进程可用的线性内存是什么”,或者换句话说,提供给开发人员的逻辑模型是什么?

最佳答案

关于无法映射 0x10.000 以下的地址,答案在“https://wiki.ubuntu.com/Security/Features”中。

0地址保护

由于内核和用户空间共享虚拟内存地址,因此需要保护“NULL”内存空间,以便用户空间 mmap 的内存不能从地址 0 开始,从而阻止“NULL 取消引用”内核攻击。这对于 2.6.22 内核是可能的,并且是通过“mmap_min_addr”sysctl 设置实现的。从 Ubuntu 9.04 开始,内核中内置了 mmap_min_addr 设置。 (x86 为 64k,ARM 为 32k。)

我们可以使用指令 sudo sysctl -w vm.mmap_min_addr=0

来改变“mmap_min_addr”

所以答案是整个地址空间无一异常(exception)地可用(线性地址)。

关于c - 为什么我无法加载 0x201.000 以下的可执行文件(哪个线性地址空间在 linux 进程中被视为可用?它记录在哪里?),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28053302/

相关文章:

c - 向 C 程序添加插件

linux - 使用 gdbus-codegen 进行 dbus 方法调用,服务器端工作但客户端的响应字符串始终为 NULL

php - 发送 POST 请求 wget

Linux 内核内存泄漏目前已修复

c - 如何使用 C 和 WinAPI 将包含特殊字符的文本复制到剪贴板?

c - C while 循环和轮询中的电源效率

C - 获取字符串前 n 个字符后的子字符串

linux - 这个sed有什么问题?

c - 并行操作执行时间因分配动态内存与静态内存而异

c++ - delete[] 运算符是否处理通过指针返回的动态分配的内存?