# 機能設計書 85-JITコンパイル

## 概要

本ドキュメントは、JuliaのJIT（Just-In-Time）コンパイル機能の設計を記述する。LLVM ORC JIT フレームワークを使用して、実行時にメソッドをネイティブコードにコンパイルし、動的にリンクして実行する。

### 本機能の処理概要

JIT コンパイルは、Julia のメソッドが特定の型引数で初めて呼び出された際に、LLVM ORC JIT エンジンを使用してネイティブコードを生成・リンクする機能である。

**業務上の目的・背景**：Julia は「書きやすさ」と「速さ」の両立を目標とする言語であり、JIT コンパイルはその中核技術である。インタプリタ実行ではなく、初回呼び出し時にネイティブコードを生成して以後はそのコードを直接実行することで、動的言語でありながら高い実行性能を実現する。LLVM ORC JIT は遅延コンパイル、並列コンパイル、プロファイリング統合をサポートしており、Julia の要件に適合する。

**機能の利用シーン**：Julia のユーザーが関数を呼び出す全ての場面で透過的に動作する。初回呼び出し時にコンパイルが発生し、以後はキャッシュされたネイティブコードが直接実行される。型の異なる引数で呼び出された場合は、新しい特殊化がコンパイルされる。

**主要な処理内容**：
1. メソッド予約（`jl_engine_reserve`）: コンパイル中のメソッドの排他制御
2. LLVM Module の構築: codegen.cpp でのIR生成
3. LLVM 最適化パス: O0-O3 の最適化レベルに応じた変換
4. ネイティブコード生成: ターゲットアーキテクチャのマシンコード生成
5. リンク: シンボル解決とメモリへの配置
6. グローバル変数の内部化: 文字列プールへの定数の intern

**関連システム・外部連携**：コード生成（No.84）からの LLVM Module を入力とし、生成されたネイティブコードをランタイムが直接呼び出す。推論エンジン（engine.cpp）がコンパイルの並列性制御を行う。

**権限による制御**：特になし。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| - | - | - | 本機能はランタイム内部機能であり、直接的なUI画面は存在しない |

## 機能種別

計算処理（実行時コンパイル処理）

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| MethodInstance | jl_method_instance_t* | Yes | コンパイル対象のメソッド特殊化 | 有効なMethodInstanceであること |
| owner | jl_value_t* | No | オーバーレイメソッドテーブルのオーナー | NULLの場合はデフォルト |
| LLVM Module | orc::ThreadSafeModule | Yes | codegen で生成された LLVM Module | 有効な LLVM IR であること |

### 入力データソース

- 多重ディスパッチシステムからのメソッド解決結果
- codegen.cpp からの LLVM Module

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| 関数ポインタ（通常） | void* | 通常の関数呼び出し用ポインタ |
| 関数ポインタ（特殊化） | void* | 特殊化された関数呼び出し用ポインタ |
| CodeInstance | jl_code_instance_t* | コンパイル結果のキャッシュエントリ |

### 出力先

- CodeInstance に関数ポインタとして格納
- メソッドテーブルのキャッシュに登録

## 処理フロー

### 処理シーケンス

```
1. メソッド予約（jl_engine_reserve）
   └─ 排他ロック取得、デッドロック検出、CodeInstance プレースホルダ割当
2. 型推論の実行
   └─ 必要に応じて型推論と最適化を実行
3. LLVM Module の生成
   └─ codegen.cpp で Julia IR → LLVM IR 変換
4. LLVM 最適化パスの適用
   └─ O0/O1/O2/O3 に応じた最適化
5. ネイティブコード生成
   └─ LLVM のマシンコード生成器でターゲットコード生成
6. リンクとメモリ配置
   └─ ORC JIT によるシンボル解決とメモリ配置
7. CodeInstance の更新
   └─ 関数ポインタの設定とキャッシュ登録
8. メソッド予約の解放（jl_engine_complete）
   └─ 排他ロック解放、待機スレッドへの通知
```

### フローチャート

