JVM chooses the appropriate garbage collector (CMS, G1)

JDK1.8 as an example:

1. JVM (Java Virtual Machine) is a virtual machine used to run Java bytecode. The Java Virtual Machine includes a class loader subsystem (Class Loader SubSystem), runtime data area (Runtime Data Area), execution engine and local Native Interface Library. The local interface library interacts with the operating system by calling the Native Method Library

The runtime data area is the main area for JVM parameter tuning. It includes the stack, program counter, heap, method area-metaspace, and local method area. Except for the program counter, other areas can be garbage collected.
Insert image description here

2. The stack has the same life cycle as the thread. The thread is private and uses the operating system's native memory, local variables, object references, etc. within the method. The memory used will be recycled by the operating system as the method is executed and the thread is destroyed. The stack memory defaults to 1M, and the JVM sets the size through the -Xss256k command. The larger the stack setting, the deeper the stack depth allowed (such as recursion). If the stack depth requested by the thread is greater than the depth allowed by the virtual machine, a StackOverflowError exception will be thrown.

3. The local method stack is the relevant area for executing local Native methods.

4. The program counter saves the code execution position. The next time the CPU executes it again, it will execute from the saved position.

5. The method area (metaspace) is used to store metadata information of a type, such as: storing constants, static variables, class information, field information, method names, method codes, method return types, constant pools, and JIT-compiled machines Code and other data, in Java 8, the JVM puts the metadata of the class into local memory (Native Memory), and puts the constant pool and static variables of the class into the Java heap. In this way, it no longer matters how much metadata information the JVM can load. It is determined by the maximum available memory (MaxPermSize) space of the JVM, which is determined by the actual available memory space of the operating system.

6. Heap, the largest memory area of ​​​​JVM. Parameter tuning is mainly in this area. The virtual machine divides the heap memory into the new generation and the old generation according to the generation model.

6.1. Most of the objects in the new generation are "born and destroyed". Using Young GC can often quickly clean up most of the garbage. The remaining objects will be directly copied back and forth between Survivor1 and Survivor2, and the age of the object will be increased until the age is reached. Put it in the old generation together with large objects

6.2. The old generation stores objects and large objects that have not been recycled many times in the new generation, and Full GC is used. (1. Some judgments will be made before each Young GC to see whether it is necessary to perform Full GC in the old generation first. 2. After Young GC, the surviving objects cannot be placed in the Survivor area, nor can they be placed in the old generation, then a Full GC is triggered). If the memory cannot be applied for after collection, an OutOffMemoryError will be thrown.

6.3. Criteria for determining garbage objects: 1. Reference counting method (two classes cannot be released when they refer to each other), 2. Reachability analysis algorithm (JVM uses this method)

6.4. Garbage collection algorithm: In heap memory, JVM uses different garbage collection algorithms according to different generations (or JDK versions).

  • Mark-clear: Mark garbage objects and clear them directly. There will be memory fragmentation.
  • Copy: The copy algorithm is fast and the memory usage is not high. After the new generation is recycled, only a small number of surviving objects are retained and copied to the Survivor area.
  • Mark-organize: Mark all reachable objects. After completion, unmarked objects will be cleaned up, and then all surviving objects will be compressed to one end of the memory. The mark-organize algorithm solves the high cost problem of halving the memory of the copy algorithm.

6.5.JVM garbage collection algorithm

  • Serial garbage collector: single-threaded recycling, all application threads will be suspended during Young GC and Full GC, suitable for 32-bit minicomputer small memory environment, use -XX:+UseSerialGC
  • ParallelGC garbage collector: multi-threaded recycling, all application threads will be suspended when performing Young GC and Full GC. This collector is the default for JDK 7u4 and later versions. Use -XX:+UseParallelGC -XX:+UseParallelOldGC to specify explicitly (the former It is to collect the new generation, and the latter is to collect the old generation)
  • CMS collector: multi-thread recycling, all application threads will be suspended during Young GC, and application threads will no longer be suspended during Full GC (using multiple background threads to collect the old generation, the price paid is higher CPU usage), The CMS collector in JDK8 is turned off by default. Use -XX:+UseParNewGC -XX:+UseConcMarkSweepGC to display it on (the former collects the new generation and the latter collects the old generation).
  • G1 garbage collector: multi-threaded collection, the new generation garbage collection still suspends all application threads, it divides the entire heap into 2048 small areas, uses the memory resources of these areas independently and tracks the progress of garbage collection in these areas. A priority list is maintained in the background. During the garbage collection process, according to the longest garbage collection time allowed by the system, the area with the most garbage will be recycled first. Use -XX:+UseG1GC to enable it in JDK8.
  • ZGC garbage collector: The recycling algorithm available in JDK11 has been optimized on G1. Use XX:+UnlockExperimentalVMOptions -XX:+UseZGC. You can refer to Tencent's open source Tencent Kona JDK11 .

