[Original Document]

 

 

신세대 Heap
JDK 1.4.1에서 heap은 신세대, 구세대,
영구세대(Permanent generation)의 3단계로 나눠진다.
신세대는 또한 Eden과 Semi-spaces로 나뉜다. Eden과
semi-spaces의 크기는 SurvivorRatio(생존률)에 의해 조정되며 다음과 같이 계산할 수 있다.

Eden = NewSize – ((NewSize / ( SurvivorRatio
+ 2)) * 2)
From space = (NewSize – Eden) / 2
To space = (NewSize – Eden) /
2

NewSize는 신세대의 크기이며 -XX:NewSize 옵션을 사용해 지정할 수 있다.
SurvivorRatio는 정수이며 1부터 매우 높은 값까지 가능하다. 신세대의 크기는 다음 옵션을 사용해 조절할 수 있다.

-XX:NewSize
-XX:MaxNewSize
-XX:SurvivorRatio

예를 들어 128MB의 신세대에서 64MB를 Eden에, 32MB를
Semi-Space에 할당하고자 하면 NewSize와 MaxNewSize, SurvivorRatio의 값을 다음과 같이 명시할 수 있다.

java -Xms512m -Xmx512m -XX:NewSize=128m
-XX:MaxNewSize=128m \
-XX:SurvivorRatio=2 application


구세대 Heap

구세대 또는 Tenured
Generation는 신세대에서 승진한 오래된 객체를 가지고 있다. -Xms 매개변수를 사용해서 구세대의 최대 크기를 조정할 수
있다.
앞서 예를 보다 확장해서 256MB의 구세대 heap과 256MB의 신세대를 -mx 변수를 사용해서 지정할 수 있다.

java -Xms512m -Xmx512m -XX:NewSize=256m
-XX:MaxNewSize=256m \
-XX:SurvivorRatio=2
application

신세대가 256MB를 사용하고 구세대가 다른 256MB를 사용한다. -Xms를 사용해서 초기 heap 크기를
지정했다.

 

 

영구세대의 Heap
영구세대(Permanent
generation)는 클래스 객체와 그 관련 메타 정보를 저장하는 데에 사용된다. 기본 크기는 4MB이며 -XX:PermSize와
-XX:MaxPermSize 옵션을 사용해 설정할 수 있다.
종종 로그 파일에서 Full GC를 볼 수 있을 텐데, 이것은 영구세대를
확장할 때 생기는 것이다. 이런 현상은 -XX:PermSize와 -XX:MaxPermSize 옵션을 사용해서 영구세대의 heap을 크게 잡으면
막을 수 있다. 예를 들어 다음과 같이 해보자.

java -Xms512m -Xmx512m -XX:NewSize=256m
-XX:MaxNewSize=256m \
-XX:SurvivorRatio=2 -XX:PermSize=64m
-XX:MaxPermSize=64m application

영구세대의 컬렉션을 비활성화시키는 방법은 -Xnoclassgc 옵션을 사용하는 것이다.
이 옵션은 클래스 객체를 컬렉션하지 못하게 하기 때문에 조심해서 사용해야 한다. 이를 사용하기 위해서는 GC가 일어나지 않을 정도로 클래스
객체를 저장할 수 있는 영구세대의 크기를 크게 잡으면 된다. 예를 들어 다음과 같이 한다.

java -Xms512m -Xmx512m -XX:NewSize=256m
-XX:MaxNewSize=256m \
-XX:SurvivorRatio=2 -XX:PermSize=128m
-XX:MaxPermSize=128m \
-Xnoclassgc
application
 
 
기본 사용법
Java 애플리케이션은 다음 명령어로 실행될 수 있다.

java application

기본적으로 신세대에서 Eden은 2MB, Semi-space는 64KB가 잡혀 있다.
구세대 heap은 5MB로 시작해서 44MB까지 확장된다. 영구세대의 기본 크기는 4MB이다.

-Xms와 -Xms 스위치
사용하기

구세대의 기본 heap 크기는 -Xms와 -Xmx를 사용해서 초기값 및 최대 크기값을 변경할 수 있다.

java -Xms <initial size> -Xmx
<maximum size> program

예를 들면 다음과 같다.

java -Xms128m -Xmx512m
application

:XX 스위치를 사용해 새로운 Low Pause 또는 Throughput
Collector 사용하기

·Low Pause Collector 사용하기
신세대에서는
-XX:+UseParNewGC 옵션을 사용해 Parallel Copying Collector를 활성화시킬 수 있으며, 구세대에서는 -XX:
+UseConcMarkSweepGC를 사용해 Concurrent Collector를 활성화시킬 수 있다. 예를 들면 다음과 같다.

java -server -Xms512m -Xmx512m
-XX:NewSize=64m -XX:MaxNewSize=64m \
-XX:SurvivorRatio=2 -XX:+
UseConcMarkSweepGC \
-XX:+UseParNewGC application

