JVM in-depth good article, CMS collector and GC log analysis and positioning problem detailed explanation

Insert picture description here
CMS collector combat

The latest real interview questions for first-line Internet companies collected in 2020 (all organized into documents), there are a lot of dry goods, including detailed explanations of netty, spring, thread, spring cloud, etc., there are also detailed learning plans, interview questions, etc. I feel that I am in the interview This section is very clear: to get the interview information, just: click here to get it!!! Password: CSDNInsert picture description here

The actual combat begins, are you ready?

Insert picture description here
Insert picture description here

Simulated business scenario code:

@RestController
public class IndexController {
    
    
/***
 * 存 big 对象
 * @return
 */
@GetMapping("/put")
public String process() {
    
    
   ArrayList<User> users = queryUsers();
   for (User user:users){
    
    
      //TODO 业务操作
   }
   return "ok";
}
private ArrayList<User> queryUsers() {
    
    
   ArrayList<User> users = new ArrayList<>();
   for (int i = 0; i < 50000; i++) {
    
    
      users.add(new User(i, "java2b"));
   }
   return users;
}
}
public class User {
    
    

   private int id;
   private String name;
   private byte[] data;

   public User(int id, String name) {
    
    
      this.id = id;
      this.name = name;
      data=new byte[1 * 128 * 1024];
   }
}

Output collector information:

/***
 * 打印 jvm 信息
 * @return
 */
@GetMapping("/info")
public String info() {
    
    
   List<GarbageCollectorMXBean> garbages = ManagementFactory.getGarbageCollectorMXBeans();
   StringBuilder stringBuilder = new StringBuilder();
   for (GarbageCollectorMXBean garbage : garbages) {
    
    
      stringBuilder.append("垃圾收集器:名称=" + garbage.getName() + ",收集=" + garbage.getCollectionCount() + ",总花费时间="
              + garbage.getCollectionTime());
      // + ",内存区名称=" + Arrays.deepToString(garbage.getMemoryPoolNames()));
      stringBuilder.append("\r\n");
   }
   MemoryMXBean memory = ManagementFactory.getMemoryMXBean();
   MemoryUsage headMemory = memory.getHeapMemoryUsage();
   long MB = 1024 * 1024;
   stringBuilder.append("head 堆:");
   stringBuilder.append("\t 初始(M):" + headMemory.getInit() / MB);
   stringBuilder.append("\t 最大(上限)(M):" + headMemory.getMax() / MB);
   stringBuilder.append("\t 当前(已使用)(M):" + headMemory.getUsed() / MB);
   stringBuilder.append("\t 提交的内存(已申请)(M):" + headMemory.getCommitted() / MB);
   stringBuilder.append("\t 使用率:" + headMemory.getUsed() * 100 / headMemory.getCommitted() + "%");
   return stringBuilder.toString();
}

Generating jar package deployed to the server
startup parameters:

 java -Xms256m -Xmx256m -verbose:gc -Xloggc:/root/jvm/gc-cms.log -XX:+UseConcMarkSweepGC -XX:+HeapDumpOnOutOfMemoryError -XX:+PrintHeapAtGC -XX:HeapDumpPath=/root/jvm/dump.hprof -XX:+PrintGCApplicationStoppedTime -XX:+PrintGCTimeStamps -XX:+PrintCommandLineFlags -XX:+PrintFlagsFinal -XX:+PrintGCDetails -XX:+UseCMSCompactAtFullCollection -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.port=6666 -Djava.rmi.server.hostname=192.168.0.31 -jar /root/jvm/jvm-web-0.0.1-SNAPSHOT.jar > catalina.out &

Here we need to insert the meaning of JVM parameters.

Detailed JVM parameters:

JVM parameter meaning

-XX:-CMSPrecleaningEnabled
does not perform precleaning . Those who have passed our previous articles know that CMS will have a precleaning job during the period of concurrent marking and remarking , and this pass will try within 5 seconds Wait for YGC to come. In order not to spend a lot of time in the later re-marking phase to mark the new generation of objects.

-XX:+UseConcMarkSweepGC
This parameter will start the CMS collector. The default new generation is ParNew, you can also set Serial as the new generation collector. This parameter is equivalent to -Xconcgc.

-XX:ParallelGCThreads
is a parallel processor, of course you can also specify the number of threads. The default number of concurrent threads is: (ParallelGCThreads + 3)/4).
-XX:ConcGCThreads
or -XX:ParallelCMSThreads; In addition to the way of setting threads above, you can also manually set the number of concurrent CMS threads through either of these two parameters

