JVM의 Garbage Collector
10분 테코톡 - 던님의 "JVM의 Garbage Collector"를 시청하고 작성한 글입니다.
JVM이란 Java Virtual Machine으로 운영체제의 메모리 영역에 접근하여 메모리 관리하는 프로그램이다. 메모리 관리, Garbage Collector 역할을 수행한다.
Garbage Collector
동적으로 할당한 메모리 영역 중 사용하지 않는 영역을 탐지하여 해제하는 기능을 담당한다.
여기서 말하는 동적으로 할당한 메모리 영역은, Heap을 뜻한다. Heap에는 모든 Object 타입의 데이터가 할당되고 Heap영역의 Object를 가리키는 참조 변수가 Stack에 할당된다.
Stack은 정적으로 할당한 메모리 영역으로, Stack에는 원시 타입의 데이터가 값과 함께 할당되고 Heap영역에 생성된 Object 타입의 데이터의 참조 값이 할당된다.
public class Hello {
public static void main(String[] args) {
int num1 = 10;
int num2 = 5;
int sum = num1 + num2;
String name = "던";
}
}
- 해당 클래스의 메인 메서드가 실행될 때 int와 같은 원시 타입의 데이터는 Stack영역에 그림과 같이 값과 함께 할당, 또한 Heap영역의 참조 변수도 할당
- String과 같은 Object 타입(객체) 데이터는 Heap영역에 그림과 같이 할당
- 메인 메서드가 종료되면 Stack영역은 모두 pop되어 사라지지만 Heap영역의 데이터(객체)들은 사라지지 않고 남아있게 된다.
- 존재하지만 접근할 수 없기 때문에 Unreachable Object라고 부르고 이것이 바로 GC의 대상이다.
Garbage Collector 과정
- Garbage Collector가 Stack의 모든 변수를 스캔하면서 각각 어떤 객체를 참조하고 있는지 찾아서 마킹
- Reachable Object가 참조하고 있는 객체도 찾아서 마킹한다.
- 마킹되지 않은 객체를 Heap에서 제거한다. ==> 마킹되지 않은 것이 바로 Unreachable Object
1,2번 과정이 마킹을 한다는 뜻에서 Mark 라고 하고, 3번 과정을 쓸어내린다라는 뜻에서 Sweep 이라고 한다. Garbage Collector의 과정을 Mark & Sweep이라고 한다.
Garbage Collection은 언제 일어날까?
Heap의 구조는 아래와 같다.
Heap은 크게 New Generation 영역과 Old Generation 영역으로 나누어진다. 먼저 New Generation을 살펴보자.
New Generation 영역은 Eden, Survival 0, Survial 1으로 다시 나누어져있는데, 새로운 객체가 생성되면 Eden 영역에 할당된다.
계속 할당되다가 Eden영역의 메모리가 가득 차면 GC(Garbage Collection)가 발생한다. 이 때의 GC를 Minor GC라고 한다.
Eden영역에서 GC를 통해 Mark&Sweep이 발생하고 그 중에 살아남은 객체(Reachable Object)는 Survival 0영역으로 옮겨진다. 이 과정이 계속해서 반복된다.
반복이 되다가 Survival 0 또한 마찬가지로 가득 차게되면, Survival 0 영역에 대해서도 Mark&Sweep 과정이 수행된다.
Survival 0영역의 GC에서 살아남은 객체들은 Survival 1영역으로 이동하게 되고, 이동한 객체는 Age 값이 증가한다.
이 때 중요한 것이 두 Survival영역 중 하나는 반드시 아무것도 없는 빈 상태여야 한다는 것이다. 즉, 위의 과정에서 Survival 0영역이 가득차 GC를 수행하고 살아남은 객체를 Survival 1영역으로 이동시킨다고 했는데, 이동을 하고 나면 Survival 0는 아무것도 없는 빈 상태가 된다. 추가로 Eden영역이 또 가득찬다면 GC를 수행하고 살아남은 객체는 비어있지 않은 Survival 1영역으로 이동하는 것이다. 이 과정이 반복해서 수행된다.(반대로 Survival 1이 가득차면 GC 수행하고 살아남은 객체 Survival 0로 이동)
이 과정이 반복되다가 객체의 Age 값이 특정 값 이상이되면 Old Generation영역으로 옮겨지는데 이 과정을 Promotion이라고 한다. 이 Old Generation영역이 가득차게되면 GC가 발생하는데 이는 Major GC라고 한다.
이런 과정이 반복되면서 Garbage Collector가 메모리를 관리하는 것이다!!!
Garbage Collector 종류
1. Serial GC
GC를 처리하는 스레드가 1개이다. CPU 코어가 적을 때 사용하는 방식이다.
Mark-compact collection 알고리즘을 사용한다.
- Mark&Sweep과정 이후에 Compact과정을 통해 메모리 파편화를 방지하는 알고리즘이다.
2. Parallel GC
GC를 처리하는 스레드가 여러개이다. 메모리가 충분하고 코어의 개수가 많을 때 사용하면 좋다.
아래 그림은 Serial GC와 Parallel GC의 스레드를 비교한 그림이다.
3. Concurrent Mark Sweep GC (CMS GC)
Stop-The-World : GC를 실행하기 위해 JVM이 애플리케이션 실행을 멈추는 것, GC를 실행하는 스레드를 제외한 스레드는 모두 작업을 멈추고 GC 완료 후에 다시 시작한다.
쉽게 말해 Stop-The-World시간을 줄이는 GC이다. 애플리케이션의 응답 시간이 빨라야할 때 사용하면 좋다.
하지만 다른 GC 방식보다 메모리와 CPU를 더 많이 사용하고 Compaction단계가 제공되지 않는다는 단점이 존재한다.
4. G1 GC
각 영역을 Region 영역으로 나누고, GC가 일어날 때 전체 영역(Eden, Survival, Old generation)을 탐색하지 않는다.
G1 GC는 바둑판의 각 영역에 객체를 할당하고 GC를 실행한다. 해당 영역이 꽉 차면 다른 빈 영역에 객체를 할당하고 GC를 실행한다.
Stop-The-World이 짧고, Compaction을 사용한다는 장점이 존재한다.
참고
'테코톡 스터디' 카테고리의 다른 글
교착상태 (0) | 2021.07.23 |
---|---|
트랜잭션 (0) | 2021.07.17 |
웹서버 vs WAS (0) | 2021.07.13 |
Spring IoC/DI (0) | 2021.07.13 |