ELF64 / x86_64和内存映射段的起始地址(用于共享对象)

我编写了几个程序,发现当在64位编译时,内存映射段(例如共享对象和共享内存保存)总是位于7f9aca84a000-7fff88400000左右但从未完全相同.

我想知道x86_64架构(ELF64)上的内存段是否有固定的起始地址,或者该段的最大和最小范围是多少?

这就是为什么我问这个问题.我们正在将系统从Tru64 UNIX迁移到Linux.该系统使用IPC Sys V共享内存的复杂固定内存映射,并使用链表在该段内从结构转到另一个.由于这段代码的大小和复杂性,以及我们手头有限的时间,我们正在尝试找到一种可靠的方法来修复共享内存的开始(有效地使用带有指定地址的shmat来附加段).
对于64位,虚拟地址空间是如此巨大(48位有效可能的地址),选择“安全”固定地址比32位更容易,风险更小.

最佳答案
x86-64内存映射布局在arch/x86/mm/mmap.c中定义.如您所见,有两种策略:自上而下和自下而上.

自上而下的分配是认的.它从堆栈最大范围以下128MB开始(由堆栈rlimit定义),由随机偏移量调整,然后从内存中向下分配后续映射.

自下而上的分配是后备.它用于以下任何一种情况:

>堆栈限制是无限的;
>该过程具有ADDR_COMPAT_LAYOUT个性设置;要么
> vm.legacy_va_layout sysctl非零.

在自下而上分配下,映射区域被逐渐分配更高的地址,从TASK_SIZE / 3开始,由随机偏移量调整. x86-64上的TASK_SIZE为0x800000000000,因此自下而上的分配将从0x2AAAAAAAAAAA开始.

我会为你的固定映射建议一个合适的漏洞,在任一分配策略下都应该是2 * TASK_SIZE / 3 – 我会使用0x500000000000.

相关文章

在Linux上编写运行C语言程序,经常会遇到程序崩溃、卡死等异...
git使用小结很多人可能和我一样,起初对git是一无所知的。我...
1. 操作系统环境、安装包准备 宿主机:Max OSX 10.10.5 虚拟...
因为业务系统需求,需要对web服务作nginx代理,在不断的尝试...
Linux模块机制浅析 Linux允许用户通过插入模块,实现干预内核...
一、Hadoop HA的Web页面访问 Hadoop开启HA后,会同时存在两个...