-
JIT(Just In Time) Compilation개발/기술 2021. 11. 26. 20:10
기존 정적 컴파일 방식에서는 실행 전 소스 코드를 모두 기계어로 번역해야 했다면 JIT 컴파일러는 코드를 런타임에 기계어로 번역한다.
인터프리터도 런타임에 소스코드를 기계어로 변환해서 비슷하다고 볼 수 있으나 JIT 가 컴파일 하는 대상은 소스 코드가 아니라 최적화를 한번 거친 바이트 코드다. 바이트코드는 기계어는 아니지만 JVM 같은 가상 머신에서 쉽게 기계어로 변환할 수 있는 코드이며 이 과정이 실시간으로 일어나기 때문에 JIT(Jut In Time) 이라고 부른다. Java 개발자가 빌드해서 만든 바이너리는 기계어로 된 파일이 아니라 JVM에서 돌릴 수 있는 바이트 코드 덩어리다. 이 바이트 코드 덩어리가 JVM에 올라가면 내부 JIT 컴파일러에서 바이트 코드를 기계어로 변역해서 실행하게 된다.
JIT 컴파일러는 전체 프로젝트 파일을 기계어로 번역하지 않고 함수 단위나 파일 단위로 바이트 코드를 기계어로 번역한다. 그래서 실행 중 모든 바이트 코드를 기계어로 변환하는 것이 아니라 호출된 함수나 파일만 번역되게 된다. 그리고 이미 번역된 기계어의 경우 캐싱에 남겨둬 동일한 함수를 여러번 호출하는 경우 다시 컴파일 하는게 아니라 기존에 번역한 코드를 재사용한다. 최적화 작업을 거치게 되기 때문에 오버헤드가 최소화 된다.
물론 실행전에 모두 기계어로 번역한 정적 컴파일 방식에 비해선 성능이 좋지 않다. 특히 애플리케이션을 처음 시작 할 때 눈에 띌만한 딜레이가 있는데 이것은 바이트 코드를 불러오고 기계어로 컴파일 하는 과정에서 발생하게 된다. 메모리나 CPU의 제약이 있는 경우, 프로그램 특성상 빠른 시작시간과 일관된 성능이 중요한 경우에는 적용하기가 좋지 않다.
하지만 JIT 컴파일러를 사용할 경우 개발자로선 이점이 많다. 우선 빌드 과정이 간소화된다. 모두 기계어로 번역해야하는 경우 하드웨어 아키텍처 별로 모두 따로 빌드해야하기 때문에 관리가 어렵고 프로젝트 규모가 커질수록 기계어로 번역하는 빌드 과정에서 소요되는 시간도 길어진다. 반면 바이트 코드를 사용하면 최적화된 컴파일러를 사용해 빌드 소요 시간을 줄일 수 있고 기계어로 번역하는 과정을 JIT 컴파일러에게 일임 할 수 있어 아키텍처별로 따로 빌드를 할 필요가 없어진다.
그리고 몇몇 VM의 경우 JIT 컴파일러를 이용해 Hot Reload 옵션을 제공한다. Hot Reload 는 소스코드 재 컴파일 과정 없이 내가 현재 작성하고 있는 코드 수정사항을 바로 화면에서 업데이트해 볼 수 있는 기능을 말한다. 플러터를 경험한 개발자라면 내가 수정한 코드가 빌드 없이 바로 화면상에 반영되는 것이 이런 원리다. 플러터 상에선 Dart VM에서 업데이트된 소스코드 부분에 대해서 바이트 코드로 변환하고 JIT 컴파일러로 바로 기계어로 변환하는 과정을 거쳤기 때문이다. 안드로이드 스튜디오 상에선 Instant Run도 JIT Compiler를 이용한 기능이다.
'개발 > 기술' 카테고리의 다른 글
log4j 이슈 살펴보기 (1) 2021.12.13 AOT(Ahead Of Time) Compiler (0) 2021.11.26 명령형 UI vs 선언형 UI (0) 2021.11.26 Kafka - Event Streaming Platform (0) 2021.10.13 JAVA 파일 생성/읽기/쓰기 (0) 2018.11.25