JVM OutOfMemory 错误“死亡螺旋”(不是内存泄漏)
我们最近将许多应用程序从在RedHat linux JDK1.6.0_03下运行迁移到Solaris 10u8 JDK1.6.0_16(更高规格的机器),我们注意到一个似乎相当紧迫的问题:在某些负载下,我们的JVM会让自己陷入“死亡螺旋”并最终耗尽内存。注意事项:
- 这不是内存泄漏的情况。这些应用程序运行良好(在一种情况下运行了3年以上),并且在任何情况下都不确定内存不足的错误。有时应用程序工作,有时它们不起作用
- 这不是我们移动到64位VM - 我们仍然运行32位
- 在一种情况下,在1.6.0_18上使用最新的G1垃圾回收器似乎已经解决了这个问题。在另一个中,移回1.6.0_03已经奏效了
- 有时我们的应用程序会因热点错误而崩溃
SIGSEGV
- 这影响了用Java和Scala编写的应用程序。
最重要的一点是:这种行为表现在那些突然获得大量数据(通常通过TCP)的应用程序中。就好像VM决定继续添加更多数据(可能将其推进到TG)而不是在“newspace”上运行GC,直到它意识到它必须执行完整的GC,然后,尽管VM中几乎所有内容都是垃圾,但它以某种方式决定不收集它!
这听起来很疯狂,但我只是不明白它是什么。否则你怎么能解释一个应用程序,一分钟倒下,最大堆为1Gb,下一个工作得很好(当应用程序做完全相同的事情时,永远不会大约256M)
所以我的问题是:
- 有没有人观察到这种行为?
- 有没有人对我如何调试JVM本身(而不是我的应用程序)有任何建议?如何证明这是 VM 问题?
- 是否有任何 VM 专家论坛,我可以在其中询问 VM 的作者(假设他们不在 SO 上)?(我们没有支持合同)
- 如果这是最新版本的 VM 中的一个错误,为什么没有其他人注意到它?