【问题标题】:How to track/find out which userdata are GC-ed at certain time?如何跟踪/找出哪些用户数据在特定时间被 GC-ed?
【发布时间】:2017-03-15 09:34:47
【问题描述】:

我在 LuaJIT 中编写了一个应用程序,使用第三方 GUI 框架(基于 FFI)+一些额外的自定义 FFI 调用。该应用程序在运行后不久的某个时候突然失去了部分功能,我很有信心这是因为一些未固定的对象被 GC-ed。我假设它们仅被 C 世界引用1,因此 Lua GC 认为它们未被引用并可以释放它们。问题是,我不知道在 Lua 端的众多用户数据中哪些未被引用(未固定)?

为了证实我的理论,我在禁用 GC 的情况下运行了该应用,通过:

collectgarbage 'stop'

你看,有了这条线,应用程序运行良好长时间超过了它之前被破坏的点。显然,这是一个丑陋的解决方法,我更喜欢启用 GC,并且应用程序仍然可以正常工作......

我想找出哪个未固定的对象(我假设是用户数据)被 GCed,所以我可以将它正确地固定在 Lua 端,以防止它过早地被 GCed。因此,我的问题是:

(如何)当我的应用失去功能时,我如何跟踪收集了哪些用户数据对象?

一个问题是,AFAIK,LuaJIT FFI 已经分配了自定义 __gc 处理程序,所以我不能添加自己的,因为每个对象只能有一个。无论如何,这个框架太大了,我无法尝试在其中的每个可以想象的地方添加__gc。此外,我已经通过从一些变量中删除local 来消除代码中“最明显可疑的”位置——从而使它们成为_G 的一部分,所以我假设不支持GC。 (或者这还不够?)

1 具体来说,WinAPI.

【问题讨论】:

    标签: luajit


    【解决方案1】:

    目前,我已经为我的一些对象添加了一些ffi.gc() 处理程序(打印一些容易看到的全大写消息),然后添加了一些急切的collectgarbage() 调用以尝试尽快触发问题:

    ffi.gc(foo, function()
        print '\n\nGC FOO !!!\n\n'
    end)
    
    [...]
    
    collectgarbage()
    

    确实,这暴露了一些我没想到的 GCing。具体来说,它让我发现了a note in luajit's FFI docs,这在我的情况下肯定是相关的:

    请注意,[C] 指针 [...] 不是 后跟垃圾收集器。所以例如如果将 cdata 数组分配给指针,则只要指针仍在使用中,就必须保持保存数组的 cdata 对象 [在 Lua 中]。

    【讨论】:

      猜你喜欢
      • 2018-03-21
      • 1970-01-01
      • 2020-12-22
      • 2020-10-20
      • 2023-03-09
      • 1970-01-01
      • 2012-08-16
      • 2012-04-29
      • 2011-05-14
      相关资源
      最近更新 更多