다만 -XX:+UseParNewGC가 명시되지 않았으면 신세대는 기본적으로
Copying Collector(http://wireless.java.sun.com/ midp/articles/garbage/참조)를 사용하게
될 것이다. 또한 단일 CPU 시스템에서 -XX+UseParNewGC가 명시되지 않았다면 CPU의 개수가 1개이기 때문에 기본인 Copy
Collector가 사용된다. 병렬의 정도를 증가시켜 Parallel Copy Collector를 활성화시킬 수
있다.

– 병렬의 정도를 조정하기
기본적으로 Parallel Copy Collector는 CPU 개수만큼의
쓰레드를 생성해 사용하지만 병렬의 정도를 조정해야 한다면 다음과 같이 변경할 수 있다.

-XX:ParallelGCThreads=<desired
parallelism>

기본값은 CPU 개수와 동일하다. 예를 들어 신세대의 컬렉션이 4개의 병렬 쓰레드를
사용하기 위해선 다음과 같다.

java -server -Xms512m -Xmx512m
-XX:NewSize=64m -XX:MaxNewSize=64m \
-XX:SurvivorRatio=2 -XX:+UseParNewGC
-XX:ParallelGCThreads=4 \
-XX:+UseConcMarkSweepGC application


– JDK 1.4.1에서 ‘promoteall’ 변경자
모방하기

‘promoteall’ 변경자는 JDK 1.2.2에서 신세대의 모든 유효한 객체를 구세대로 별도의 과정 없이 곧바로
승진시킨다. JDK 1.4.1에는 ‘promoteall’ 변경자가 없지만 보유분포(tenuring distribution)를 조정해서 비슷한
현상을 만들 수 있다. MaxTenuringThreshold 옵션을 통해 신세대에 있는 객체가 노화되는 횟수를 조정한다. 이 옵션을 0으로
설정하면 곧바로 구세대로 승진되는 것이다. SurvivorRatio는 20000 또는 그 이상의 높은 값으로 설정해서 신세대 Heap 크기 중
Eden이 대부분 사용하게 한다.

-XX:MaxTenuringThreshold=0
-XX:SurvivorRatio=20000

예를 들면 다음과 같다.

java -server -Xms512m -Xmx512m
-XX:NewSize=64m -XX:MaxNewSize=64m \
-XX:SurvivorRatio=20000
-XX:MaxTenuringThreshold=0 \
-XX:+UseParNewGC -XX:+UseConcMarkSweepGC
application


Concurrent Collection 초기화
조정하기

Concurrent Collector의 백그라운드 쓰레드는 구세대의 공간 활용 비율이 기본적으로 68%인,
-XX:CMSInitiatingOccupancy Fraction보다 높으면 시작하게 된다. 이 값은 변경할 수 있으며, 다음 옵션을 사용해서
Concurrent Collector를 더 빨리 실행시킬 수
있다.

-XX:CMSInitiatingOccupancyFraction=<percent>

예를 들면 다음과
같다.

java -server -Xms512m -Xmx512m -XX:NewSize=64m -XX:MaxNewSize=64m
\
-XX:SurvivorRatio=20000 -XX:MaxTenuringThreshold=0 \
-XX:+UseParNewGC
-XX:+UseConcMarkSweepGC \
-XX:CMSInitiatingOccupancyFraction=35
application

·Throughput Collector 사용하기
신세대에서 -XX:UseParallelGC
옵션을 사용해서 Parallel Scavenge Collector를 활성화시킬 수 있다. 구세대는 기본적으로 Mark-Compact
Collector을 사용하기 때문에 명시할 필요가 없다.

32비트일 때:
java -server -Xms3072m -Xmx3072m
-XX:NewSize=2560m \
-XX:MaxNewSize=2560m XX:SurvivorRatio=2
\
-XX:+UseParallelGC application64비트일 때:
java -server -d64
-Xms8192m -Xmx8192m -XX:NewSize=7168m \
-XX:MaxNewSize=7168m
XX:SurvivorRatio=2 \
-XX:+UseParallelGC application

단, -XX:TargetSurvivorRatio는 신세대에서 보유하고 있는 객체를
복사하는 데에 사용되는 보유한계이다. 큰 heap과 SurvivorRatio가 2이면 TargetSurvivorRatio의 기본값이 50이기
때문에 survivor semi-space가 낭비될 수 있다. 이 값을 75나 90으로 조정하면 공간 활용이 극대화될
것이다.


– 병렬 정도 조정하기

Parallel Scavenge Collector 또한 CPU 개수만큼
쓰레드를 생성해 사용하지만 병렬의 정도를 조정해야 한다면 다음과 같이 변경할 수 있다.

-XX:ParallelGCThreads=<desired
parallelism>

기본값은 CPU의 개수와 동일하다. 예를 들어 신세대 컬렉션을 처리하는 데에 4개의
병렬 쓰레드를 사용하기 위해선 다음과 같이 하면 된다.

java -server -Xms3072m -Xmx3072m
-XX:NewSize=2560m \
-XX:MaxNewSize=2560m XX:SurvivorRatio=2
\
-XX:+UseParallelGC -XX:ParallelGCThreads=4
application


– 성능을 위한 적응형 크기 조절

Parallel
Scavenge Collector는 -XX:+UseAdaptiveSizePolicy를 사용할 때 성능이 더 좋다. 신세대의 크기를 자동으로
조정하고 최대 성능을 위한 최적화된 생존률을 설정해준다. Parallel Scavenge Collector는 항상
-XX:UseAdaptiveSizePolicy 옵션을 사용하는 게 좋다. 예를 들면 다음과 같다.

java -server -Xms3072m -XX:+UseParallelGC
\
-XX:+UseAdaptiveSizePolicy
application

 

 

 

 

출처 : http://blog.daum.net/bluelinu/8247868