# 帳票設計書 2-ZIRデバッグ出力

## 概要

本ドキュメントは、Zigコンパイラにおける ZIR（Zig Intermediate Representation）デバッグ出力帳票の設計仕様を記述するものである。ZIRはZigソースコードから生成される中間表現であり、本帳票はその内容を人間が読みやすいテキスト形式で出力する機能を定義する。

### 本帳票の処理概要

ZIRデバッグ出力は、Zigソースコードがコンパイラ内部でどのように表現されているかを可視化するための帳票である。セマンティック解析前の中間表現を詳細にダンプし、コンパイラの動作理解やデバッグに活用される。

**業務上の目的・背景**：コンパイラ開発において、ソースコードから生成される中間表現の正確性を検証することは極めて重要である。ZIRはセマンティック解析の入力となるため、この段階での問題はコンパイル結果全体に影響する。本帳票により、開発者はZIR生成の正確性を視覚的に確認でき、パーサーやASTからZIRへの変換ロジックのデバッグを効率的に行える。

**帳票の利用シーン**：
1. コンパイラ開発者がZIR生成ロジックのデバッグを行う際
2. 新しい言語機能追加時のZIR出力確認
3. コンパイルエラーの原因調査（セマンティック解析前の状態確認）
4. 教育目的でのコンパイラ内部構造の学習
5. クラッシュレポート生成時のコンテキスト情報提供

**主要な出力内容**：
1. メイン構造体命令（`%0 = ...`）
2. 各ZIR命令の詳細（命令タグ、オペランド、ソース位置）
3. インポート情報一覧
4. ブロック構造と命令の階層関係
5. ソースコードの行・列情報

**帳票の出力タイミング**：`zig ast-check -t <ファイル>` コマンド実行時、またはクラッシュレポート生成時に出力される。

**帳票の利用者**：Zigコンパイラ開発者、言語仕様の研究者、高度なデバッグを行うユーザー

## 帳票種別

デバッグ/診断レポート

## 利用画面

| 画面No | 画面名 | URL/ルーティング | 出力操作 |
|--------|--------|-----------------|---------|
| - | コマンドライン | `zig ast-check -t <file>` | `-t`オプション指定時 |
| - | クラッシュレポート | 自動 | パニック時に自動出力 |

## 出力形式

### 基本仕様

| 項目 | 内容 |
|-----|------|
| ファイル形式 | テキスト（標準出力または標準エラー出力） |
| 用紙サイズ | N/A |
| 向き | N/A |
| ファイル名 | N/A（標準出力） |
| 出力方法 | バッファリングされたストリーム書き込み |
| 文字コード | UTF-8 |

## 帳票レイアウト

### レイアウト概要

ZIRデバッグ出力は階層的な構造を持ち、命令番号とその内容が行単位で出力される。

```
┌─────────────────────────────────────────────────────────────┐
│ %0 = struct_decl(...)                                       │
├─────────────────────────────────────────────────────────────┤
│ Imports:                                                    │
│   @import("...") [位置情報]                                  │
├─────────────────────────────────────────────────────────────┤
│ [各命令の詳細]                                               │
│   %N = instruction_tag(operands) [位置情報]                  │
│     [ネストされたブロック]                                    │
└─────────────────────────────────────────────────────────────┘
```

### ヘッダー部

| No | 項目名 | 説明 | データ取得元 | 表示形式 |
|----|-------|------|-------------|---------|
| 1 | メイン構造体命令 | モジュールのルート構造体定義 | `Zir.Inst.Index.main_struct_inst` | `%0 = struct_decl(...)` |

### 明細部

| No | 項目名 | 説明 | データ取得元 | 表示形式 | 列幅 |
|----|-------|------|-------------|---------|-----|
| 1 | 命令番号 | ZIR命令のインデックス | `Zir.Inst.Index` | `%N` | 可変 |
| 2 | 命令タグ | 命令の種別 | `Zir.Inst.Tag` | 小文字スネークケース | 可変 |
| 3 | オペランド | 命令の引数 | 命令固有データ | カンマ区切り | 可変 |
| 4 | ソース位置 | ソースコード上の位置 | `line:column` | 括弧付き | 可変 |
| 5 | インポートパス | @import引数 | `Zir.Inst.Imports.Item` | `@import("...")` | 可変 |

### フッター部

N/A

## 出力条件

### 抽出条件

| 条件名 | 説明 | 必須 |
|-------|------|-----|
| ASTチェックコマンド | `zig ast-check -t`実行時 | Yes（コマンドライン利用時） |
| クラッシュコンテキスト | パニック時のコンテキストダンプ | Yes（クラッシュ時） |
| ZIR存在 | 対象ファイルのZIRが生成済み | Yes |

### ソート順

| 優先度 | 項目 | 昇順/降順 |
|-------|------|---------|
| 1 | 命令インデックス | 昇順 |

### 改ページ条件

N/A（連続テキスト出力）

## データベース参照仕様

N/A（データベースを使用しない。コンパイラ内部のZIRデータ構造を参照）

### 内部データ構造参照

| 参照項目 | 帳票項目との対応 | 取得条件 | 備考 |
|---------|----------------|---------|------|
| `Zir.instructions` | 各命令の詳細 | 全命令を走査 | MultiArrayList形式 |
| `Zir.extra` | 命令の追加データ | 命令タグに応じて | 可変長データ |
| `Zir.string_bytes` | 文字列リテラル | 文字列参照時 | NUL終端 |

## 計算仕様

### 計算項目一覧

