Ruby용 AOT 컴파일러 개발 현황 및 성능 평가

[29S04] AOT Compiler for Ruby (ja)

작성자
RubyKaigi
발행일
2025년 10월 05일

핵심 요약

  • 1 Ruby 스크립트를 C 언어로 미리 컴파일하는 AOT 컴파일러를 개발 중이며, Ruby 1.9 런타임과 협력하여 동작합니다.
  • 2 개발된 컴파일러는 Ruby 1.9 테스트의 대부분을 통과하여 높은 호환성과 이식성을 보였으나, 매크로 벤치마크에서는 성능 저하가 발생했습니다.
  • 3 주요 과제는 과도하게 커지는 생성 코드 크기를 줄여 캐시 미스 문제를 해결하고 컴파일 시간을 단축하는 것입니다.

도입

도쿄 대학의 시바 연구원은 Ruby 프로그래밍 언어의 성능 향상을 목표로 Ruby용 AOT(Ahead-Of-Time) 컴파일러를 개발 중입니다. 이 컴파일러는 프로그램 실행 전에 Ruby 스크립트를 C 언어로 변환하여 미리 컴파일하며, 기존 Ruby 1.9 런타임 환경과의 호환성을 유지하면서 저수준 언어 변환을 통한 고속화를 추구합니다. 본 발표에서는 이 AOT 컴파일러의 사용법, 동작 방식, 개발 계획, 그리고 현재까지의 예비 성능 평가 결과를 공유합니다.

AOT 컴파일러 개요 및 동작 방식

  • 목표: Ruby 1.9 호환성을 유지하며 Ruby 스크립트를 C 언어로 변환하여 고속화하고, 궁극적으로 CRuby에 통합하는 것을 목표로 합니다.

  • 변환 단위: YARV 바이트코드 시퀀스 하나당 1~2개의 C 함수를 생성합니다. 클래스, 예외 처리, 메서드, 블록 등이 각각 하나의 바이트코드 시퀀스에 해당합니다.

  • 변환 방법: 바이트코드에 대응하는 C 소스 코드 템플릿을 붙여넣는 방식으로 변환합니다. VM 생성기를 통해 템플릿을 자동 생성하며, 리터럴 임베딩, 프로그램 카운터 및 스택 조작 최적화, 예외 처리 등 실행 빈도가 낮은 부분 제외를 통해 코드 크기를 줄이려는 시도를 합니다.

  • 런타임: 확장된 Ruby 1.9 런타임(약 100줄의 변경)이 필요하며, AOT 컴파일러는 VM 실행 부분만 담당하고 GC, 내장 메서드, 클래스 등은 기존 런타임에 위임합니다.

  • 출력 형식: 단일 실행 파일 또는 공유 라이브러리 형태로 생성되며, 컴파일되지 않은 Ruby 코드와 혼용하여 사용 가능합니다.

개발 계획 및 평가 항목

  • 개발 단계:
    1. 호환성 및 이식성 확보 (Ruby 1.9 테스트 통과, 다중 환경 동작) - 완료
    2. 간단한 C 코드 최적화 (데이터 흐름/타입 정보 불필요한 최적화) - 완료
    3. 프로파일 정보(실행 시 타입 정보, 빈번한 실행 경로)를 활용한 고급 최적화 - 향후 계획
  • 평가 항목: Ruby 1.9 호환성, 이식성, 실행 속도, 생성 바이너리 크기, 컴파일 시간.

예비 평가 결과

  • 호환성 및 이식성:
    • 535개 테스트 파일 중 533개 컴파일 성공. 2개 파일은 생성된 C 코드(25만 줄 이상)로 인해 GCC 메모리 부족 오류 발생.
    • 7850개 테스트 중 7847개 통과. 높은 호환성을 보였으며, 5가지 OS와 2가지 아키텍처에서 Rails 및 RDoc 실행에 성공하여 이식성도 입증.
  • 실행 속도:
    • 마이크로 벤치마크: 피보나치 수열 계산에서 최대 3.5배 속도 향상 등 전반적인 속도 개선 확인.
    • 매크로 벤치마크 (Rails): Apache Bench를 사용한 Rails 최상위 페이지 표시에서 오히려 약간의 속도 저하 발생. 이는 AOT 컴파일러가 최적화하는 VM 실행 시간이 전체의 15~20%에 불과하며, 과도하게 큰 생성 코드(캐시 미스 유발)가 다른 부분의 성능까지 저하시킨 것으로 분석.
  • 바이너리 크기 및 컴파일 시간:
    • 마이크로 벤치마크: 단일 스크립트의 경우 바이너리 크기(수십 KB) 및 컴파일 시간(수십 초)은 수용 가능한 수준.
    • 매크로 벤치마크 (전체 라이브러리):
      • lib 디렉토리 (CRuby 라이브러리): 컴파일 시간 95분, 바이너리 크기 109MB.
      • lib + test 디렉토리: 총 컴파일 시간 5시간.
    • 문제점: 디렉토리 단위 컴파일 시 바이너리 크기가 100MB를 쉽게 초과하고, 컴파일 시간이 3~5시간에 달하는 심각한 문제 발생. 이는 생성 코드 크기가 지나치게 크기 때문으로 판단.

결론

현재 개발 중인 Ruby용 AOT 컴파일러는 Ruby 1.9 환경에서 높은 수준의 호환성과 이식성을 확보했으며, 마이크로 벤치마크에서는 유의미한 속도 향상을 달성했습니다. 그러나 매크로 벤치마크에서의 성능 저하와 과도한 컴파일 시간 및 바이너리 크기는 주요 해결 과제로 남아 있습니다. 이는 주로 C 언어로 변환된 코드의 크기가 너무 커서 발생하는 캐시 미스와 컴파일 오버헤드 때문으로 분석됩니다. 향후 개발은 코드 크기 최적화에 중점을 두고 프로파일링 정보를 활용한 추가적인 최적화를 통해 실용적인 고성능 Ruby 실행 환경을 구축하는 방향으로 진행될 예정입니다.

댓글 0

댓글 작성

0/1000
정중하고 건설적인 댓글을 작성해 주세요.

아직 댓글이 없습니다

첫 번째 댓글을 작성해보세요!