【问题标题】:Linux reserved heap sizeLinux 保留堆大小
【发布时间】:2012-09-11 13:27:48
【问题描述】:

我注意到在 2.6.32 MIPS 内核上,内存布局总是相同的。对于大多数进程(或至少我研究过的进程)来说,这是一个程序的堆从0x10146000 开始。还有另一个相似之处是/lib32/ld-2.9.so 总是从2aaa8000 开始。

所以基本上堆在虚拟内存中保留了所有这些大小,我想修改它,因为似乎在某些时候我用完了虚拟内存(在地址空间的其余部分)mmap 会尽管堆只有几 MB,但没有尝试在上述空间中映射就失败了。有人现在内核在哪里设置这个地址吗?

【问题讨论】:

  • 在您的进程上运行 pmap -x <pid> 以查看是否有任何空闲的虚拟地址空间区域及其大小。
  • 好吧,pmap/proc/pid/maps 提供的内容并没有太大区别。整个想法是修改参数,以便堆没有那么大的空间保留(几乎 400mb)
  • 堆通常使用brksbrk 调用分配。你能strace你的进程看看它是否调用了这些吗?
  • brk()sbrk() 通常会分配 /proc/pid/maps 中未报告的内存。所以基本上它扩展了我想要缩小的那个空间中的 [heap] 部分
  • 这正是我所说的。但这不是我要找的。我不想使用brk()/sbrk() 我想限制操作系统内核为将来的brk() 调用保留的第一个间隙。

标签: linux linux-kernel kernel


【解决方案1】:

如果你查看arch/mips/mm/mmap.c你会发现在Linux中有两种放置内存的方式,选择哪种方式取决于mmap_is_legacy的返回值,而这又取决于你是否启用了无限堆栈(强制旧模式)以及您的二进制文件是否编译了标志PT_GNU_STACK(没有此设置强制兼容模式)。新布局是在 2.6.7 中添加的,并在 http://lwn.net/Articles/90311/ 中进行了描述。

简单地说,旧布局如下所示:

| CODE ---- | HEAP ----------> | MMAP ------>  | <-------- STACK |
| 0GB       |                  | 2GB/3         |             2GB |

新布局如下所示:

| CODE ---- | HEAP ----------> | <------------- MMAP | --- STACK |
| 0GB       |                  |             2GB-8MB |       2GB |

请注意,在旧布局中,堆和 mmap 区域之间的划分是固定的,而在新区域中它是灵活的。您可能正在运行缺少新模式的旧内核,或者您正在以我之前描述的兼容模式运行。

请注意,您找到的地址 0x2AAA8000 大约是 2GB/3(libc 是首先要映射的),而 0x10146000 大约是 256MB(这足以容纳您的程序的代码、数据和未初始化的数据段)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-01-15
    • 2015-04-25
    • 2011-05-03
    • 2019-08-11
    • 2014-07-14
    • 2013-11-15
    • 2011-03-30
    相关资源
    最近更新 更多