# 機能設計書 74-インクリメンタルコンパイル

## 概要

本ドキュメントは、Zigコンパイラにおけるインクリメンタルコンパイル機能の設計を記載する。この機能は、ソースコードの変更時に変更された部分のみを再コンパイルすることで、ビルド時間を大幅に短縮する。

### 本機能の処理概要

インクリメンタルコンパイルは、Zigコンパイラの高速再コンパイル機能である。ソースファイルの変更を検出し、変更の影響を受ける部分のみを再コンパイルすることで、フルビルドと比較して大幅にコンパイル時間を短縮する。`-fincremental`オプションにより有効化される。

**業務上の目的・背景**：大規模なプロジェクトでは、わずかなコード変更でもフルビルドに長時間かかることがある。インクリメンタルコンパイルにより、開発者は迅速なフィードバックループを維持でき、開発効率が大幅に向上する。特にイテレーティブな開発やデバッグ作業で効果を発揮する。

**機能の利用シーン**：
- 開発中のコード変更時に高速な再コンパイルが必要な場合
- テスト駆動開発でのテスト・実装サイクルを高速化したい場合
- デバッグ時に頻繁にコードを変更して動作確認する場合
- ホットリロードのような開発体験を実現したい場合

**主要な処理内容**：
1. `-fincremental`オプションの解析と有効化
2. 前回のコンパイル結果のキャッシュ読み込み
3. ソースファイルの変更検出
4. 依存関係の分析と影響範囲の特定
5. 変更された部分のみの再コンパイル
6. リンカによる差分リンク（use_new_linkerと連動）
7. キャッシュの更新

**関連システム・外部連携**：
- ファイルシステム：ソースファイルの変更検出
- キャッシュシステム：コンパイル結果のキャッシュ管理
- リンカ：インクリメンタルリンキング（新リンカ）

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

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 3 | 実行ファイルビルド画面 | 補助機能 | -fincremental オプション使用時の高速再コンパイル処理 |

## 機能種別

コンパイル最適化 / キャッシュ管理 / パフォーマンス向上

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| -fincremental | フラグ | No | インクリメンタルコンパイルを有効化 | なし |
| -fno-incremental | フラグ | No | インクリメンタルコンパイルを無効化 | なし |

### 入力データソース

- コマンドライン引数
- ソースファイル
- 前回のコンパイルキャッシュ

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| 実行可能ファイル/ライブラリ | バイナリ | コンパイル・リンク結果 |
| キャッシュデータ | バイナリ | 次回のインクリメンタルビルド用キャッシュ |

### 出力先

- 指定された出力パス（実行可能ファイル等）
- キャッシュディレクトリ

## 処理フロー

### 処理シーケンス

```
1. オプション解析
   └─ -fincremental/-fno-incrementalの判定
2. 設定解決
   └─ Config.resolveでincremental設定を反映
   └─ incrementalがtrueの場合、use_new_linkerも連動して有効化
3. コンパイル開始
   └─ Compilation.createでインクリメンタルモードを設定
4. キャッシュ確認
   └─ 前回のコンパイル結果があるか確認
   └─ ある場合は差分コンパイルモードに移行
5. 変更検出
   └─ ソースファイルのタイムスタンプ/ハッシュを比較
   └─ 変更されたファイルを特定
6. 依存関係分析
   └─ 変更ファイルに依存する他のモジュールを特定
7. 差分コンパイル
   └─ 変更されたモジュールのみを再コンパイル
8. 差分リンク
   └─ 新リンカによるインクリメンタルリンキング
9. キャッシュ更新
   └─ 新しいコンパイル結果をキャッシュに保存
```

### フローチャート