```mermaid
flowchart TD
    A[メソッド呼び出し] --> B{キャッシュにあるか?}
    B -->|Yes| C[キャッシュされた関数ポインタで呼び出し]
    B -->|No| D[jl_engine_reserve: 排他予約]
    D --> E{デッドロック検出}
    E -->|デッドロック| F[既存の不完全な CodeInstance を返却]
    E -->|OK| G[型推論・最適化]
    G --> H[LLVM Module 生成]
    H --> I[LLVM 最適化パス]
    I --> J[ネイティブコード生成]
    J --> K[リンク・メモリ配置]
    K --> L[CodeInstance 更新]
    L --> M[jl_engine_complete: 予約解放]
    M --> C
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-85-01 | 遅延コンパイル | メソッドは初回呼び出し時にJITコンパイルされる | 未コンパイルメソッドの呼び出し時 |
| BR-85-02 | デッドロック回避 | 循環的な推論依存がある場合、既存の不完全な CodeInstance を返却して循環を断ち切る | jl_engine_reserve 内 |
| BR-85-03 | ファイナライザ無効化 | 推論中はファイナライザが無効化される（engine_nqueued でカウント） | jl_engine_reserve 〜 complete 間 |
| BR-85-04 | グローバル定数の intern | 文字列定数等はグローバル文字列プールに intern される | リンク時 |
| BR-85-05 | 統計収集 | SpecFPtrCount, UnspecFPtrCount, ModulesAdded 等の統計がLLVM STATISTICで収集される | 常時 |

### 計算ロジック

特になし。

## データベース操作仕様

本機能はデータベースを使用しない。

### 操作別データベース影響一覧

該当なし。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| - | デッドロック検出 | 循環的な推論依存 | 不完全な CodeInstance を返却して推論を進める |
| - | LLVM エラー | コード生成/最適化でのLLVM内部エラー | abort（致命的エラー） |
| - | リンクエラー | シンボル解決失敗 | abort（致命的エラー） |

### リトライ仕様

該当なし。デッドロック検出時は不完全な結果を返却して続行。

## トランザクション仕様

`jl_engine_reserve` / `jl_engine_complete` がトランザクション的な排他制御を提供する。

## パフォーマンス要件

- 初回コンパイル時間（TTFX: Time To First eXecution）は Julia のユーザー体験に直結
- 最適化レベルは O0-O3 で選択可能（デフォルト O2）
- 並列コンパイルにより複数スレッドで同時にコンパイル可能（engine.cpp の予約機構）

## セキュリティ考慮事項

- JIT コンパイルはメモリの実行可能フラグを設定するため、W^X ポリシーとの互換性に注意
- MSan（MemorySanitizer）との互換性のため、MSAN_EMUTLS_WORKAROUND が提供されている

## 備考

- Perf/VTune/GDB との統合プラグインにより、JIT コンパイルされたコードのプロファイリングが可能
- `LinkedGlobals`, `InternedGlobals` 等のLLVM統計で内部動作を監視可能

---

## コードリーディングガイド

本機能を理解するために参照すべきファイルと、推奨する読み解き順序を以下に示す。

### 推奨読解順序

#### Step 1: データ構造を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | engine.cpp | `src/engine.cpp` | ReservationInfo / InferKey 構造体（14-22行目）: 推論予約の管理データ |
| 1-2 | engine.cpp | `src/engine.cpp` | Reservations / Awaiting（48-53行目）: グローバルな予約テーブル |
| 1-3 | jitlayers.h | `src/jitlayers.h` | JIT レイヤーの型定義 |

**読解のコツ**: engine.cpp の予約機構は `std::mutex` と `std::condition_variable` を使用した典型的な条件変数パターンである。`Reservations` は DenseMap でメソッドインスタンス→予約情報のマッピングを保持し、`Awaiting` は各スレッドが待機中の推論キーを記録する。

#### Step 2: エントリーポイントを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | engine.cpp | `src/engine.cpp` | jl_engine_reserve 関数（60行目〜）: メソッドコンパイルの排他予約 |
| 2-2 | jitlayers.cpp | `src/jitlayers.cpp` | STATISTIC定数（72-81行目）: JIT 統計情報の定義 |

**主要処理フロー**:
1. **60-63行目**: engine_nqueued をインクリメント（ファイナライザ無効化）
2. **64行目**: jl_new_codeinst_uninit でプレースホルダ CodeInstance を割当
3. **67-76行目**: Reservations テーブルに予約登録。既に他スレッドが処理中なら待機
4. **78-80行目**: デッドロック検出: 待機スレッドが保持する lease を再帰的に追跡

#### Step 3: JIT レイヤーの構造を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | jitlayers.cpp | `src/jitlayers.cpp` | MSan ワークアラウンド（83-99行目）: TLS リロケーションの問題回避 |
| 3-2 | jitlayers.cpp | `src/jitlayers.cpp` | ORC JIT の初期化とモジュール追加 |

### プログラム呼び出し階層図

```
メソッド呼び出し (runtime dispatch)
    |
    +-- jl_engine_reserve (engine.cpp)
    |      +-- デッドロック検出
    |      +-- CodeInstance 割当
    |
    +-- 型推論 (abstractinterpretation.jl)
    +-- 最適化 (optimize.jl)
    +-- codegen (codegen.cpp)
    |      +-- emit_function
    |      +-- LLVM Module 構築
    |
    +-- JIT コンパイル (jitlayers.cpp)
    |      +-- LLVM 最適化パス
    |      +-- ネイティブコード生成
    |      +-- ORC JIT リンク
    |
    +-- jl_engine_complete (engine.cpp)
           +-- 予約解放
           +-- 待機スレッド通知
```

### データフロー図

```
[入力]                      [処理]                       [出力]

MethodInstance      --> jl_engine_reserve          --> CodeInstance (placeholder)
CodeInfo            --> codegen                    --> LLVM Module
LLVM Module         --> LLVM Optimization          --> Optimized LLVM Module
Optimized Module    --> Native Code Generation     --> Machine Code
Machine Code        --> ORC JIT Link              --> Function Pointer
Function Pointer    --> CodeInstance Update        --> Cached Native Code
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| jitlayers.cpp | `src/jitlayers.cpp` | ソース | LLVM ORC JIT レイヤーの実装 |
| engine.cpp | `src/engine.cpp` | ソース | 推論・コンパイルの並列性制御 |
| jitlayers.h | `src/jitlayers.h` | ヘッダ | JIT レイヤーの型定義・インタフェース |
| codegen.cpp | `src/codegen.cpp` | ソース | Julia IR → LLVM IR 変換 |
| llvm-julia-task-dispatcher.h | `src/llvm-julia-task-dispatcher.h` | ヘッダ | JuliaタスクベースのLLVMディスパッチャー |
| processor.h | `src/processor.h` | ヘッダ | ターゲットプロセッサの検出 |
