# 機能設計書 102-llvm-debuginfod

## 概要

本ドキュメントは、llvm-debuginfod機能の設計仕様を記述する。llvm-debuginfodは、debuginfodプロトコルに準拠したHTTPサーバーであり、ELFバイナリのデバッグ情報を配信する。

### 本機能の処理概要

llvm-debuginfodは、デバッグ情報を提供するHTTPサーバーである。指定されたディレクトリを定期的にスキャンしてELFバイナリを収集し、Build IDに基づいてデバッグ情報、実行ファイル、ソースコードを配信する。未知のBuild IDに対するリクエストは、DEBUGINFOD_URLS環境変数で設定された上流サーバーにフェデレーションされる。

**業務上の目的・背景**：デバッグ作業において、デバッグシンボルやソースコードを取得するのは時間のかかる作業である。debuginfodプロトコルにより、デバッガ（LLDBやGDB）がネットワーク経由でデバッグ情報を自動的に取得できるようになり、デバッグワークフローが大幅に効率化される。中央集権的なデバッグ情報リポジトリを構築することで、組織全体でデバッグ情報を共有できる。

**機能の利用シーン**：組織内でデバッグ情報サーバーを運用する際に使用される。CIパイプラインでビルドされたバイナリのデバッグ情報を自動的に収集・配信できる。開発者がリモートのデバッグシンボルを取得してローカルでデバッグする場合にも活用される。

**主要な処理内容**：
1. 指定ディレクトリのファイルシステムスキャン
2. ELFバイナリからBuild IDとデバッグ情報の抽出
3. HTTPサーバーの起動とリクエスト処理
4. デバッグ情報/実行ファイル/ソースコードの配信
5. 上流debuginfodサーバーへのリクエストフェデレーション
6. 定期的なファイルシステム再スキャン

**関連システム・外部連携**：上流のdebuginfodサーバー（DEBUGINFOD_URLS環境変数で設定）、HTTPクライアント（LLDB、GDB、curl等）と連携する。

**権限による制御**：特になし。ファイルシステムへの読み取りアクセス権限が必要。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| - | CLIインターフェース | 主画面 | サーバー起動とオプション設定 |
| - | HTTPエンドポイント | API | /buildid/{id}/debuginfo等のREST API |

## 機能種別

サーバー処理 / データ配信

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| directories | 文字列リスト | No | スキャン対象ディレクトリ | 存在するパス |
| -p (--port) | 整数 | No | リッスンポート（0で自動割当） | 0以上の整数 |
| -i (--host-interface) | 文字列 | No | バインドするインターフェース | デフォルト: 0.0.0.0 |
| -t (--scan-interval) | 整数 | No | スキャン間隔（秒） | デフォルト: 300 |
| -m (--min-interval) | 浮動小数点 | No | オンデマンド更新の最小間隔（秒） | デフォルト: 10.0 |
| -c (--max-concurrency) | 整数 | No | 最大同時スキャン数 | デフォルト: 0（ハードウェア並列度） |
| -v (--verbose-logging) | フラグ | No | 詳細ログ出力 | - |

### 入力データソース

- ファイルシステム（ELFバイナリ）
- コマンドライン引数
- DEBUGINFOD_URLS環境変数

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| debuginfo | バイナリ | .debug_*セクションを含むファイル |
| executable | バイナリ | ストリップされた実行ファイル |
| source | テキスト | ソースファイル |
| ログ | テキスト | サーバー動作ログ |

### 出力先

HTTPレスポンス、標準出力（ログ）

## 処理フロー

### 処理シーケンス

```
1. 初期化
   └─ HTTPClientの初期化
2. 引数解析
   └─ ポート、インターフェース、スキャン設定の取得
3. コレクション構築
   └─ DebuginfodCollectionの作成
4. サーバー起動
   └─ DebuginfodServerの作成とバインド
5. 非同期処理開始
   └─ リクエスト処理スレッドとログ処理スレッドの起動
6. 定期スキャン
   └─ updateForeverによる永続スキャン
```

### フローチャート