```mermaid
flowchart TD
    A[開始] --> B{-fincremental?}
    B -->|No| C[通常コンパイル]
    B -->|Yes| D[インクリメンタルモード設定]
    D --> E{前回キャッシュ存在?}
    E -->|No| F[フルビルド実行]
    E -->|Yes| G[変更ファイル検出]
    G --> H{変更あり?}
    H -->|No| I[キャッシュ結果を使用]
    H -->|Yes| J[依存関係分析]
    J --> K[影響範囲特定]
    K --> L[差分コンパイル]
    L --> M[差分リンク]
    M --> N[キャッシュ更新]
    C --> O[終了]
    F --> N
    I --> O
    N --> O
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-74-01 | 新リンカ連動 | incremental有効時はuse_new_linkerもデフォルトで有効 | incremental=true時 |
| BR-74-02 | キャッシュモード | インクリメンタルモードはキャッシュに依存 | incremental=true時 |
| BR-74-03 | LLD非互換 | LLDはインクリメンタルリンキングをサポートしない | LLD使用時 |

### 計算ロジック

特になし

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

本機能ではデータベース操作は行わない。キャッシュはファイルシステム上で管理される。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| LldCannotIncrementallyLink | 設定エラー | LLDとインクリメンタルの同時使用 | 新リンカを使用するか、インクリメンタルを無効化 |
| NewLinkerIncompatibleWithLld | 設定エラー | 新リンカとLLDの競合 | どちらか一方を選択 |

### リトライ仕様

キャッシュ破損時はフルビルドにフォールバック

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

該当なし

## パフォーマンス要件

- 差分コンパイルは変更されたファイル数に比例した時間で完了すること
- フルビルドと比較して、小規模な変更で80%以上の時間短縮が期待される

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

- キャッシュデータの改ざんにより不正なコードが実行される可能性
- 信頼できないキャッシュは使用しないこと

## 備考

- インクリメンタルコンパイルはZig 0.14.0以降で安定化を目指している
- 現時点では全てのターゲットでサポートされているわけではない
- CIビルドでは-fno-incrementalを推奨（再現性確保のため）

---

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

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

### 推奨読解順序

#### Step 1: 設定オプションを理解する

インクリメンタルコンパイルの設定がどのように解決されるかを理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | Config.zig | `src/Compilation/Config.zig` | incremental設定フィールドとOptions.incremental |

**読解のコツ**:
- **53行目**: `incremental: bool`フィールドの定義
- **110行目**: `Options.incremental: bool = false`（デフォルト値）
- **448-454行目**: `use_new_linker`がincrementalに連動して有効化される条件

#### Step 2: コマンドライン解析を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | main.zig | `src/main.zig` | -fincremental/-fno-incrementalの解析 |

**主要処理フロー**:
- **429行目**: ヘルプ表示での-fincremental/-fno-incrementalの説明
- コマンドライン引数の解析でincremental設定を取得

#### Step 3: Compilation設定を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | Compilation.zig | `src/Compilation.zig` | incremental設定の使用箇所 |

**主要処理フロー**:
- Compilation構造体でのincremental設定の保持
- config.incrementalに基づくコンパイル動作の分岐

#### Step 4: リンカとの連携を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | link.zig | `src/link.zig` | インクリメンタルリンキングの処理 |
| 4-2 | Elf.zig | `src/link/Elf.zig` | ELFフォーマットでのインクリメンタル処理 |

**読解のコツ**: 新リンカ（use_new_linker）がインクリメンタルリンキングの鍵となる。

#### Step 5: キャッシュシステムを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 5-1 | Cache.zig | `lib/std/Build/Cache.zig` | キャッシュディレクトリ管理 |

**読解のコツ**: インクリメンタルコンパイルはキャッシュシステムに大きく依存している。

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

```
main.zig::buildOutputType()
    │
    ├─ 引数解析 (-fincremental/-fno-incremental)
    │
    └─ Compilation.create()
           │
           ├─ Config.resolve()
           │      └─ incremental設定の解決
           │      └─ use_new_linkerの連動設定
           │
           ├─ [incremental=true]
           │      ├─ キャッシュ読み込み
           │      ├─ 変更検出
           │      ├─ 差分コンパイル
           │      └─ 差分リンク
           │
           └─ [incremental=false]
                  └─ 通常のフルビルド
```

### データフロー図

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

ソースファイル ───────▶ 変更検出
                            │
前回キャッシュ ───────▶    │
                            ▼
                      依存関係分析
                            │
                            ▼
                      差分コンパイル ───────────▶ 中間ファイル
                            │                      (更新分)
                            ▼
                      差分リンク ─────────────▶ 実行ファイル
                            │
                            ▼
                      キャッシュ更新 ─────────▶ 新キャッシュ
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| Config.zig | `src/Compilation/Config.zig` | ソース | incremental設定の定義と解決 |
| main.zig | `src/main.zig` | ソース | コマンドラインオプション解析 |
| Compilation.zig | `src/Compilation.zig` | ソース | コンパイル処理本体 |
| link.zig | `src/link.zig` | ソース | リンカ統合 |
| Elf.zig | `src/link/Elf.zig` | ソース | ELFインクリメンタルリンク |
| MachO.zig | `src/link/MachO.zig` | ソース | Mach-Oインクリメンタルリンク |
| Wasm.zig | `src/link/Wasm.zig` | ソース | WASMインクリメンタルリンク |
| Cache.zig | `lib/std/Build/Cache.zig` | ソース | キャッシュ管理 |
| IncrementalDebugServer.zig | `src/IncrementalDebugServer.zig` | ソース | デバッグサーバー統合 |
