[英]Hotspot JVM - G1GC Heap resizing issue
我最近在测试具有相对较高并发负载的演示应用程序。 该应用程序是一个Java应用程序,并在Hotspot JVM(1.8.0_111)上运行。
使用4G堆和并行吞吐量收集器,我可以获得大约400 TPS的最大吞吐量。 吞吐量图表(作为负载的函数)如下所示。
因为Oracle建议将G1GC用于大于4G的堆大小,所以我想尝试G1,看看这是否有益于我的应用程序吞吐量。
令我惊讶的是,在G1GC中,我看到了以下吞吐量趋势。
我真的很惊讶,决定深入了解这里发生的事情。 这是我发现的。
我看到,最初,在4G堆中,1.5G被分配给旧的gen区域,2.5G被分配给eden区域。 但是随着时间的推移和旧的gen不再适合1.5G,堆会被调整大小。 这似乎是无害的。 但问题似乎在于调整大小的方式。
所有的4G现在都分配给了旧的地区,而且几乎没有分配给伊甸园地区。 现在,当需要将某些内容分配给eden时,堆会再次调整大小。 这成为新常态,其中堆重复调整大小,导致应用程序的巨大性能成本。
有没有人在G1GC之前注意到这一点? 是否有任何建议可以协商这个问题?
下面是带有JVM选项的启动命令行。
java -server -Xms4096m -Xmx4096m -XX:MetaspaceSize=100m -XX:MaxMetaspaceSize=100m -XX:MaxDirectMemorySize=512m -XX:MinMetaspaceFreeRatio=0 -XX:MaxMetaspaceFreeRatio=100 -XX:CompressedClassSpaceSize=20m -XX:InitialCodeCacheSize=50m -XX:ReservedCodeCacheSize=50m -XX:+AlwaysPreTouch -XX:+DisableExplicitGC -XX:+PrintGCDetails -XX:+PrintGCDateStamps -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/var/tmp -Xloggc:/servers/logs/gc.log.2017-01-05-085234 -Djava.awt.headless=true -XX:+UnlockCommercialFeatures -XX:+FlightRecorder -Dio.netty.leakDetectionLevel=simple -XX:MaxDirectMemorySize=512m -Dadmin.connectors.http.port=9000 -Dproxy.connectors.http.port=8080 -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port=8654 -Dcom.sun.management.jmxremote.local.only=false -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false -server -cp ...
JVM选项:
-server
-Xms4096m
-Xmx4096m
-XX:MetaspaceSize=100m
-XX:MaxMetaspaceSize=100m
-XX:MaxDirectMemorySize=512m
-XX:MinMetaspaceFreeRatio=0
-XX:MaxMetaspaceFreeRatio=100
-XX:CompressedClassSpaceSize=20m
-XX:InitialCodeCacheSize=50m
-XX:ReservedCodeCacheSize=50m
-XX:+AlwaysPreTouch
-XX:+DisableExplicitGC
-XX:+PrintGCDetails
-XX:+PrintGCDateStamps
-XX:+HeapDumpOnOutOfMemoryError
-XX:HeapDumpPath=/var/tmp
-Xloggc:/servers/logs/gc.log.2017-01-05-085234
-Djava.awt.headless=true
-XX:+UnlockCommercialFeatures
-XX:+FlightRecorder
-Dio.netty.leakDetectionLevel=simple
-XX:MaxDirectMemorySize=512m
-Dadmin.connectors.http.port=9000
-Dproxy.connectors.http.port=8080
-Dcom.sun.management.jmxremote
-Dcom.sun.management.jmxremote.port=8654
-Dcom.sun.management.jmxremote.local.only=false
-Dcom.sun.management.jmxremote.authenticate=false
-Dcom.sun.management.jmxremote.ssl=false
-server
-cp ...
请在这里找到gc日志
似乎有以下两种GC原因:
巨大的分配需要旧的空间,空间的耗尽推动了年轻人的规模。 他们基本上是相互竞争的。
看起来你分配了很多大量的物体(> 1/2 G1区域大小)比IHOP发起的并发周期更快收集它们。
您可以尝试增加区域大小。 如果它们是大型原始阵列(即不是参考arrasy),那么实验性的急切回收功能也可能有所帮助。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.