```mermaid
flowchart TD
    A[開始] --> B[HTTP Client初期化]
    B --> C[引数解析]
    C --> D[ThreadPool作成]
    D --> E[DebuginfodCollection作成]
    E --> F[DebuginfodServer作成]
    F --> G{ポート指定?}
    G -->|Yes| H[指定ポートでバインド]
    G -->|No| I[自動ポート割当]
    H --> J[リッスン開始]
    I --> J
    J --> K[非同期: リクエスト処理]
    J --> L[非同期: ログ出力]
    J --> M{ディレクトリ指定?}
    M -->|Yes| N[定期スキャン開始]
    M -->|No| O[リクエスト待機のみ]
    N --> P[永続実行]
    O --> P
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-102 | ポート自動割当 | ポート0指定時はOSが利用可能なポートを割り当て | -p 0 指定時 |
| BR-103 | フェデレーション | 未知のBuild IDは上流サーバーにリクエスト転送 | DEBUGINFOD_URLS設定時 |
| BR-104 | 最小間隔制限 | オンデマンドスキャンは最小間隔を守る | リクエスト時 |

### 計算ロジック

特になし

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

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

データベースは使用しない。インメモリでBuild ID→ファイルパスのマッピングを保持。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| - | バインド失敗 | ポートが使用中 | エラーメッセージ出力、プロセス終了 |
| - | ディレクトリアクセス失敗 | 指定パスが存在しないまたはアクセス権限なし | 警告出力、続行 |
| 404 | Not Found | 要求されたBuild IDが見つからない | HTTP 404レスポンス |

### リトライ仕様

上流サーバーへのリクエストはHTTPClientの設定に従う。

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

該当なし

## パフォーマンス要件

- スキャン並列度は--max-concurrencyで制御可能
- ThreadPoolを使用した非同期I/O処理

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

- デフォルトで全インターフェース(0.0.0.0)にバインド
- 認証機能は未実装
- ファイルシステムアクセスはプロセス権限に従う

## 備考

debuginfodプロトコルはelfutils projectで標準化されている。

---

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

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

### 推奨読解順序

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

まず、debuginfodの基本データ構造を理解する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | Debuginfod.h | `llvm/include/llvm/Debuginfod/Debuginfod.h` | DebuginfodLog, DebuginfodCollection, DebuginfodServerクラス |
| 1-2 | HTTPClient.h | `llvm/include/llvm/Debuginfod/HTTPClient.h` | HTTPサーバー/クライアント基盤 |

**読解のコツ**: DebuginfodCollectionがBuild ID→ファイルマッピングを管理し、DebuginfodServerがHTTPリクエストを処理する構造を把握する。

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | llvm-debuginfod.cpp | `llvm/tools/llvm-debuginfod/llvm-debuginfod.cpp` | main関数の処理フロー |
| 2-2 | Opts.td | `llvm/tools/llvm-debuginfod/Opts.td` | コマンドラインオプション定義 |

**主要処理フロー**:
1. **124行目**: llvm_debuginfod_main関数がエントリーポイント
2. **125行目**: HTTPClient::initialize()でHTTPクライアント初期化
3. **126行目**: parseArgs()で引数解析
4. **131-133行目**: ThreadPool、DebuginfodLog、DebuginfodCollectionの作成
5. **134行目**: DebuginfodServerの作成
6. **136-139行目**: サーバーのバインド（ポート指定有無で分岐）
7. **143-152行目**: 非同期でリッスンとログ出力を開始
8. **153-154行目**: ディレクトリ指定時は永続スキャン開始

#### Step 3: オプション解析を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | Opts.td | `llvm/tools/llvm-debuginfod/Opts.td` | TableGenによるオプション定義 |
| 3-2 | llvm-debuginfod.cpp | `llvm/tools/llvm-debuginfod/llvm-debuginfod.cpp` | parseArgs関数（86-122行目） |

**主要処理フロー**:
- **104行目**: VerboseLoggingフラグの取得
- **105行目**: ScanPathsの取得
- **107-109行目**: 整数オプション（port、scan_interval、max_concurrency）の解析
- **111-118行目**: min_interval（浮動小数点）の解析
- **121行目**: host_interfaceの取得

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

```
llvm_debuginfod_main (124行目)
    │
    ├─ HTTPClient::initialize (125行目)
    │
    ├─ parseArgs (126行目)
    │      ├─ parseIntArg (port)
    │      ├─ parseIntArg (scan_interval)
    │      ├─ parseIntArg (max_concurrency)
    │      └─ to_float (min_interval)
    │
    ├─ DefaultThreadPool (131行目)
    │
    ├─ DebuginfodLog (132行目)
    │
    ├─ DebuginfodCollection (133行目)
    │
    ├─ DebuginfodServer (134行目)
    │
    ├─ Server.bind (136-139行目)
    │
    └─ Pool.async (143-154行目)
           ├─ Server.listen (リクエスト処理)
           ├─ Log.pop (ログ出力)
           └─ Collection.updateForever (定期スキャン)
```

### データフロー図

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

ファイルシステム ───▶ DebuginfodCollection ───▶ Build IDマッピング
                      (スキャン)

HTTPリクエスト ───▶ DebuginfodServer ───▶ HTTPレスポンス
  /buildid/{id}/...   │                    (debuginfo/executable/source)
                      │
                      └─ 上流サーバー ───▶ フェデレーション応答
                         (DEBUGINFOD_URLS)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| llvm-debuginfod.cpp | `llvm/tools/llvm-debuginfod/llvm-debuginfod.cpp` | ソース | メインエントリーポイント |
| Opts.td | `llvm/tools/llvm-debuginfod/Opts.td` | TableGen | コマンドラインオプション定義 |
| CMakeLists.txt | `llvm/tools/llvm-debuginfod/CMakeLists.txt` | ビルド設定 | ビルド構成 |
| Debuginfod.h | `llvm/include/llvm/Debuginfod/Debuginfod.h` | ヘッダ | debuginfodライブラリAPI |
| HTTPClient.h | `llvm/include/llvm/Debuginfod/HTTPClient.h` | ヘッダ | HTTPサーバー/クライアント基盤 |
