바이트코드
바이트코드(Bytecode)는 특정 CPU 대신 가상 머신이나 언어 런타임이 이해하도록 정의된 명령어 형태의 프로그램 표현이다. 컴파일러가 고수준 소스를 JVM 클래스 파일·.NET CIL 또는 WebAssembly 같은 형식으로 변환한 뒤, 실행기는 이를 해석하거나 JIT·AOT 컴파...
| 영어 명칭 | Bytecode |
|---|---|
| 분류 | 가상 머신·언어 실행기의 명령 표현 |
| 주요 예시 | JVM bytecode·.NET CIL·WebAssembly |
| 생성 | 컴파일러가 언어 소스 등에서 변환 |
| 실행 | 가상 머신 해석·JIT·AOT 변환 |
| 구조 | 명령어·타입·상수 풀과 모듈 메타데이터 등 |
| 다양성 | 스택 기반·레지스터 기반 및 가상 ISA별 |
| 성질 | 기계어처럼 단일 범용 표준을 의미하지 않음 |
| 참조 | Java Virtual Machine Specification |
| Wasm | WebAssembly Core Spec |
바이트코드(Bytecode)는 특정 CPU 대신 가상 머신이나 언어 런타임이 이해하도록 정의된 명령어 형태의 프로그램 표현이다. 컴파일러가 고수준 소스를 JVM 클래스 파일·.NET CIL 또는 WebAssembly 같은 형식으로 변환한 뒤, 실행기는 이를 해석하거나 JIT·AOT 컴파일하여 실제 하드웨어에서 실행할 수 있다. 바이트코드라는 명칭을 사용해도 반드시 모든 명령어가 정확히 1바이트 길이는 아니며 각 가상 ISA는 별도의 명세를 갖는다.[1]
JVM 바이트코드는 스택 기반 명령어와 클래스·메서드·상수 풀 등의 메타데이터를 사용한다. .NET의 공통 중간 언어(CIL)는 CLR 실행을 위한 명령과 타입·어셈블리 메타데이터를 정의하며 WebAssembly는 모듈·함수·메모리 및 검증 가능한 명령 체계를 갖는다. 세 체계는 모두 바이트코드라는 범주에 속할 수 있지만 서로의 실행기가 같은 바이너리를 직접 이해하지는 못한다.
바이트코드의 장점은 소스 언어와 하드웨어 사이에 독립적인 실행 계약을 제공할 수 있다는 점이다. 그러나 하드웨어 독립성이 무제한인 것은 아니며 실행기·표준 라이브러리·운영체제 접근 권한과 호스트 API에 영향을 받는다. 실제로 바이트코드를 JIT 컴파일하면 실행 중 프로파일에 맞춰 최적화할 수 있고 AOT 방식은 설치나 배포 전에 네이티브 코드를 준비한다.[2]
컴파일러 내부의 중간 표현(IR)과 바이트코드의 역할도 구분해야 한다. LLVM IR처럼 최적화·분석과 코드 생성을 위해 설계된 표현은 특정 런타임용 안정적인 배포 포맷과 같지 않다. 반면 바이트코드를 내부 IR로 읽어 다른 백엔드로 출력하는 컴파일러를 만들 수 있으므로 두 개념이 항상 상호 배타적인 것도 아니다.