# 機能設計書 252-MemAlloc

## 概要

本ドキュメントは、Dear ImGuiライブラリにおけるメモリ割り当て機能（MemAlloc）の設計仕様を定義する。

### 本機能の処理概要

MemAlloc関数は、ImGuiが内部で使用するメモリ割り当て関数を提供する。設定されたアロケータ関数を呼び出し、デバッグツールが有効な場合はアロケーション情報を追跡する。

**業務上の目的・背景**：
ImGuiライブラリ内部では、ウィジェット、ウィンドウ、フォントデータなど多くのオブジェクトの動的メモリ確保が必要となる。MemAlloc関数は、これらのメモリ確保を一元化し、カスタムアロケータのサポートとデバッグ機能の統合を実現する。また、DLL境界を跨ぐ場合のメモリ管理問題を解決するための仕組みの一部として機能する。

**機能の利用シーン**：
- ImGuiウィジェットの内部データ構造の確保
- ImVector等のコンテナのバッファ確保
- フォントアトラス、テクスチャデータの確保
- ユーザーがImGuiのメモリ管理システムを利用したい場合
- IM_ALLOCマクロ経由での呼び出し
- IM_NEWマクロ経由でのオブジェクト生成

**主要な処理内容**：
1. グローバルに設定されたアロケータ関数（GImAllocatorAllocFunc）を呼び出してメモリを確保
2. デバッグツールが有効な場合、DebugAllocHookを呼び出してアロケーション情報を記録
3. 確保したメモリのポインタを返却

**関連システム・外部連携**：
- SetAllocatorFunctions: アロケータ関数の設定
- GetAllocatorFunctions: アロケータ関数の取得
- MemFree: 確保したメモリの解放

**権限による制御**：
権限による制御は存在しない。全ての呼び出し元から使用可能。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| - | - | - | 本機能は画面に直接関連しない内部API |

## 機能種別

メモリ管理処理

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| size | size_t | Yes | 確保するメモリのバイト数 | 0以上の値 |

### 入力データソース

- グローバル変数`GImAllocatorAllocFunc`: メモリ割り当て関数
- グローバル変数`GImAllocatorUserData`: アロケータに渡すユーザーデータ
- グローバルコンテキスト`GImGui`: デバッグ情報記録用（オプション）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| 戻り値 | void* | 確保されたメモリへのポインタ。失敗時はNULL |

### 出力先

呼び出し元に直接返却

## 処理フロー

### 処理シーケンス

```
1. アロケータ関数呼び出し
   └─ GImAllocatorAllocFunc(size, GImAllocatorUserData)でメモリ確保
2. デバッグ情報記録（IMGUI_DISABLE_DEBUG_TOOLS未定義時）
   ├─ GImGuiコンテキストの存在確認
   └─ DebugAllocHookを呼び出してアロケーション情報を記録
3. ポインタ返却
   └─ 確保したメモリのポインタを返す
```

### フローチャート

```mermaid
flowchart TD
    A[開始] --> B[GImAllocatorAllocFunc呼び出し]
    B --> C{デバッグツール有効?}
    C -->|Yes| D{GImGui != NULL?}
    C -->|No| F[ポインタ返却]
    D -->|Yes| E[DebugAllocHook呼び出し]
    D -->|No| F
    E --> F
    F --> G[終了]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-252-01 | デフォルトアロケータ | 未設定時はmalloc関数を使用 | SetAllocatorFunctions未呼び出し時 |
| BR-252-02 | コンテキスト非依存 | アロケータ呼び出し自体はコンテキスト不要 | 常に適用 |
| BR-252-03 | デバッグ追跡 | IMGUI_DISABLE_DEBUG_TOOLS未定義時のみ追跡 | コンパイル時設定 |
| BR-252-04 | ペア解放 | MemAllocで確保したメモリはMemFreeで解放 | 常に適用 |

### 計算ロジック

特になし（メモリ確保の委譲のみ）

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

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

| 操作 | 対象テーブル | 操作種別 | 概要 |
|-----|-------------|---------|------|
| - | - | - | データベース操作なし |

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| - | メモリ不足 | システムメモリが不足 | NULLを返却、呼び出し元で対処 |

### リトライ仕様

リトライ機能なし。メモリ不足時はNULLを返却。

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

トランザクション管理なし

## パフォーマンス要件

- 基本的にO(1)の時間計算量（アロケータ実装依存）
- デバッグモードでは追加のオーバーヘッドあり

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

- 確保されたメモリは初期化されない（内容は不定）
- バッファオーバーフロー防止は呼び出し元の責任
- カスタムアロケータのセキュリティは設定者の責任

## 備考

- IM_ALLOCマクロは本関数のラッパーとして定義されている
- IM_NEWマクロは本関数を使用してplacement newを実行
- メトリクスウィンドウでアロケーション数を確認可能

---

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

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

### 推奨読解順序

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

デバッグ用アロケーション情報の構造を確認する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | imgui.h | `imgui.h` | ImGuiMemAllocFunc型定義（288行目） |
| 1-2 | imgui_internal.h | `imgui_internal.h` | ImGuiDebugAllocInfo構造体（デバッグ用） |

**読解のコツ**: ImGuiMemAllocFuncは`void* (*)(size_t sz, void* user_data)`という関数ポインタ型。

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

MemAlloc関数の宣言と実装を確認する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | imgui.h | `imgui.h` | 関数宣言（1152行目） |
| 2-2 | imgui.cpp | `imgui.cpp` | 関数実装（5041-5049行目） |

**主要処理フロー**:
1. **5041行目**: MemAlloc関数定義開始
2. **5043行目**: GImAllocatorAllocFunc呼び出しでメモリ確保
3. **5044-5046行目**: デバッグツール有効時のフック処理
4. **5048行目**: ポインタ返却

#### Step 3: マクロ定義を理解する

IM_ALLOC/IM_NEWマクロの関係を確認する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | imgui.h | `imgui.h` | IM_ALLOCマクロ定義（2184行目） |
| 3-2 | imgui.h | `imgui.h` | IM_NEWマクロ定義（2187行目） |

**主要処理フロー**:
- **2184行目**: `#define IM_ALLOC(_SIZE) ImGui::MemAlloc(_SIZE)`
- **2187行目**: `#define IM_NEW(_TYPE) new(ImNewWrapper(), ImGui::MemAlloc(sizeof(_TYPE))) _TYPE`

#### Step 4: デバッグフックを理解する

アロケーション追跡の仕組みを確認する。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | imgui.cpp | `imgui.cpp` | DebugAllocHook関数（5063-5085行目） |

**主要処理フロー**:
- **5076-5078行目**: アロケーション時（size != -1）のカウント増加
- **5082-5084行目**: フリー時（size == -1）のカウント増加

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

```
MemAlloc(size)
    │
    ├─ GImAllocatorAllocFunc(size, user_data)
    │      └─ MallocWrapper (デフォルト) または カスタムアロケータ
    │
    └─ DebugAllocHook (デバッグモード時)
           └─ ImGuiDebugAllocInfo更新
```

### データフロー図

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

size     ───────▶ GImAllocatorAllocFunc ───────▶ void* ptr
                           │
                           ▼
                  DebugAllocHook (記録)
                           │
                           ▼
                  ImGuiDebugAllocInfo
                  (TotalAllocCount++)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| imgui.h | `imgui.h` | ヘッダー | 関数宣言、マクロ定義 |
| imgui.cpp | `imgui.cpp` | ソース | 関数実装、デバッグフック |
| imgui_internal.h | `imgui_internal.h` | 内部ヘッダー | デバッグ用構造体定義 |
