【JVM】OOM与调优(一)

OOM与调优

方法区

java 复制代码
import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;

import java.lang.reflect.Method;

public class MetaspaceOverFlowTest {

    /**
     * 模拟CGLIB向元空间写入数据
     */
    public static void main(String[] args) {
        while (true) {
            try {
                Thread.sleep(10);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }

            Enhancer enhancer = new Enhancer();

            enhancer.setSuperclass(MetaspaceOverFlowTest.class);
            enhancer.setUseCache(false);
            enhancer.setCallback(new MethodInterceptor() {
                @Override
                public Object intercept(Object o, Method method, Object[] objects, MethodProxy methodProxy) throws Throwable {
                    return methodProxy.invokeSuper(o, args);
                }
            });

            System.out.println("running ....");

            enhancer.create();
        }
    }
}

模拟OOM

查看方法区使用情况

在配置Java环境的情况下,直接打开命令行输入jvisualvm命令即可打开

bash 复制代码
C:\Users\87766>jvisualvm

然后在左边找到我们的程序,右边是查看图形

查看GC情况需要安装一个插件Visual GC,左上方工具栏安装即可

GC日志

bash 复制代码
[GC (Metadata GC Threshold) [PSYoungGen: 9003K->672K(64512K)] 16030K->9067K(236544K), 0.0038284 secs] [Times: user=0.00 sys=0.00, real=0.00 secs]
[Full GC (Metadata GC Threshold) [PSYoungGen: 672K->0K(64512K)] [ParOldGen: 8395K->8858K(74752K)] 9067K->8858K(139264K), [Metaspace: 20138K->20138K(32768K)], 0.0648738 secs] [Times: user=0.02 sys=0.00, real=0.07 secs]
```![在这里插入图片描述](https://i-blog.csdnimg.cn/direct/4bd6eccf56664bd8b1d467cb6f906d1d.png)

### 调优参数
```bash
-XX:MetaspaceSize=20M -XX:MaxMetaspaceSize=20M -XX:+PrintGCDetails

原则:最大、最小设置成一样大,避免因内存分配不足而引发扩容

程序运行起来后,通过VisualVM、Arthas查看占用了多少内存,向上调优,预留20%以上的空间

堆区

java 复制代码
public class HeapOverFlowTest1 {

    int[] intArr = new int[10];

    public static void main(String[] args) {
        List<HeapOverFlowTest1> list = new ArrayList<HeapOverFlowTest1>();

        for (;;) {
            try {
                Thread.sleep(1);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }

            list.add(new HeapOverFlowTest1());
        }

    }
}

模拟OOM

调优vm参数

java 复制代码
-Xms10m -Xmx10m -XX:+PrintGCDetails

jvisualvm查看gc情况

gc日志

bash 复制代码
[GC (Allocation Failure) [PSYoungGen: 1120K->469K(2048K)] 7372K->6786K(9216K), 0.0021594 secs] [Times: user=0.00 sys=0.02, real=0.01 secs]
[GC类型(GC原因)[新生代收集器:gc前新生代的内存使用情况->gc后新生代的内存使用情况(新生代总内存)]gc前堆内存的使用情况->gc后堆内存的使用情况(堆总内存), gc耗时][TImes:gc阶段用户空间耗时 gc阶段内核空间耗时,gc阶段实际耗时]

[Full GC (Ergonomics) [PSYoungGen: 469K->0K(2048K)] [ParOldGen: 6316K->5603K(7168K)] 6786K->5603K(9216K), [Metaspace: 9480K->9410K(1058816K)], 0.0488684 secs] [Times: user=0.08 sys=0.02, real=0.05 secs]
[GC类型(GC原因)[新生代垃圾收集器:gc前新生代的内存使用情况->gc后新生代的内存使用情况(新生代总内存)][老年代垃圾收集器:gc前老年代的内存使用情况->gc后老年代的内存使用情况(老年代总内存)]gc前堆内存的使用情况-> gc后堆内存的使用情况(堆总内存),[Metaspace:gc前元空间的内存使用情况-> gc后元空间的内存使用情况(元空间总内存)], gc耗时][Times:gc阶段用户空间耗时 gc阶段内核空间耗时,gc阶段实际耗时]

调优原则:

  • 1.预留30%以上的空间
  • 2.周期性看日志,重点关注Full GC频率

3.虚拟机栈

java 复制代码
public class StackOverFlowTest {

    private int val = 0;

    public void test() {
        val++;

        test();
    }

    public static void main(String[] args) {
        StackOverFlowTest test = new StackOverFlowTest();

        try {
            test.test();
        } catch (Throwable e) {
            e.printStackTrace();

            System.out.println(test.val);
        }
    }
}

模拟OOM

调优参数

-Xss200k 默认1M

4.直接内存

JVM进程的堆与运行时数据区平行

  • 1.Unsafe.allocateMemory
  • 2.ByteBuf.allocateDirect(NIO)

怎么调优?不调优会怎样?(默认是不受限制)

模拟OOM

模拟OOM,可以看到触发了操作系统的SIGKILL信号机制(signal 9:SIGKILL),但是这个日志怎么查看呢

如何查看Linux内核日志呢?

bash 复制代码
dmesg -T

5.调优参数类型

  • 1.KV类型:-XX:MetaspaceSize=10M
  • 2.boolean类型:-XX:+UseCompressedOops
  • 3.简写类型:-Xms10m
相关推荐
Daniel 大东38 分钟前
BugJson因为json格式问题OOM怎么办
java·安全
Theodore_10225 小时前
4 设计模式原则之接口隔离原则
java·开发语言·设计模式·java-ee·接口隔离原则·javaee
冰帝海岸6 小时前
01-spring security认证笔记
java·笔记·spring
世间万物皆对象6 小时前
Spring Boot核心概念:日志管理
java·spring boot·单元测试
没书读了7 小时前
ssm框架-spring-spring声明式事务
java·数据库·spring
小二·7 小时前
java基础面试题笔记(基础篇)
java·笔记·python
开心工作室_kaic7 小时前
ssm161基于web的资源共享平台的共享与开发+jsp(论文+源码)_kaic
java·开发语言·前端
懒洋洋大魔王7 小时前
RocketMQ的使⽤
java·rocketmq·java-rocketmq
武子康7 小时前
Java-06 深入浅出 MyBatis - 一对一模型 SqlMapConfig 与 Mapper 详细讲解测试
java·开发语言·数据仓库·sql·mybatis·springboot·springcloud
转世成为计算机大神8 小时前
易考八股文之Java中的设计模式?
java·开发语言·设计模式