我愛學習網(wǎng)-上傳
當前位置: 主頁 > 文庫 > Java >

Java常見的JVM 異常介紹

時間:2020-07-19 15:22來源:我愛學習網(wǎng) 作者:apple 點擊:

JVM 堆內(nèi)存溢出展示

 

public class OutOfMemoryException {

  public static void main(String[] args) {
    List bufList = new ArrayList<>();
    for (; ; ) {
      bufList.add(new OutOfMemoryException());
    }
  }
}

 

需要注意的是,由于現(xiàn)在計算機配置都非常高,因此直接讓計算機內(nèi)存溢出是一件非常困難的操作,因此這里我們將虛擬機的配置更改下,需要在啟動參數(shù)中添加 `-Xms1m -Xmx1m -XX:+HeapDumpOnOutOfMemoryError`  標識初始化內(nèi)存1M,最大拓展內(nèi)存1M,并且dump 異常信息當出現(xiàn)OOM的時候

 

執(zhí)行代碼,等待一段時間之后,控制臺出現(xiàn)以下錯誤信息并且項目的根目錄出現(xiàn)后綴名為: hprof 如:java_pid92363.hprof 的文件

 

java.lang.OutOfMemoryError: Java heap space
Dumping heap to java_pid92363.hprof ...
Heap dump file created [2571260 bytes in 0.011 secs]
Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
	at java.util.Arrays.copyOf(Arrays.java:3210)
	at java.util.Arrays.copyOf(Arrays.java:3181)
	at java.util.ArrayList.grow(ArrayList.java:265)
	at java.util.ArrayList.ensureExplicitCapacity(ArrayList.java:239)
	at java.util.ArrayList.ensureCapacityInternal(ArrayList.java:231)
	at java.util.ArrayList.add(ArrayList.java:462)
	at com.zhoutao.memory.OutOfMemoryException.main(OutOfMemoryException.java:17)

Process finished with exit code 1

 

 

我們可以在控制臺輸入命令  `jvisualvm`   啟動 JVisualVM 工具  ,在文件中載入 java_pid92363.hprof 文件,在文件選項卡中載入此hprof文件即可

 

可以看到報錯信息中顯示在main線程中出現(xiàn)OOM,標識OOM的異常信息是在main線程出現(xiàn)的,在類選項卡中,我們可以看到,OutOfMemoryException 類的實例達到4萬之多,導(dǎo)致OOM

 

 

棧內(nèi)存溢出異常

 

/**
 * 使用遞歸的方式測試 JVM 的棧內(nèi)存溢出
 *
 * 

設(shè)置棧內(nèi)存大小: -Xss100k */ public class StackOverflowException { public static void main(String[] args) { StackOverExample example = new StackOverExample(); example.test(); } } class StackOverExample { private int length; void test() { this.length++; try { test(); } catch (Throwable throwable) { System.out.println("棧深度:" + this.length); throwable.printStackTrace(); } } }

 

 

輸出數(shù)據(jù):

 

棧深度:9925
java.lang.StackOverflowError
	at sun.misc.Unsafe.compareAndSwapLong(Native Method)
	at java.util.concurrent.ConcurrentHashMap.addCount(ConcurrentHashMap.java:2259)
	at java.util.concurrent.ConcurrentHashMap.putVal(ConcurrentHashMap.java:1070)
	at java.util.concurrent.ConcurrentHashMap.putIfAbsent(ConcurrentHashMap.java:1535)
	at java.lang.ClassLoader.getClassLoadingLock(ClassLoader.java:463)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:404)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:411)
	at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:349)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
	at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
	at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:26)

 

可以看到棧深度達到9925 的時候出現(xiàn)了棧內(nèi)存溢出異常的錯誤,使用JVisuaVM 獲取線程Dump的數(shù)據(jù)可以看到一下信息, 當前線程狀態(tài)為 TIMED_WAITING ,處于等待休眠狀態(tài)。

 

"main" #1 prio=5 os_prio=31 tid=0x00007fcce4801800 nid=0x1103 sleeping[0x000070000d0c9000]
   java.lang.Thread.State: TIMED_WAITING (sleeping)
        at java.lang.Thread.sleep(Native Method)
        at java.lang.Thread.sleep(Thread.java:340)
        at java.util.concurrent.TimeUnit.sleep(TimeUnit.java:386)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:27)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)
        at com.zhoutao.memory.StackOverExample.test(StackOverflowException.java:28)

 

 

死鎖異常信息

 

程序分析:

  • 線程A 已經(jīng)獲取到對象 lockObject1 的鎖,然后延時2秒
  • 線程2 已經(jīng)獲取到對象 lockObject2的鎖,然后延時1秒
  • 由于延時的時間差異,線程B首先執(zhí)行完成,這時候B嘗試獲取 lockObject1的鎖,但是A線程持有l(wèi)ockObject1的鎖,所以B線程在等待獲取lockObject1的鎖
  • 在B線程等待的期間,A線程執(zhí)行完成,嘗試獲取對象lockObject2的鎖,此時就會出現(xiàn)死鎖問題

 

