Memory management Erlang中的垃圾收集和内存管理

Memory management Erlang中的垃圾收集和内存管理,memory-management,garbage-collection,erlang,Memory Management,Garbage Collection,Erlang,我想了解有关Erlang/OTP中垃圾收集(GC)和内存管理的技术细节 但是,我找不到关于它和它的文件 我在网上找到了一些关于GC的文章,内容非常笼统,例如使用了什么垃圾收集算法。该算法的参考文献:由Joe Armstrong和Robert Virding在 1995年(在CiteSeerX) 摘要: 传统的标记清除垃圾收集算法在算法的标记阶段结束之前不允许回收数据。对于不允许破坏性操作的语言类,我们可以安排堆中的所有指针始终向后指向“较旧”的数据。在本文中,我们提出了一个简单的方案,用一个通过

我想了解有关Erlang/OTP中垃圾收集(GC)和内存管理的技术细节

但是,我找不到关于它和它的文件


我在网上找到了一些关于GC的文章,内容非常笼统,例如使用了什么垃圾收集算法。

该算法的参考文献:由Joe Armstrong和Robert Virding在 1995年(在CiteSeerX)

摘要:

传统的标记清除垃圾收集算法在算法的标记阶段结束之前不允许回收数据。对于不允许破坏性操作的语言类,我们可以安排堆中的所有指针始终向后指向“较旧”的数据。在本文中,我们提出了一个简单的方案,用一个通过标记扫描采集器回收此类语言类的数据。我们还展示了如何修改简单方案,以便以增量方式进行收集(使其适合实时收集)。接下来,我们将展示如何修改收集器以进行分代垃圾收集,以及如何将该方案用于具有并发进程的语言


我不知道你的背景,但是除了jj1bdx已经指出的论文,你也可以给我一个机会

BTW,如果您想监视Erlang中的内存使用,将其与C++进行比较,您可以查看:


希望这有帮助

Erlang有一些属性,使GC实际上非常简单

1-每个变量都是不可变的,因此变量永远不能指向其后创建的值

2-值在Erlang进程之间复制,因此进程中引用的内存几乎总是完全隔离的

这两种方法(尤其是后者)都极大地限制了GC在收集过程中必须扫描的堆的数量

Erlang使用复制GC。在GC期间,进程停止,然后将活动指针从from空间复制到to空间。我忘记了确切的百分比,但是如果在一次收集过程中只能收集25%的堆,则堆会增加,如果可以收集75%的进程堆,则堆会减少。当进程的堆变满时,将触发集合

唯一的例外是当涉及到发送到另一个进程的大值时。这些将被复制到共享空间中,并进行引用计数。收集对共享对象的引用时,计数会减少,当该计数为0时,对象将被释放。不会尝试处理共享堆中的碎片

一个有趣的结果是,对于共享对象,共享对象的大小不会影响进程堆的计算大小,只有引用的大小会影响。这意味着,如果您有很多大型共享对象,那么在触发GC之前,您的VM可能会耗尽内存


如果这是Jesper Wilhelmsson在EUC2012上的演讲,那么大多数情况下都是这样。

要对事物进行分类,让我们定义内存布局,然后讨论GC是如何工作的

内存布局 在Erlang中,每个执行线程称为一个进程。每个进程都有自己的内存,内存布局由三部分组成:进程控制块堆栈

  • PCB:过程控制块保存诸如过程标识符(PID)、当前状态(运行、等待)、其注册名称和其他此类信息

  • 堆栈:它是一个向下增长的内存区域,用于保存传入和传出参数、返回地址、局部变量和用于计算表达式的临时空间

  • 堆:它是一个向上增长的内存区域,用于存放进程邮箱消息和复合术语。大于64字节的二进制项不存储在进程专用堆中。它们存储在一个大型共享堆中,所有进程都可以访问该堆


垃圾收集 目前,Erlang使用一个分代的垃圾收集,该垃圾收集在每个Erlang进程私有堆内独立运行,并且对全局共享堆执行一个引用计数垃圾收集

  • 私有堆GC:它是分代的,因此将堆分为两个部分:年轻一代和老一代。还有两种收集策略;第二代(小调)和第二代(大调)。分代GC只收集年轻堆,而fullsweep同时收集年轻堆和旧堆

  • 共享堆GC:这是引用计数。共享堆(Refc)中的每个对象都有一个由其他对象(ProcBin)持有的引用计数器,这些对象存储在Erlang进程的私有堆中。如果对象的引用计数器达到零,则该对象将无法访问并将被销毁



要获得更多细节和性能提示,只需看看我的文章,这是答案的来源:

一个
大值有多大
?我猜是二进制文件?(>64字节)感谢您添加摘要!