# 機能設計書 100-ファイルリネーム

## 概要

本ドキュメントは、libuvにおけるファイルリネーム機能（uv_fs_rename()）の設計を記述する。ファイルおよびディレクトリの非同期リネーム（移動）操作を提供する。

### 本機能の処理概要

**業務上の目的・背景**：ファイルやディレクトリの名前変更・移動はファイルシステム操作の基本機能である。libuvはPOSIX rename()をクロスプラットフォームで抽象化し、同期・非同期の両モードで利用可能なAPIを提供する。同一ファイルシステム上での移動はアトミックに実行される。

**機能の利用シーン**：一時ファイルの本番ファイルへの差し替え（アトミックな更新）、ファイルの整理・移動、ファイル名の変更、ログファイルのローテーションなどで利用される。

**主要な処理内容**：
1. ソースパスとコピー先パスの検証と設定
2. Linux環境ではio_uring経由の最適化パスを試行
3. POSIX rename()システムコールの実行
4. 結果のlibuvエラーコードへの変換

**関連システム・外部連携**：POSIX rename()システムコール、libuvスレッドプール、Linux io_uringと連携する。

**権限による制御**：ソースおよびコピー先の親ディレクトリに対する書き込み権限が必要。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 24 | ファイルシステム操作 | 主機能 | uv_fs_rename()による非同期ファイルリネームのAPI定義 |

## 機能種別

ファイルI/O操作 / CRUD操作（Update）

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| loop | uv_loop_t* | Yes | イベントループ | NULLでないこと |
| req | uv_fs_t* | Yes | FSリクエスト | NULLでないこと |
| path | const char* | Yes | リネーム元パス | NULLでないこと |
| new_path | const char* | Yes | リネーム先パス | NULLでないこと |
| cb | uv_fs_cb | No | 完了コールバック（NULLで同期実行） | - |

### 入力データソース

呼び出し元コードから直接パラメータとして渡される。

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| 戻り値 | int | 同期: 0（成功）/負のエラーコード。非同期: 0 |
| req->result | ssize_t | コールバック内で結果取得（0=成功） |

### 出力先

呼び出し元への戻り値。ファイルシステム上でのファイル名変更。

## 処理フロー

### 処理シーケンス

```
1. INIT(RENAME)マクロでリクエスト初期化
2. PATH2マクロでソース/コピー先パスを設定
3. [非同期] io_uring最適化パスを試行（Linux）
4. POSTマクロで実行
   ├─ [非同期] uv__work_submit() --> uv__fs_work() --> rename(req->path, req->new_path)
   └─ [同期] uv__fs_work()を直接実行
```

### フローチャート

```mermaid
flowchart TD
    A[uv_fs_rename 呼び出し] --> B[INIT + PATH2]
    B --> C{cb != NULL?}
    C -->|Yes| D{io_uring 利用可能?}
    D -->|Yes| E[io_uring 経由]
    D -->|No| F[スレッドプールに投入]
    F --> G[rename syscall]
    C -->|No| H[同期 rename]
    G --> I[コールバック呼び出し]
    H --> J[結果返却]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-100-1 | 同期/非同期切替 | cbがNULLなら同期、非NULLなら非同期 | 常時 |
| BR-100-2 | PATH2マクロ | 非同期時はpath/new_pathの両方をメモリコピーして保持 | cb != NULL時 |
| BR-100-3 | io_uring最適化 | Linux環境でio_uring利用可能時はスレッドプールを回避 | Linux環境 |
| BR-100-4 | アトミック性 | 同一ファイルシステム上のrename()はアトミック | OS保証 |
| BR-100-5 | コピー先上書き | コピー先にファイルが存在する場合はアトミックに置換 | コピー先既存時 |

### 計算ロジック

特になし。

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

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

該当なし。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| UV_EINVAL | 無効パラメータ | reqがNULL | 有効なリクエストを渡す |
| UV_ENOMEM | メモリ不足 | パスのmalloc失敗 | メモリ確保後にリトライ |
| UV_ENOENT | ファイル不存在 | ソースファイルが存在しない | パスを確認 |
| UV_EACCES | アクセス拒否 | ディレクトリの書き込み権限なし | 権限を確認 |
| UV_EXDEV | デバイス跨ぎ | 異なるファイルシステム間の移動 | コピー+削除で対応 |
| UV_EISDIR | ディレクトリ | ファイルをディレクトリ名にリネーム | 正しいパスを指定 |
| UV_ENOTDIR | ディレクトリでない | ディレクトリをファイル名にリネーム | 正しいパスを指定 |

### リトライ仕様

EINTRのリトライはuv__fs_work()で自動処理される。

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

該当なし（rename()自体がアトミック操作）。

## パフォーマンス要件

- 非同期モードではイベントループをブロックしない
- Linux io_uringによる最適化が利用可能
- 同一ファイルシステム上のrename()はメタデータ操作のみで高速

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

- ソースおよびコピー先の親ディレクトリの書き込み権限が必要
- rename()のアトミック性を利用したセキュアなファイル更新パターンが可能

## 備考

- 異なるファイルシステム間のリネームはEXDEVエラーとなる。その場合はコピー+削除で対応する必要がある
- PATH2マクロにより、非同期実行時はpath/new_pathが一つの連続したメモリブロックに格納される

---

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

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

### 推奨読解順序

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | uv.h | `include/uv.h` | **1566-1570行目**: uv_fs_rename()のAPI宣言 |
| 1-2 | uv.h | `include/uv.h` | **1449-1460行目**: uv_fs_s構造体。new_pathフィールドを確認 |

#### Step 2: マクロを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | fs.c | `src/unix/fs.c` | **119-137行目**: PATH2マクロ。2つのパスの格納方法（連続メモリブロック） |

**読解のコツ**: PATH2マクロでは非同期時にpath_lenとnew_path_lenを計算し、1回のmalloc()で連続メモリを確保してpathとnew_pathを格納する。

#### Step 3: 公開APIを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | fs.c | `src/unix/fs.c` | **2120-2131行目**: uv_fs_rename()の実装 |

**主要処理フロー**:
- **2125行目**: `INIT(RENAME)` - UV_FS_RENAMEとして初期化
- **2126行目**: `PATH2` - 2つのパスを設定
- **2127-2129行目**: io_uring最適化パスの試行

#### Step 4: ディスパッチャーを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | fs.c | `src/unix/fs.c` | **1726行目**: uv__fs_work()内のディスパッチ。`X(RENAME, rename(req->path, req->new_path))` |

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

```
uv_fs_rename(loop, req, path, new_path, cb)
    |
    +-- INIT(RENAME) + PATH2
    |
    +-- [io_uring] uv__iou_fs_rename(loop, req)
    |
    +-- [async] uv__work_submit() --> uv__fs_work()
    |                                     |
    |                                     +-- rename(req->path, req->new_path)
    |
    +-- [sync] uv__fs_work() --> rename(req->path, req->new_path)
```

### データフロー図

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

const char* path      ---> rename() syscall --->
const char* new_path  --->                  ---> ファイル名変更
                                                 int (0 or error)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| uv.h | `include/uv.h` | ヘッダ | API宣言 |
| fs.c | `src/unix/fs.c` | ソース | Unix系ファイルリネームの実装 |
| fs.c | `src/win/fs.c` | ソース | Windowsファイルリネームの実装 |
