【问题标题】:Hierarchical Memory allocator library for C++C++ 的分层内存分配器库
【发布时间】:2010-10-24 13:14:15
【问题描述】:

我的应用程序主要是按组织的,所以我发现像APR memory pools 这样的东西是最好的方法。

在阅读关于 C++ placement new 帖子 hereherea more generic C allocation question 的 SO 时,我正在考虑按照一篇帖子中的建议手工制作分层池分配器,但在纯 NYI 传统中 我首先要问这样的东西是否已经存在。

它还可以具有能够将未使用的内存归还给操作系统的良好属性(因为分配可以使用mmap(MAP_ANON) 完成)或者可以是allocating from the stack,如建议的Ferrucico here

【问题讨论】:

  • 让我们回问一些事情。内存分配是否是您的应用程序中已通过分析证明的瓶颈?如果没有,为什么还要使用自定义分配器?
  • 分层内存池也有助于确保正确性,因为您可以消除一种内存泄漏源。
  • @florin 如果您正确使用 c++(容器、raii、...),发生泄漏的可能性非常低。我什至不记得我何时必须追踪最后一次泄漏。这是很久以前的事了。
  • 他们无助于“正确性”,他们在不正确的代码上使用了创可贴。
  • 其实这个应用是为了临时分配十几兆,然后再释放。因此,由于我不想在两次使用之间保持未使用状态,因此我首先想到了“手动”映射一些内存。但是在这里和那里读了一点之后,我认为拥有一个好的 API 会非常好,并促进这种使用模式的重用。这并不是要替换 整个 分配(RAII 非常适合一般用途)

标签: c++ memory-management hierarchical


【解决方案1】:

我知道另一个很好的分层内存分配器,但它在后台调用malloc

talloc 是一个基于分层池的内存分配器,带有析构函数。它是 Samba4 中使用的核心内存分配器,在 Samba4 开发的许多方面都产生了巨大的影响。

要开始使用talloc,我建议您阅读talloc guide

话虽如此,Glibc 的malloc 已经使用mmap(MAP_ANON) 分配大于mmap_threshold,您可以通过mallopt(M_MMAP_THRESHOLD, bytes) 设置。默认情况下是动态调整的

/*
  MMAP_THRESHOLD_MAX and _MIN are the bounds on the dynamically
  adjusted MMAP_THRESHOLD.
*/

#ifndef DEFAULT_MMAP_THRESHOLD_MIN
#define DEFAULT_MMAP_THRESHOLD_MIN (128 * 1024)
#endif

#ifndef DEFAULT_MMAP_THRESHOLD_MAX
  /* For 32-bit platforms we cannot increase the maximum mmap
     threshold much because it is also the minimum value for the
     maximum heap size and its alignment.  Going above 512k (i.e., 1M
     for new heaps) wastes too much address space.  */
# if __WORDSIZE == 32
#  define DEFAULT_MMAP_THRESHOLD_MAX (512 * 1024)
# else
#  define DEFAULT_MMAP_THRESHOLD_MAX (4 * 1024 * 1024 * sizeof(long))
# endif
#endif

小心降低它;默认情况下,将使用mmap 分配不超过#define DEFAULT_MMAP_MAX 65536 的块。这可以使用mallopt(M_MMAP_MAX, count) 进行更改,但使用多个mmaps 会产生开销。

环境变量MALLOC_MMAP_THRESHOLD_等也会设置这些选项。

很明显,malloc 分配给mmap 的内存会被munmap 释放。我不确定这些内容是否记录在 Glibc 源代码之外的任何地方,或者是否有任何兼容性保证。

【讨论】:

  • sizeof(talloc_chunk) 为 88 字节 (2.0.8)。分层结构中的每个叶子都有 88 个字节的权重。这是不可能的大事
【解决方案2】:

Dave Hanson 的C Interfaces and Implementations 有一个经过精心调整的单池分配器。您可以将它们链接在一起以创建一个分层分配器,这比从头开始滚动您自己的更简单。

确实有分析结果显示内存管理是一个重要的瓶颈,对吧?或者您只是想简化分配的 API?

【讨论】:

  • 你的第二个猜测是正确的,我只是想拥有一个比手工制作匿名 mmap 更好的 API。
  • 好的,在那种情况下,我非常喜欢 Hanson 的 API——值得一试。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-09-29
  • 1970-01-01
  • 1970-01-01
  • 2017-01-08
  • 2015-07-23
  • 1970-01-01
相关资源
最近更新 更多