-XX:CMSInitiatingOccupancyFraction
Because the CMS collector is not exclusive, the application is still working during garbage collection, so you need to leave enough memory for the application, otherwise it will trigger FGC. And when does CMS GC run? It can be set by this parameter, which represents the memory usage percentage of the old generation. When this threshold is reached, CMS will be executed. The default is 68. If the memory of the old generation grows rapidly, it is recommended to lower the threshold to avoid FGC. If the growth is slow, you can increase the threshold to reduce the number of CMS GCs. Improve throughput.

-XX:+UseCMSCompactAtFullCollection
Because CMS uses mark cleaning algorithm, memory fragmentation cannot be avoided. This parameter specifies a defragmentation after each CMS.

-XX:CMSFullGCsBeforeCompaction Since each defragmentation will affect the performance, you can use this parameter to set how many times CMS will be defragmented, which is memory compression.

-XX:+CMSClassUnloadingEnabled
allows recycling of class metadata.

-XX:CMSInitiatingPermOccupancyFraction

When the permanent area occupancy rate reaches this percentage, start CMS recycling (provided that -XX:+CMSClassUnloadingEnabled is activated).

-XX:UseCMSInitiatingOccupancyOnly

Indicates that CMS recovery is only performed when the threshold is reached.

XX:CMSWaitDuration=2000
Because the CMS GC condition is relatively simple, the JVM has a thread to scan the Old area regularly. The time interval can be specified by this parameter (in milliseconds), and the default is 2s.
JVM tool parameters:
JVM parameter meaning


-XX:+PrintGCDateStamps Print GC log timestamp
-XX:+PrintGCDetails Print GC details
-XX:+PrintGCTimeStamps Print the time it takes for the garbage collection to start running
-Xloggc: Output garbage collection information to the specified file
-verbose: gc Print GC log
-XX:+PrintGCApplicationStopedTime View application suspension time caused by gc
XX:+PrintTenuringDistribution log of object promotion
-XX:+HeapDumpOnOutOfMemoryError Output dump file when memory overflows

Insert picture description here

Start effect:Insert picture description here

access:Insert picture description here

Request put: Let's see the effect after accessing the put method through http:Insert picture description here

Insert picture description here
Insert picture description here
Insert picture description here
During the operation, we found that a large number of objects entered the old age, triggered full gc, and cms has been collecting.

The utilization rate reached 99%, and cms did not stop for a moment:Insert picture description here

Log analysisInsert picture description here

Log analysis 1.0 version: We extract a log to analyze

[GC (Allocation Failure) 0K->63K(64K), 0.0047147 secs] 10258K->6780K(46144K), [Metaspace: 3434K->3434K(1056768K)], 0.0047613 secs][Times: user=0.02 sys=0.00, real=0.00 secs] The log has four parts:

Full GC:

Indicates that a garbage collection has been performed. There is no Full modification in front, indicating that this is a Minor GC. Note that it does not mean that only the new generation is GC, and the existing STW will be STW whether it is the new generation or the old generation.

Allocation Failure:

It shows that the cause of GC this time is because there is not enough space in the young generation to store new data.

10258K->6780K(46144K), the unit is KB

The three parameters are: the used capacity of the memory area (here, the young generation) before GC, the used capacity of the memory area after GC, and the total capacity of the memory area.

0.0047613 secs:

GC time spent in this memory area, in seconds

[Times: user=0.04 sys=0.00, real=0.01 secs]:

Respectively represent the user mode time-consuming, kernel mode time-consuming and total time-consuming Insert picture description here

Log Analysis 2.0 version:

Using online gceasy for analysis, we open the website and upload the gc logs we produce, as shown in the figure: Insert picture description here

Optimization problems: 4 problems that can be optimized are listed for the new generation and old generation meta-space memory usage Insert picture description here

Throughput statistics: 97.39%
Insert picture description here
of the memory changes of each generation
Insert picture description here

The time consuming of the CMS garbage collector in different periods

Insert picture description here
Insert picture description here
Classification and time-consuming of GC occurrences
Insert picture description here

Positioning problem

We use the snapshot files produced to locate the problem: Insert picture description here
JProfiler:

Downloaded to the local open view through JProfiler Insert picture description here
View large objects Insert picture description here
we find are ArrayList collection takes up 96% of memory, then we take a look at the piece of code that makes heavy use of our ArrayList collection Insert picture description here
to find the corresponding codes Insert picture description here
by the code we found put method Memory overflow OOM caused by extensive use of ArrayList collection

to sum up

I believe everyone understands the above actual combat. The general process is:

1. Enough to simulate the real large-scale user scenario of the SpringBoot project

2. Configure JVM parameters and then deploy and run monitoring data to generate log files

3. Confirm the problem by analyzing the log file.
Friends who need the above code and software, also have detailed study plans, interview questions, etc. I feel that the interview is very clear: to obtain the interview information only: click here to get it!!! Password: CSDN everyone can do it yourself Deepen the impression under actual operation.Insert picture description here

Guess you like

Origin blog.csdn.net/a3961401/article/details/109407949