6.6. How to choose a garbage collection algorithm? The suggestions are as follows:

  • If there are few CPU cores and 1-2GB of memory, you can use the JDK default collector.
  • If the CPU core is greater than 4 and the memory is 4-6GB, use the CMS garbage collector: ‐XX:+UseParNewGC -XX:+UseConcMarkSweepGC
  • For CPU cores greater than 8 and memory 6-32GB, use the G1 garbage collector: ‐XX:+UseG1GC

It is related to the CPU because CMS and G1 will open multiple background threads to collect garbage. If there are not enough CPU cores, it will cause competition for CPU resources and degrade to single-thread collection, resulting in slower performance.

6.7.JVM key parameter settings:

  • Default startup: java -jar xxx.jar
  • Set the maximum memory startup: java -jar -Xms2g -Xmx2g xxx.jar
  • Set the new generation startup: java -jar -Xms4g -Xmx4g -Xmn1g xxx.jar
  • Start using CMS collector: java -jar -Xms6g -Xmx6g ‐XX:+UseParNewGC -XX:+UseConcMarkSweepGC xxx.jar
  • Start using the G1 collector: java -jar -Xms16g -Xmx16g ‐XX:+UseG1GC -XX:MaxGCPauseMillis=120 -XX:ParallelGCThreads=8 xxx.jar
预期停顿时间是120ms:-XX:MaxGCPauseMillis=120
垃圾收集线程数:-XX:ParallelGCThreads= N ,N = 8 + ((N - 8) * 5 / 8), N代表CPU 的数目
如果服务器上有多个JVM实例,则需要调整ParallelGCThreads数量,过多的线程数会导致争抢CPU资源,ParallelGCThreads = min(CPU数量/JVM实例数, 8+((N-8)*5/8))

Please check for more other parameters by yourself

7. Direct memory. NIO related classes use direct memory to avoid data copying back and forth between the kernel and JVM.

8.JVM tools

 1.jps 查看java进程
 2.jstat 虚拟机统计工具
  jstat -gcutil 2764
   S0    S1   E    O     M    YGC YGCT FGC FGCT   GCT
   0.00 0.00 6.20 41.42 47.20 16 0.105 3   0.472 0.577
   E表示新生代Eden区使用了6.2%的空间,2个S0、S1表示Survivor0、Survivor1,老年代(O,表示Old)和元空间(M)则分别使用了41.42%和47.20%的空间。
   程序运行以来共发生Minor GC(YGC,表示YoungGC)16次,总耗时0.105秒;发生Full GC(FGC,表示Full GC)3次,总耗时(FGCT,表示Full GCTime)为0.472秒;
   所有GC总耗时(GCT,表示GC Time)为0.577秒
   
 3.jinfo 实时查看和调整虚拟机各项参数, jinfo pid
 4.jmap 用于生成堆转储快照dump文件,jmap pid ,jmap -dump:format=b,file=zy.bin 30790
 5.jhat 分析jmap生成的快照文件,jhat zy.bin (一般使用VisualVM,不用此命令工具)
 6.jstack 用来查看线程停顿情况,jstack [option] pid ,jstack -l 30790,option有 -F(当正常请求不被响应时,强制输出线程堆栈),-l(除堆栈外还输出锁信息),-m(可以显示c/c++本地方法堆栈)
 7.VisualVM https://visualvm.github.io
 8.JVM参数调优可以应用到eclipse或Idea,如:
   -XX:+UseParNewGC
   -XX:+UseConcMarkSweepGC
   或单独使用-XX:+UseG1GC

 9.查看JVM运行时长:jcmd process_id VM.uptime
 10.查看JVM属性:jcmd process_id VM.system_properties 或 jinfo -sysprops process_id
 11.获取JVM版本:jcmd process_id VM.version
 12.查看JVM内存:jinfo -flags process_id
 13.查看每个线程栈信息:jstack process_id

The above is my personal understanding of JVM knowledge and daily work. If there are any errors, please include them and leave a message to correct them.

Guess you like

Origin blog.csdn.net/zhuyu19911016520/article/details/133267236