JAVA,객체지향

java JIT 컴파일러

25G 2023. 9. 6. 16:55

JIT 컴파일러란?

JIT (just-in-time,JIT) 컴파일러는 JVM의 핵심입니다. JVM내에서 컴파일러보다 성능에 더 영향을 주는 요소는 없습니다.
대부분의 상황에서 티어드 컴파일(tiered compilation)을 사용하기만 해도 튜닝할 필요는 거의 없습니다.

컴파일과 인터프리트

CPU는 어셈블리나 바이너리 코드라고 불리는 특정 명령어만 실행시킬 수 있습니다. 그 말은 CPU가 실행하는 모든 프로그램은 이 명령어 들로 변환이 가능합니다.
C++같은 언어들은 바이너리로 컴파일된 코드로 실행되어 컴파일형 언어라고 불립니다.
즉 프로그램이 작성되고 정적 컴파일러는 바이너리를 생성합니다. 그 바이너리 내의 어셈블리 코드는 특정 CPU만을 대상으로 합니다.
반면 PHP나 Perl과 같은 언어는 인터프리트 됩니다. 동일한 프로그램 소스 코드는 머신이 같은 인터프리터라고 불리는 프로그램을 갖고 있으면 어떤 CPU에서든 실행이 가능합니다.

인터프리터 언어는 각 라인이 실행되면서 프로그램의 각 코드를 한 줄 씩 바이너리 코드로번역합니다.

컴파일언어와 인터프리터 언어의 차이점

인터프리터 언어로 작성된 프로그램은 컴파일 언어보다 이식성이 높습니다. 동일한 코드를 짜서 작성한 인터프리터가 있는 머신에 올리고 실행 시킬 수 있습니다.

하지만
컴파일언어보다 빠르게 실행되지는 않습니다. 예를들어 루프를 도는 코드가 있다고하면 인터프리터언어는 루프를할때마다 변역하는 과정이 필요하지만 컴파일언어는 그럴필요가 없어지는 것입니다.

그리고 바이너리를 생성할 때 컴파일러가 할 수 있는 역할은 더 많습니다.
그 중 관련된건 바이너리 문장의 순서입니다. 모든 어셈블리 언어 명령어는 실행하는데 동일한 시간이 걸리지 않는다.
두개의 레지스터 내에서 저장된 값을 더하는 문장은 한번 실행되지만 덧셈에 필요한 값을 메모리에서 조회하는데는 여러번의 주기를 가질 것입니다.

그렇기 대문에 컴파일러는 이러한 문장의 순서를 이해하고 먼저 데이터를 로딩하기 위한 어셈블리 명령을 실행한 후 덧셈을 하도록 순서를 바꿀 것입니다.

하지만
인터프리터 언어는 메모리에서 데이터를 요청하고 이용할 때 까지 기다린 다음 덧셈을 할 것입니다.
이러한 이유들로 인터프리터 언어는 컴파일된 코드보다 언제나 느릴수 밖에 없다.

자바는 이둘의 차이점에서 절충안을 찾으려 합니다.

자바 애플리케이션은 컴파일되지만 특정 CPU에 맞는 특정 바이너리로 컴파일 되는 게 아니라 대신 최적화된 어셈블리 언어인 바이트 코드로 컴파일됩니다.
이는 JVM이 있는 환경이라면 어디서든 실행시킬 수 있는 독립적인 플랫폼을 제공합니다 .그리고 JVM 내의 인터프리터로 최적화된 바이트 코드를 실행하면서 JIT 컴파일러로 바이너리로 컴파일 할 수 있습니다.