public class DeadLockException {

  public static void main(String[] args) throws Exception {

    final Object lockObject1 = new String();
    final Object lockObject2 = new StringBuffer();

    new Thread(
            () -> {
              System.out.println("DeadLockException.run");
              synchronized (lockObject1) {
                System.out.println("1 get 1's lock");
                try {
                  TimeUnit.SECONDS.sleep(2);
                } catch (InterruptedException e) {
                  e.printStackTrace();
                }

                synchronized (lockObject2) {
                  System.out.println("1 get 2's lock");
                }
              }
            })
        .start();

    new Thread(
            () -> {
              System.out.println("DeadLockException.run");
              synchronized (lockObject2) {
                System.out.println("2 get 2's lock");
                try {
                  TimeUnit.SECONDS.sleep(1);
                } catch (InterruptedException e) {
                  e.printStackTrace();
                }
                synchronized (lockObject1) {
                  System.out.println("2 get 1's lock");
                }
              }
            })
        .start();
  }
}

 

程序執(zhí)行結(jié)果:

 

DeadLockException.run
1 get 1's lock
DeadLockException.run
2 get 2's lock

 

 

使用JvisualVM 工具分析可見到 圖4.3.1 ,JvisualVM 已經(jīng)發(fā)現(xiàn)了死鎖,這里dump線程,可以再次看到:

 

圖 4.3.1 

 

 

 

 

圖 4.3.2 線程Dump 分析

 

 

 

 

 

圖 4.3.3 使用JProfile 查看是否存在死鎖

 

 

 

Metaspace 元空間內(nèi)存溢出

 

從Java1.8開始,永久代的概念被移除,取而代之的是在本地內(nèi)存中的元空間(Metaspace) ,默認大小20.75M,可以通過 -XX:MaxMatespaceSize=1000m,來修改元空間大小,可以通過使用Cglib 不同的創(chuàng)建類來實現(xiàn)元空間的方法溢出。通過需要修改VM 參數(shù) -XX:MaxMetaspaceSize=2M 

 

public class JavaMethodAreaOOM {

	static class OOMObject{
	}
	
	public static void main(String[] args) {
		while (true) {
			Enhancer enhancer = new Enhancer();
			enhancer.setSuperclass(OOMObject.class);
			enhancer.setUseCache(false);
			enhancer.setCallback(new MethodInterceptor() {
				@Override
				public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
					return proxy.invoke(obj, args);
				}
			});
			enhancer.create();
		}
	}
}

 

 

輸出結(jié)果:

Exception in thread “main” java.lang.OutOfMemoryError: Metaspace

at net.sf.cglib.core.AbstractClassGenerator.create(AbstractClassGenerator.java:237)

at net.sf.cglib.proxy.Enhancer.createHelper(Enhancer.java:377)

at net.sf.cglib.proxy.Enhancer.create(Enhancer.java:285)

at com.seeyon.oom.JavaMethodAreaOOM.main(JavaMethodAreaOOM.java:42)

 

 

其他監(jiān)控工具

 

Jconsole

 

 

Jprofile

 

------分隔線----------------------------
    ?分享到??
看看啦
主站蜘蛛池模板: 好看的电影网站亚洲一区| 无码一区二区三区在线| 精品国产一区二区三区不卡| 人妻视频一区二区三区免费| 日本不卡免费新一区二区三区| 精品综合一区二区三区| 无码乱人伦一区二区亚洲一| 亚洲一区二区三区在线播放| 最新欧美精品一区二区三区 | 久久影院亚洲一区| 任你躁国语自产一区在| 日本一区二区三区高清| 一区二区三区www| 波多野结衣一区二区三区88| 亚洲av成人一区二区三区观看在线 | 精品国产一区二区三区在线 | 亚洲AV无码一区二区三区在线| 中文无码精品一区二区三区| 国产精品无码一区二区三区免费| 国产精品综合一区二区三区| 国产美女一区二区三区| 久久国产精品无码一区二区三区| 亚洲无删减国产精品一区| 国产精品毛片VA一区二区三区| 国产麻豆精品一区二区三区v视界 国产美女精品一区二区三区 | 国产AV一区二区三区无码野战| 好看的电影网站亚洲一区| 亚洲爽爽一区二区三区| 中文字幕在线一区| 精品国产免费一区二区三区香蕉| 污污内射在线观看一区二区少妇| 日韩十八禁一区二区久久| 精品一区二区三区免费视频| 国产综合一区二区| 精品一区二区三区视频| 亚洲高清成人一区二区三区| 精品久久久久一区二区三区| 亚洲一区二区三区偷拍女厕| 麻豆aⅴ精品无码一区二区| 国产精品乱码一区二区三| 免费一区二区三区四区五区|