【问题标题】:mmap and hash table extension issue in glibcglibc 中的 mmap 和哈希表扩展问题
【发布时间】:2011-12-13 22:35:18
【问题描述】:

在一种检测堆损坏的方法中,我试图实现一个哈希表来保存有关分配内存的一些信息。这是在 glibc 内部完成的。当我们 malloc() 时,我们将地址和大小等信息放入哈希表中,而当我们 free() 时,我们再次在 glibc 的 free() 本身中释放相应的哈希表条目。

为了为哈希表分配内存,我已经映射了一些内存(避免使用 malloc,因为进程引起的堆损坏的可能性也会损坏我的哈希表)。 问题是进程可以请求的 malloc 数量没有限制,这要求我的哈希表是可扩展的。由于我的哈希表适用于数组索引,因此用于哈希表的内存需要是连续的,以便使用索引我们可以轻松地访问存储桶或记录。现在,当哈希表使用所有内存时,我需要再次执行“mmap”,以使该内存从前一个结束的地方开始。 mmap 的手册页说我们可以为 mmap 提供一个地址,这将作为内核在该地址映射虚拟内存的提示。对于哈希表,它看起来就像一块连续的内存。我想请教一下这种方法的可靠性以及使用这种方法的潜在缺陷是什么。

【问题讨论】:

    标签: malloc virtual hashtable glibc mmap


    【解决方案1】:

    如果是Linux,可以使用mremap

    如果您将哈希表编写为基于偏移量而不是绝对指针,则可以传递MREMAP_MAYMOVE 标志,而不必担心分配失败。 (好吧,直到你用尽虚拟内存为止。)

    【讨论】:

    • 非常感谢“Employed Russian”和“Nemo”的回答。我将探索 mremap()。看起来如果 mmap 是 malloc() 那么 mremap 是 realloc(),这是我迫切需要的。
    【解决方案2】:

    这种方法有多可靠

    MAP_FIXED 非常可靠:如果你要的内存可用,内核会给你。

    潜在的陷阱是什么

    很明显的一个:其他东西可能已经mmaped 进入您想要扩展的区域,而您输了。

    如果您为 64 位进程执行此操作,您可以 mmap 例如1TB 内存作为您的初始哈希表分配。只要您实际上没有访问它,这个mmap 实际上是免费的(成本),假设您正在执行MA_ANON 映射。

    顺便说一句,我希望你意识到你在这里重新发明了一辆自行车,因为许多现有的解决方案(例如 tcmalloc 和 jemalloc)已经提供了可能比你自己设计的更好的调试工具。

    【讨论】:

      猜你喜欢
      • 2016-01-02
      • 1970-01-01
      • 2020-09-03
      • 1970-01-01
      • 2020-12-21
      • 2011-10-07
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多