【问题标题】:Why does C manage the heap, instead of the operating system?为什么 C 管理堆而不是操作系统?
【发布时间】:2018-04-26 06:30:21
【问题描述】:

也就是说,为什么free()不只是将内存返回给操作系统,而malloc只是向操作系统请求内存?

这包含三个密切相关的问题:

  • 为什么C 需要管理自己的堆? (是因为操作系统只允许您分配和释放最小大小的连续内存吗?)
  • 假设我在括号中写的是真的,为什么会这样?
  • 此问题是否会影响操作系统本身,使其无法将内存块分配给任何正在运行的进程?

【问题讨论】:

  • 首先,运行一个分析器并计算由简单的东西发出的malloc()free() 调用的数量。然后意识到每个进程最终都会将它们作为系统调用......
  • 操作系统是全国分销商,只处理大请求。您的程序(用C 或其他方式编写)是您当地的超市,可以为您提供少量内存。
  • 这完全取决于操作系统。 [c] 标签中最不流行的标签实际上实现了自己的堆,而 CRT 只是直接使用它。这不是 Unix 的方式,在嵌入式系统中变得相当模糊。
  • 首先,C 代码并不总是在操作系统之上运行。
  • 假设存在操作系统是错误的。我使用 C 语言执行了许多在裸机上运行的软件项目。

标签: c heap-memory dynamic-memory-allocation virtual-memory


【解决方案1】:

从其他答案中,这就是我收集到的答案。

大多数操作系统仅将内存分配给固定大小的进程,称为页。当一个进程将内存返回给操作系统时,它只能在页面中这样做。页面是固定大小的内存序列。页面的起点和终点是固定的,因此即使您有足够大的可用内存,也无法将其返回给操作系统,除非它位于页面的起点和终点之间。

另一方面,您可以想象没有操作系统(或者操作系统从它自己的堆中为程序分配内存)。这有助于我更好地理解事情,因为操作系统妨碍了我的直觉,因为看起来释放的内存好像掉进了一个黑洞,而分配的内存是从一个类似的黑洞中出来的。如果没有任何操作系统,计算机中的所有内存都可以被想象为属于一个大的单元序列。如果您在计算机中分配所有可用内存,然后开始释放一些内存,那么您可能无法找到足够大的连续内存块来满足 malloc 请求。

【讨论】:

    【解决方案2】:

    为什么 C 需要管理自己的堆? (是不是因为操作系统只允许你分配和释放最小大小的连续内存?)

    操作系统以页为单位管理内存。分配和释放页面的开销很大。 C 中的大多数分配往往比页面大小小得多。

    【讨论】:

      【解决方案3】:

      实际上它是留给实现的。问题:

      为什么 free() 不只是将内存返回给操作系统,以及 malloc 只是向操作系统请求内存?

      是错误的,因为没有什么能阻止实现。所以这个问题没有答案 - 每个实现都可能不同(它只需要符合标准)

      【讨论】:

        【解决方案4】:
        1. malloc 本身就是一个 C 方法。您正在使用为您提供它的标准库,但最终,它是 C 代码,就像您的一样。
        2. 在某些操作系统中,您只能从操作系统获取页面大小的内存(使用mmap)。这对于您的常规数据结构来说太大了。
        3. 每次需要内存时都进行系统调用太昂贵了。

        【讨论】:

        • 第 2 点不适用于所有操作系统。
        • @MichaelWalz 有趣 - 你知道这不正确的例子吗?我将如何在这些操作系统中分配内存?我相信 mmap 正在处理页面?
        • @mrks Windows 就是一个例子。或者可能是没有 MMU 的微控制器上的自定义环境。
        • 好的,因为问题中的“malloc”,我只考虑POSIX。对于严格遵守 POSIX 的操作系统是否正确?
        • @mrks POSIX 兼容不排除扩展 API,因此不一定。
        【解决方案5】:

        为什么 C 需要管理自己的堆?

        实际上并没有指定它需要,但它需要按照标准中描述的方式实现malloc() 和朋友。因此,如果操作系统已经提供了这样的接口,那么 C 实现可以只提供一个微小的包装器。

        是因为操作系统只允许您分配和释放最小大小的连续内存吗?如果这是真的,原因是什么?

        是的。典型的操作系统将管理 paged 内存并映射或取消映射进程的整个内存页面。 可以“分页”的内存单元取决于硬件架构。您可能想阅读有关memory management units (MMU) 工作原理的一些详细信息。在没有 MMU 的架构上,操作系统可能什么都不做,而 C 实现只会满足来自物理地址空间中固定位置的 malloc() 请求。

        【讨论】:

          猜你喜欢
          • 2012-05-04
          • 1970-01-01
          • 2012-10-19
          • 2020-07-04
          • 2014-05-27
          • 2021-06-02
          • 1970-01-01
          • 1970-01-01
          • 2016-07-12
          相关资源
          最近更新 更多