【问题标题】:Is it possible to skip an object from collecting by v8 GC?是否可以跳过 v8 GC 收集的对象?
【发布时间】:2018-01-12 15:01:50
【问题描述】:

我在内存中有很多长寿命的对象(~10GB),我绝对知道这些对象永远不会被 GC 收集。问题是标记-扫描 gc 操作需要很长时间(90 秒)来检查内存中的所有对象及其关系。我需要一些方法来跳过收集我的对象。

我尝试使用Persistent::MarkIndependent,但它对我不起作用。

【问题讨论】:

    标签: node.js v8 node.js-addon embedded-v8


    【解决方案1】:

    如果有问题的对象是通过 C++ 的句柄保持的引用,那么它们将不会被收集。但是,收集器仍然必须遍历它们,因为它必须找到对它们包含的其他对象的所有引用。如果它不这样做,那么您可能会得到悬空指针并导致 VM 崩溃。

    所以,不,至少按照你描述的方式,这是做不到的。 (另一方面,如果这些对象不能包含随机指针,因为它们是数组缓冲区或字符串,那么 GC 知道它不需要遍历它们,因此不应该存在性能问题。)

    【讨论】:

    • 感谢您的详细解释,但我仍然不明白如果我跳过我的对象及其关系遍历会发生什么,这些悬空指针如何使 VM 崩溃?当 gc 将我的对象从一个内存页面移动到另一个内存页面时是否会发生这种情况?
    • 每个没有被 GC 标记阶段访问的对象都被认为是死的并被回收。如果它不遍历您的大对象,它可能会因此收集一些其他对象正在引用并收集它们。那么你的对象就有了悬空引用。
    • 好的,最后一个问题,如果我将所有对象及其引用(对象、字符串、缓冲区)标记为已死并已收集,那么不会发生任何不好的事情吧?
    • 不确定你的意思。你不能将任何东西标记为死亡。 GC 只标记活动。所有它看不到的东西都被认为是死的,内存被重用了。
    • 我很好奇 GC 遍历器(标记扫描)中的一个条件,它决定在迭代所有根对象时是否进入图形对象。我想标记我所有选择的对象和它引用的对象的完整图形跳过标志(总是活 - 白色?)并且当 GC 执行时永远不要进入这个标记的对象。
    猜你喜欢
    • 1970-01-01
    • 2018-10-10
    • 1970-01-01
    • 1970-01-01
    • 2010-11-17
    • 1970-01-01
    • 1970-01-01
    • 2013-12-29
    相关资源
    最近更新 更多