一次线上问题排查:java.lang.OutOfmemoryError: PermGen Space

背景

用基于Spring Boot(环境是java7)的系统做了一个报表导出的功能,第一次部署的时候用的默认JVM参数,但是测试人员在点击了一次导出之后,其他功能就疑似挂掉了,过了一会后才能正常使用;再点击导出,又出现这个问题,对这个问题的排查如下。

jmap -heap pid查看堆内存使用情况
Attaching to process ID 6082, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 24.65-b04

using thread-local object allocation.
Parallel GC with 4 thread(s)

Heap Configuration:
   MinHeapFreeRatio = 0
   MaxHeapFreeRatio = 100
   MaxHeapSize      = 8417968128 (8028.0MB)
   NewSize          = 1310720 (1.25MB)
   MaxNewSize       = 17592186044415 MB
   OldSize          = 5439488 (5.1875MB)
   NewRatio         = 2
   SurvivorRatio    = 8
   PermSize         = 21757952 (20.75MB)
   MaxPermSize      = 85983232 (82.0MB)//没加启动参数perm就这么大一点
   G1HeapRegionSize = 0 (0.0MB)

Heap Usage:
PS Young Generation
Eden Space:
   capacity = 1682440192 (1604.5MB)
   used     = 1513288224 (1443.1841125488281MB)
   free     = 169151968 (161.31588745117188MB)
   89.94603381419932% used
From Space:
   capacity = 29884416 (28.5MB)
   used     = 26140048 (24.929092407226562MB)
   free     = 3744368 (3.5709075927734375MB)
   87.47049967447917% used
To Space:
   capacity = 33030144 (31.5MB)
   used     = 0 (0.0MB)
   free     = 33030144 (31.5MB)
   0.0% used
PS Old Generation
   capacity = 350748672 (334.5MB)
   used     = 26275344 (25.058120727539062MB)
   free     = 324473328 (309.44187927246094MB)
   7.491216958905549% used
PS Perm Generation
   capacity = 76546048 (73.0MB)
   used     = 76144792 (72.6173324584961MB)
   free     = 401256 (0.38266754150390625MB)
   99.47579788835081% used  //好吧,这里知道为啥了吧

32763 interned Strings occupying 3822560 bytes.
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50

原因已经很清楚了,默认的永久代几乎被占满了,而我们知道,永久带在被占满的情况下会引发Full GC,而在Full GC的时候,会导致JVM暂停工作,要等到GC完成的时候才能工作。进一步查看了代码,发现在导出报表的代码中,涉及到大部分的类方法和常量的初始化,而刚好初始化完成之后,超过了永久代的大小,好了,问题就在这里。

解决

启动时设置JVM参数:

# nohup java -Xms1024m -Xmx1024m -Xss1024K -XX:PermSize=128m -XX:MaxPermSize=256m -jar spring-boot-1.0.0.jar >/dev/null 2>&1 &
  • 1

启动之后jmap -heap pid

Attaching to process ID 7992, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 24.65-b04

using thread-local object allocation.
Parallel GC with 4 thread(s)

Heap Configuration:
   MinHeapFreeRatio = 0
   MaxHeapFreeRatio = 100
   MaxHeapSize      = 1073741824 (1024.0MB)
   NewSize          = 1310720 (1.25MB)
   MaxNewSize       = 17592186044415 MB
   OldSize          = 5439488 (5.1875MB)
   NewRatio         = 2
   SurvivorRatio    = 8
   PermSize         = 134217728 (128.0MB)
   MaxPermSize      = 268435456 (256.0MB)
   G1HeapRegionSize = 0 (0.0MB)

Heap Usage:
PS Young Generation
Eden Space:
   capacity = 319815680 (305.0MB)
   used     = 147022504 (140.21158599853516MB)
   free     = 172793176 (164.78841400146484MB)
   45.971011802798415% used
From Space:
   capacity = 18874368 (18.0MB)
   used     = 11712952 (11.170341491699219MB)
   free     = 7161416 (6.829658508300781MB)
   62.05745273166232% used
To Space:
   capacity = 18874368 (18.0MB)
   used     = 0 (0.0MB)
   free     = 18874368 (18.0MB)
   0.0% used
PS Old Generation
   capacity = 716177408 (683.0MB)
   used     = 65918920 (62.86518096923828MB)
   free     = 650258488 (620.1348190307617MB)
   9.204272469873834% used
PS Perm Generation
   capacity = 134217728 (128.0MB)
   used     = 97287360 (92.78045654296875MB)
   free     = 36930368 (35.21954345703125MB)
   72.48473167419434% used  //
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48

好了,再怎么导出都没有问题了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值