我有一个关于ClassUnloadingWithConcurrentMark标志的问题,因为我在任何地方都找不到任何有用的帮助。如果我们使用G1GC默认设置为true(-XX:+ ClassUnloadingWithConcurrentMark)。如果我使用-XX:-ClassUnloadingWithConcurrentMark标志关闭G1并发标记后的类卸载哪里是类卸载执行那么(哪个阶段)?我读到某个地方,如果完全GC被激活,如果从未触发完整的GC会发生什么?我有很长的评论阶段的问题 - 在下面的示例中卸载花了超过3秒:
2015-06-08T08:09:16.318+0200: 572818.729: [GC remark 572818.729: [Finalize Marking, 0.0002590 secs] 572818.729: [GC ref-proc, 0.4479462 secs] 572819.177: [Unloading, 3.2004912 secs], 3.6499382 secs]
[Times: user=0.20 sys=0.08, real=3.64 secs]
使用-XX:-ClassUnloadingWithConcurrentMark对我来说减少类卸载时间会有用吗?我担心如果我将使用这个选项,如果类卸载永远不会发生,我会遇到更多问题(例如,外部存储异常......)。
编辑:如果我们使用-XX:+ ClassUnloadingWithConcurrentMark(默认选项)是每次GC备注阶段发生时触发的类卸载?在日志中我有一些GC与GC原因:元数据GC阈值,但其他人没有这个原因但卸载仍然发生在备注阶段。为什么会这样?
我担心如果我使用这个选项,我会遇到更多问题
为什么不为这些事情设置测试环境并自己测试?
无论如何,正如over here已经回答的那样,虚拟机将执行一些最后的沟通英雄(1-2个完整的GC,完整的软参考清除),以确保在投掷OOM之前情况不可恢复。
使用-XX:-ClassUnloadingWithConcurrentMark对我来说减少类卸载时间会有用吗?
它是否会减少它们,我不知道,可能不会。这就是你必须自己尝试的东西。但它可能会在很长一段时间内推迟不可避免的事情。
如果我们使用-XX:+ ClassUnloadingWithConcurrentMark(默认选项)是每次GC备注阶段发生时触发的类卸载?
是的,这是添加了JDK-8049421和旗帜再次与JDK-8051607关闭它。
您所要做的就是在openjdk bugtracker和/或hotspot-gc-dev邮件列表中搜索“类卸载”。这是所有公共信息。
您可以尝试的另一件事是设置-XX:MinMetaspaceFreeRatio=20 -XX:MaxMetaspaceFreeRatio=30
。这将更快地触发类卸载,并希望导致更短的循环。
G1在STW Remark阶段进行类卸载,这是默认行为。你不能阻止类卸载,因为这样做最终会导致“Out of Memory”错误。
缓解此问题的唯一方法是修改代码以停止使用动态类生成。