【发布时间】:2014-10-18 19:08:43
【问题描述】:
我在 Ruby MRI 1.9.3(作为 Rails 3.2.13 的一部分)环境中运行 resque-scheduler,不知何故发生了内存泄漏,这让我抓狂。它不会发生在我的 MacOS 开发机器上(在完全相同相同的环境中运行),但会发生在我们在 AWS 上运行的每台 64 位 Ubuntu 12.04.4 LTS 机器上。
每次通过 resque-scheduler 主循环时,堆都会不断增长 - 尽管堆的已使用部分保持不变。此处是 GC.stat 输出的示例,GC.stat 在 GC.start 调用之后立即调用。
GC.stat: {:count=>151, :heap_used=>2424, :heap_length=>4361, :heap_increment=>1937, :heap_live_num=>840924, :heap_free_num=>145061, :heap_final_num=>0}
GC.stat: {:count=>155, :heap_used=>2428, :heap_length=>4368, :heap_increment=>1940, :heap_live_num=>840924, :heap_free_num=>146688, :heap_final_num=>0}
GC.stat: {:count=>159, :heap_used=>2432, :heap_length=>4375, :heap_increment=>1943, :heap_live_num=>840924, :heap_free_num=>148121, :heap_final_num=>0}
GC.stat: {:count=>164, :heap_used=>2437, :heap_length=>4384, :heap_increment=>1947, :heap_live_num=>840924, :heap_free_num=>150347, :heap_final_num=>0}
GC.stat: {:count=>170, :heap_used=>2443, :heap_length=>4395, :heap_increment=>1952, :heap_live_num=>840924, :heap_free_num=>152593, :heap_final_num=>0}
GC.stat: {:count=>176, :heap_used=>2449, :heap_length=>4406, :heap_increment=>1957, :heap_live_num=>840924, :heap_free_num=>155230, :heap_final_num=>0}
GC.stat: {:count=>181, :heap_used=>2454, :heap_length=>4415, :heap_increment=>1961, :heap_live_num=>840924, :heap_free_num=>157266, :heap_final_num=>0}
GC.stat: {:count=>191, :heap_used=>2464, :heap_length=>4433, :heap_increment=>1969, :heap_live_num=>840924, :heap_free_num=>161334, :heap_final_num=>0}
作为一个单独的问题,RUBY_FREE_MIN、RUBY_HEAP_MIN_SLOTS、RUBY_GC_MALLOC_LIMIT 环境变量似乎对 1.9.3 GC 的行为方式没有任何影响。随着 heap_increment 的增长,问题仅仅是因为一些硬编码设置,GC 认为它需要不断增加堆大小吗?
[编辑]
再看一遍,我可以看到 heap_used 正在上升。但是如果我考虑与 GC.stat 一起打印的 ObjectSpace.count_objects,那就没有意义了:
GC.stat: {:count=>172, :heap_used=>2438, :heap_length=>4386, :heap_increment=>1948, :heap_live_num=>841064, :heap_free_num=>150208, :heap_final_num=>0}
ObjectSpace.count_objects: {:TOTAL=>991767, :FREE=>92284, :T_OBJECT=>45577, :T_CLASS=>10048, :T_MODULE=>2452, :T_FLOAT=>1038, :T_STRING=>449766, :T_REGEXP=>4537, :T_ARRAY=>213156, :T_HASH=>17273, :T_STRUCT=>591, :T_BIGNUM=>1605, :T_FILE=>6, :T_DATA=>91099, :T_MATCH=>17, :T_COMPLEX=>1, :T_RATIONAL=>436, :T_NODE=>57652, :T_ICLASS=>4229}
GC.stat: {:count=>173, :heap_used=>2439, :heap_length=>4388, :heap_increment=>1949, :heap_live_num=>840996, :heap_free_num=>150016, :heap_final_num=>0}
ObjectSpace.count_objects: {:TOTAL=>992173, :FREE=>150621, :T_OBJECT=>45073, :T_CLASS=>9922, :T_MODULE=>2452, :T_FLOAT=>636, :T_STRING=>403784, :T_REGEXP=>4502, :T_ARRAY=>207916, :T_HASH=>15856, :T_STRUCT=>591, :T_BIGNUM=>14, :T_FILE=>6, :T_DATA=>89977, :T_MATCH=>17, :T_COMPLEX=>1, :T_RATIONAL=>63, :T_NODE=>56639, :T_ICLASS=>4103}
当所有对象计数下降时,heap_used 是如何上升的?
【问题讨论】:
标签: ruby memory-leaks garbage-collection ruby-1.9.3