# 通知設計書 113-hintPerformance

## 概要

本ドキュメントは、Nimコンパイラにおける`hintPerformance`（パフォーマンスヒント）通知の設計について記述する。

### 本通知の処理概要

`hintPerformance`は、コンパイル時にパフォーマンスに影響を与える可能性のあるコードパターンを検出した際に、開発者に改善の余地を通知するためのヒント通知である。主にメモリ管理やコピー操作に関する最適化の機会を示す。

**業務上の目的・背景**：Nimの高度なメモリ管理機能（特にムーブセマンティクスとsinkパラメータ）を最大限に活用するため、暗黙のコピーが発生している箇所や、sinkパラメータへの変換が可能な箇所を開発者に通知する。これにより、パフォーマンスクリティカルなアプリケーションの最適化を支援する。

**通知の送信タイミング**：セマンティック解析フェーズ（特にデストラクタ注入処理およびsinkパラメータ推論処理）において、最適化の機会が検出された際に送信される。

**通知の受信者**：コンパイルを実行している開発者。コンソール出力またはIDE経由でメッセージを受け取る。

**通知内容の概要**：暗黙のコピーが発生している変数名や、sinkパラメータへの変換ができなかった理由が通知される。

**期待されるアクション**：開発者はコードの制御フローを見直し、`move`の使用やコード構造の変更により暗黙のコピーを回避する。

## 通知種別

コンパイラ出力（コンソール / IDE統合）

## 送信仕様

### 基本情報

| 項目 | 内容 |
|-----|------|
| 送信方式 | 同期 |
| 優先度 | 低（Hint） |
| リトライ | なし |

### 送信先決定ロジック

コンパイラの標準出力または標準エラー出力へ送信。`--verbosity`オプションの設定により制御される。verbosity レベル1以下ではデフォルトで無効化されている。

## 通知テンプレート

### コンソール出力の場合

| 項目 | 内容 |
|-----|------|
| 送信元 | Nimコンパイラ |
| 形式 | テキスト |

### 本文テンプレート

```
Hint: passing '{変数名}' to a sink parameter introduces an implicit copy; if possible, rearrange your program's control flow to prevent it [Performance]
```

または

```
Hint: could not turn '{パラメータ名}' to a sink parameter [Performance]
```

### 添付ファイル

なし

## テンプレート変数

| 変数名 | 説明 | データ取得元 | 必須 |
|--------|------|-------------|-----|
| $1 | パフォーマンス関連メッセージ | 動的生成 | Yes |

## 送信トリガー・条件

### トリガー一覧

| トリガー種別 | トリガーイベント | 送信条件 | 説明 |
|------------|----------------|---------|------|
| デストラクタ注入 | sinkパラメータへの値渡し | isLValue(n) && !isCapturedVar(n) && nTyp != tyRef && c.inSpawn == 0 | 暗黙のコピーが発生する場合 |
| sinkパラメータ推論 | パラメータ解析 | sfWasForwarded notin arg.sym.flags | sinkに変換できなかった場合 |

### 送信抑止条件

| 条件 | 説明 |
|-----|------|
| verbosity <= 1 | デフォルトのverbosityレベルでは抑止 |
| hintPerformance not in conf.notes | ヒントが無効化されている場合 |
| c.inSpawn > 0 | spawn内での呼び出しの場合 |

## 処理フロー

### 送信フロー

```mermaid
flowchart TD
    A[セマンティック解析] --> B{sinkパラメータ解析}
    B --> C{暗黙コピー検出?}
    C -->|Yes| D{c.inSpawn == 0?}
    C -->|No| H[処理続行]
    D -->|Yes| E[hintPerformance発行]
    D -->|No| H
    E --> F[コピー生成コード挿入]
    F --> G[終了]
    H --> G
```

## データベース参照・更新仕様

### 参照テーブル一覧

該当なし（コンパイラ内部処理のみ）

## エラー処理

### エラーケース一覧

| エラー種別 | 発生条件 | 対処方法 |
|----------|---------|---------|
| なし | このヒント自体はエラーを発生させない | - |

### リトライ仕様

| 項目 | 内容 |
|-----|------|
| リトライ回数 | なし |
| リトライ間隔 | - |
| リトライ対象エラー | - |

## 配信設定

### レート制限

| 項目 | 内容 |
|-----|------|
| 制限 | なし |

### 配信時間帯

制限なし

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

変数名が出力されるが、機密情報を含む可能性は低い。

## 備考

- verbosity レベル2以上で有効になる
- `--hint:Performance:on/off`オプションで個別に制御可能
- ムーブセマンティクスを活用したパフォーマンス最適化の指針として活用

---

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

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

### 推奨読解順序

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

まず、通知の定義と設定について理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | lineinfos.nim | `compiler/lineinfos.nim` | TMsgKind列挙型のhintPerformance定義（112行目）、MsgKindToStr配列でのメッセージテンプレート（236行目） |

**読解のコツ**: hintPerformanceは汎用的な"$1"テンプレートを持ち、呼び出し元で具体的なメッセージを生成する。

#### Step 2: デストラクタ注入での使用箇所を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | injectdestructors.nim | `compiler/injectdestructors.nim` | 暗黙コピー検出とヒント発行（490-493行目） |

**主要処理フロー**:
1. **486-489行目**: コピー生成処理の開始
2. **490行目**: `isLValue(n) and not isCapturedVar(n) and nTyp.skipTypes(abstractInst).kind != tyRef and c.inSpawn == 0`の条件確認
3. **491-493行目**: `message(c.graph.config, n.info, hintPerformance, ...)`でヒント発行

#### Step 3: sinkパラメータ推論での使用箇所を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | sinkparameter_inference.nim | `compiler/sinkparameter_inference.nim` | sinkパラメータ推論とヒント発行（45-51行目） |

**主要処理フロー**:
- **45-46行目**: sinkパラメータへの変換成功時の処理
- **46-51行目**: 変換失敗時のヒント発行

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

```
セマンティック解析
    │
    ├─ injectdestructors (injectdestructors.nim)
    │      │
    │      └─ 暗黙コピー検出
    │             └─ message(hintPerformance)
    │
    └─ sinkパラメータ推論 (sinkparameter_inference.nim)
           │
           └─ checkForSink
                  └─ message(hintPerformance)
```

### データフロー図

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

sinkパラメータ ─────▶ 暗黙コピー検出 ─────▶ パフォーマンスヒント
への引数渡し          injectdestructors          "passing 'x' to sink..."
       │
       │
パラメータ定義 ─────▶ sink推論 ─────────────▶ パフォーマンスヒント
                    sinkparameter_inference    "could not turn..."
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| lineinfos.nim | `compiler/lineinfos.nim` | ソース | TMsgKind定義、メッセージテンプレート |
| msgs.nim | `compiler/msgs.nim` | ソース | メッセージ送信処理 |
| injectdestructors.nim | `compiler/injectdestructors.nim` | ソース | デストラクタ注入、暗黙コピー検出 |
| sinkparameter_inference.nim | `compiler/sinkparameter_inference.nim` | ソース | sinkパラメータ推論 |