| 項目名 | 計算式 | 端数処理 | 備考 |
|-------|-------|---------|------|
| ソース位置 | `findLineColumn(source, offset)` | なし | 行・列番号の計算 |

## 処理フロー

### 出力フロー

```mermaid
flowchart TD
    A[renderAsText呼び出し] --> B[Arena Allocator初期化]
    B --> C[Writer構造体初期化]
    C --> D[メイン構造体命令出力]
    D --> E{インポートあり?}
    E -->|Yes| F[インポート一覧出力]
    E -->|No| G[命令ループ開始]
    F --> G
    G --> H[各命令をwriteInstToStreamで出力]
    H --> I{ブロック命令?}
    I -->|Yes| J[再帰的にブロック内容出力]
    I -->|No| K[次の命令へ]
    J --> K
    K --> L{全命令完了?}
    L -->|No| H
    L -->|Yes| M[終了]
```

## エラー処理

### エラーケース一覧

| エラー種別 | 発生条件 | 表示メッセージ | 対処方法 |
|----------|---------|--------------|---------|
| メモリ不足 | アロケーション失敗 | エラー返却 | Arena Allocatorで一括解放 |
| 書き込みエラー | 出力ストリームエラー | エラー返却 | 呼び出し元で処理 |

## パフォーマンス要件

| 項目 | 内容 |
|-----|------|
| 想定データ件数 | 数千〜数万命令（ファイルサイズに依存） |
| 目標出力時間 | O(N)（命令数に比例） |
| 同時出力数上限 | 1件 |

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

- ZIRダンプにはソースコードの構造情報が含まれる
- 機密性の高いプロジェクトでは出力の取り扱いに注意

## 備考

- `renderAsText`は完全なZIRダンプ、`renderInstructionContext`は特定命令周辺のコンテキストダンプに使用
- ソース位置解決は`line_col_cursor`でO(N^2)からO(N)に最適化されている
- `recurse_decls`/`recurse_blocks`フラグでダンプ範囲を制御可能

---

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

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

### 推奨読解順序

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

ZIRの基本構造を理解することが前提となる。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | Zir.zig | `lib/std/zig/Zir.zig`（標準ライブラリ） | `Inst`構造体：命令の基本構造（tag, data） |
| 1-2 | Zir.zig | `lib/std/zig/Zir.zig` | `Inst.Tag`列挙型：命令種別の定義 |

**読解のコツ**: ZIRはMultiArrayList形式で格納されており、`tag`と`data`が別々の配列に格納されている。

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

ZIRテキスト出力の起点を特定。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | print_zir.zig | `src/print_zir.zig` | `renderAsText`関数（行13-51）：完全なZIRダンプのエントリーポイント |
| 2-2 | print_zir.zig | `src/print_zir.zig` | `renderInstructionContext`関数（行53-84）：コンテキスト限定ダンプ |
| 2-3 | print_zir.zig | `src/print_zir.zig` | `renderSingleInstruction`関数（行86-110）：単一命令出力 |

**主要処理フロー**:
1. **行14-15**: Arena Allocatorの初期化
2. **行17-26**: Writer構造体の初期化（設定フラグを含む）
3. **行28-31**: メイン構造体命令の出力
4. **行32-50**: インポート情報の出力

#### Step 3: Writer構造体を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | print_zir.zig | `src/print_zir.zig` | `Writer`構造体（行112-121）：出力状態管理 |
| 3-2 | print_zir.zig | `src/print_zir.zig` | `line_col_cursor`（行126-177）：ソース位置の効率的な解決 |

**主要処理フロー**:
- `recurse_decls`: 宣言を再帰的に出力するかどうか
- `recurse_blocks`: ブロックを再帰的に出力するかどうか
- `line_col_cursor`: キャッシュを使用した行・列計算の最適化

#### Step 4: 命令出力処理を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | print_zir.zig | `src/print_zir.zig` | `writeInstToStream`関数（行181-500+）：命令タグに応じた出力分岐 |

**読解のコツ**: `switch (tag)`で命令タグごとに出力処理が分岐する。各ケースで対応する`write*`関数が呼び出される。

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

```
renderAsText / renderInstructionContext / renderSingleInstruction
    |
    +-- Writer初期化
    |
    +-- writeInstToStream
            |
            +-- [命令タグに応じた分岐]
            |       |
            |       +-- writeUnNode
            |       +-- writeUnTok
            |       +-- writeBoolBr
            |       +-- writeBlock
            |       +-- writeFunc
            |       +-- ... (各命令タイプ固有の出力関数)
            |
            +-- [ブロック命令の場合]
                    +-- writeBody (再帰)
                            +-- writeInstToStream (再帰)
```

### データフロー図

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

Zir構造体            ─────> renderAsText ─────────────────> stdout/Writer
  |                         |
  +-- instructions   ─────> writeInstToStream ────────────> "%N = tag(...)"
  |                         |
  +-- extra          ─────> extraData() ──────────────────> オペランド詳細
  |                         |
  +-- string_bytes   ─────> nullTerminatedString() ───────> 文字列値
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| print_zir.zig | `src/print_zir.zig` | ソース | ZIRテキスト出力のメイン実装 |
| Zir.zig | `lib/std/zig/Zir.zig` | ソース（標準ライブラリ） | ZIRデータ構造定義 |
| crash_report.zig | `src/crash_report.zig` | ソース | クラッシュ時のZIR出力呼び出し元 |
| Zcu.zig | `src/Zcu.zig` | ソース | ファイル・ソース位置管理 |
