jvm常见内存溢出异常
来源:互联网 发布:喋血街头java 编辑:程序博客网 时间:2024/05/16 17:35
上面这幅图就是jvm虚拟机运行时的主要数据区,蓝色部分是线程共享区域,而白色部分就是线程私有区域。
以下例子均在jdk1.7中运行
1.堆内存溢出
/** * VM Args: -Xms2m -Xmx2m * Created by Stay on 2017/5/15 14:50. */public class Base1 { public static void main(String[] args) { List<Object> list = new ArrayList<>(); while(true){ list.add(new byte[2 * 1024]); } }}result: Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
-Xms2m 堆内存最小为2m
-Xmx2m 堆内存最大为2m,参数设置一样是为了避免堆自动扩展
我们再加上-XX:+PrintGCDetails 打印出GC回收的过程:
[GC [PSYoungGen: 2047K->504K(2560K)] 2047K->2028K(5120K), 0.0014692 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] [Full GC [PSYoungGen: 504K->0K(2560K)] [ParOldGen: 1524K->1696K(5120K)] 2028K->1696K(7680K) [PSPermGen: 2776K->2775K(21504K)], 0.0123204 secs] [Times: user=0.02 sys=0.00, real=0.01 secs] [GC [PSYoungGen: 2046K->512K(2560K)] 3743K->4080K(7680K), 0.0009728 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] [Full GC [PSYoungGen: 512K->0K(2560K)] [ParOldGen: 3568K->3587K(5120K)] 4080K->3587K(7680K) [PSPermGen: 2792K->2792K(21504K)], 0.0063521 secs] [Times: user=0.00 sys=0.00, real=0.01 secs] [Full GC [PSYoungGen: 2047K->503K(2560K)] [ParOldGen: 3587K->5066K(5120K)] 5635K->5570K(7680K) [PSPermGen: 2815K->2815K(21504K)], 0.0091229 secs] [Times: user=0.00 sys=0.00, real=0.01 secs] [Full GC [PSYoungGen: 2046K->2023K(2560K)] [ParOldGen: 5066K->5056K(5120K)] 7113K->7079K(7680K) [PSPermGen: 2843K->2843K(21504K)], 0.0054760 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] [Full GC [PSYoungGen: 2046K->2046K(2560K)] [ParOldGen: 5056K->5056K(5120K)] 7102K->7102K(7680K) [PSPermGen: 2843K->2843K(21504K)], 0.0056718 secs] [Times: user=0.02 sys=0.00, real=0.00 secs] [Full GC [PSYoungGen: 2048K->2046K(2560K)] [ParOldGen: 5118K->5118K(5120K)] 7166K->7164K(7680K) [PSPermGen: 2845K->2845K(21504K)], 0.0051912 secs] [Times: user=0.00 sys=0.00, real=0.01 secs] [Full GC [PSYoungGen: 2046K->2046K(2560K)] [ParOldGen: 5118K->5106K(5120K)] 7164K->7153K(7680K) [PSPermGen: 2845K->2845K(21504K)], 0.0075618 secs] [Times: user=0.03 sys=0.00, real=0.01 secs] [Full GC [PSYoungGen: 2046K->2046K(2560K)] [ParOldGen: 5119K->5119K(5120K)] 7165K->7165K(7680K) [PSPermGen: 2846K->2846K(21504K)], 0.0056501 secs] [Times: user=0.00 sys=0.00, real=0.01 secs] [Full GC [PSYoungGen: 2046K->2046K(2560K)] [ParOldGen: 5119K->5119K(5120K)] 7165K->7165K(7680K) [PSPermGen: 2846K->2846K(21504K)], 0.0051502 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] [Full GCException in thread "main" [PSYoungGen: 2048K->0K(2560K)] [ParOldGen: 5119K->518K(4608K)] 7167K->518K(7168K) [PSPermGen: 2872K->2872K(21504K)], 0.0084184 secs] [Times: user=0.01 sys=0.00, real=0.01 secs] java.lang.OutOfMemoryError: Java heap spaceat jvm.base1.main(base1.java:16)at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)at java.lang.reflect.Method.invoke(Method.java:606)at com.intellij.rt.execution.application.AppMain.main(AppMain.java:147)Heap PSYoungGen total 2560K, used 67K [0x00000000ffd00000, 0x0000000100000000, 0x0000000100000000) eden space 2048K, 3% used [0x00000000ffd00000,0x00000000ffd10c38,0x00000000fff00000) from space 512K, 0% used [0x00000000fff80000,0x00000000fff80000,0x0000000100000000) to space 512K, 0% used [0x00000000fff00000,0x00000000fff00000,0x00000000fff80000) ParOldGen total 4608K, used 518K [0x00000000ff800000, 0x00000000ffc80000, 0x00000000ffd00000) object space 4608K, 11% used [0x00000000ff800000,0x00000000ff8819e0,0x00000000ffc80000) PSPermGen total 21504K, used 2897K [0x00000000fa600000, 0x00000000fbb00000, 0x00000000ff800000) object space 21504K, 13% used [0x00000000fa600000,0x00000000fa8d4468,0x00000000fbb00000)
从打印的这些信息就能看出,虽然JVM在尽力的回收,但是也抵挡不住while(true)的威力。
二.栈溢出
/** * VM Args: -Xss128k * Created by Stay on 2017/5/15 15:41. */public class Base2 { private int stackLength = 1; public static void main(String[] args) { Base2 base2 = null; try { base2 = new Base2(); base2.stackLeak(); } catch (Throwable e) { System.out.println("stack length:" + base2.stackLength); throw e; } } public void stackLeak() { stackLength++; stackLeak(); }}
result:
Exception in thread "main" java.lang.StackOverflowErrorstack length:11409.....
Thread api中有一个不常用的构造器 Thread(ThreadGroup group, Runnable target, String name, long stackSize) ,最后一个参数就是每个线程的栈大小的设置
再来个栗子:
/** * Created by Stay on 2017/5/15 16:15. */public class Base3 { private static int count = 1; public static void main(String[] args) { Thread t1 = new Thread(null,new Runnable() { @Override public void run() { try { add(1); } catch (Throwable e) { System.out.println(count); e.printStackTrace(); } } private void add(int i) { count++; add(i + 1); } },"stackTest"); t1.start(); }}
result:
java.lang.StackOverflowError10472....
在最后加上一个stackSize参数 Thread t1 = new Thread(null,....,"stackTest",1 << 24);
result:
975998java.lang.StackOverflowError....
count最后的值比刚开始大了不少,就是因为我们给每个线程分配的栈空间变大了,但是能创建的线程就变小了,因为总的栈空间没变。这个构造方法一般用的很少。
有些时候我们把jvm只分为两块 堆和栈,这样的分法是比较粗糙的,只能说明大多数程序员最关注的,就是这两块区域,这里所指的栈就是虚拟机栈,或者说是虚拟机中局部变量表部分.
而堆 就是存放对象实例,所有new出来的实例都存放在这里 栈中只是引用堆中的对象。垃圾回收器也是主要管理这个区域,称为GC堆
三.方法区内存溢出(PermGen space)
我们利用字符串的intern()方法进行实验
为了尽快溢出,jvm参数设置永久代参数5M: -XX:PermSize=5m -XX:MaxPermSize=5m
public static void main(String[] args) {List list = new ArrayList();int i = 0;while(true){list.add((String.valueOf(i++)).intern());}}
运行结果如下:OutOfMemoryError后面提示 PermGen space ;改代码在jdk6及以下版本能够报出如下异常,jdk7高版本及以上部分jvm已经逐渐开始取消永久代的原因,只会报出堆内存异常
Exception in thread "main" java.lang.OutOfMemoryError: PermGen spaceat java.lang.String.intern(Native Method)at com.TestSocket.main(TestSocket.java:12)
- jvm常见内存溢出异常
- JVM的内存溢出异常
- jvm的内存溢出异常
- JVM的内存溢出异常
- jvm的内存溢出异常
- jvm的内存溢出异常
- JVM内存区域与内存溢出异常
- JVM内存区域和内存溢出异常
- JVM--内存区域和内存溢出异常
- JVM内存区域与内存溢出异常
- 常见JVM内存异常分析
- JVM常见内存溢出问题归纳
- 常见jvm内存溢出典型案例
- JVM----内存区域及溢出异常
- Java常见内存溢出异常分析
- Java常见内存溢出异常分析
- Java常见内存溢出异常分析(OutOfMemoryError)
- Java常见内存溢出异常分析
- 《Mesos in Action》一些零碎的笔记(Mesos之于Kubernetes,犹如WebKit之于Chromium)
- 24. Swap Nodes in Pairs
- lua.h源码详解
- loadrunner性能测试_第一步 录制脚本
- jQuery插件开发模式
- jvm常见内存溢出异常
- 数据结构基础加强之二叉树
- 分布式架构学习之:028--ActiveMQ高可用集群(zookeeper+leveldb)安装、配置、高可用测试
- Android 弱引用
- union 与 union all 的区别
- linux系统下安装tomcat
- git创建分支、切换分支
- 关于 Linux windows 平台上的Nginx 403错误
- 讨论事务的隔离性下,商品库存超买问题