# 機能設計書 57-マルチキャストオプション設定

## 概要

本ドキュメントは、libuvにおけるマルチキャストオプション設定機能（`uv_udp_set_multicast_loop()` / `uv_udp_set_multicast_ttl()` / `uv_udp_set_multicast_interface()`）の設計仕様を記述する。

### 本機能の処理概要

**業務上の目的・背景**：マルチキャスト通信の動作を細かく制御するために、ループバック設定、TTL（ホップ数）、送信インターフェースの指定が必要となる。これらのオプションにより、マルチキャストパケットの到達範囲やルーティング動作を制御できる。

**機能の利用シーン**：
- マルチキャストパケットのループバック有効化/無効化（自身への配信制御）
- マルチキャストTTLによるネットワーク到達範囲制御
- 複数インターフェースを持つホストでの送信インターフェース指定
- ルーター越えのマルチキャスト配信設定

**主要な処理内容**：
1. multicast_loop: IP_MULTICAST_LOOP/IPV6_MULTICAST_LOOPの設定
2. multicast_ttl: IP_MULTICAST_TTL/IPV6_MULTICAST_HOPSの設定
3. multicast_interface: IP_MULTICAST_IF/IPV6_MULTICAST_IFの設定

**関連システム・外部連携**：OSのソケットAPI（setsockopt）。

**権限による制御**：特になし。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 21 | UDP | 主機能 | マルチキャストオプション設定のAPI定義 |

## 機能種別

ソケットオプション設定

## 入力仕様

### 入力パラメータ

#### uv_udp_set_multicast_loop()

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| handle | uv_udp_t* | Yes | UDPハンドル | ソケットがバインド済みであること |
| on | int | Yes | ループバックの有効/無効 | 0-255の範囲 |

#### uv_udp_set_multicast_ttl()

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| handle | uv_udp_t* | Yes | UDPハンドル | ソケットがバインド済みであること |
| ttl | int | Yes | マルチキャストTTL（ホップ数） | 0-255の範囲 |

#### uv_udp_set_multicast_interface()

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| handle | uv_udp_t* | Yes | UDPハンドル | ソケットがバインド済みであること |
| interface_addr | const char* | No | インターフェースアドレス | NULLでデフォルト、有効なIPアドレス文字列 |

### 入力データソース

アプリケーションから直接指定されるオプション値。

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| 戻り値 | int | 成功時は0、失敗時は負のエラーコード |

### 出力先

OSカーネルのソケットオプションが変更される。

## 処理フロー

### 処理シーケンス

```
[multicast_loop / multicast_ttl]
1. 値の範囲チェック（0-255）
2. UV_HANDLE_IPV6フラグでIPv4/IPv6を判定
3. プラットフォーム依存の型サイズ処理
   ├─ Solaris/AIX/OpenBSD/z/OS/QNX: IPv6時はsizeof(int)
   └─ その他: uv__setsockopt_maybe_char()で型を自動選択
4. setsockopt()で設定

[multicast_interface]
1. interface_addrがNULLの場合はデフォルトアドレスを設定
2. interface_addrをIPv4/IPv6としてパース
3. IPv4: IP_MULTICAST_IFにsin_addrを設定
4. IPv6: IPV6_MULTICAST_IFにsin6_scope_idを設定
```

### フローチャート

```mermaid
flowchart TD
    A[multicast_loop/ttl呼び出し] --> B{値の範囲OK?}
    B -->|No| C[UV_EINVAL]
    B -->|Yes| D{IPv6ソケット?}
    D -->|Yes| E[IPV6_MULTICAST_LOOP/HOPS設定]
    D -->|No| F[IP_MULTICAST_LOOP/TTL設定]
    E --> G[setsockopt呼び出し]
    F --> G
    G -->|成功| H[0返却]
    G -->|失敗| I[UV__ERR errno]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-57-01 | 値範囲制限 | loop/ttl値は0-255の範囲 | multicast_loop, multicast_ttl |
| BR-57-02 | プラットフォーム型差異 | Solaris/AIX等ではIPv6オプションにintを使用 | 該当プラットフォーム |
| BR-57-03 | IPv4/IPv6自動判定 | UV_HANDLE_IPV6フラグでプロトコルレベルを自動選択 | 常時 |
| BR-57-04 | インターフェースNULL | interface_addrがNULLの場合はINADDR_ANY/scope_id=0 | multicast_interface |

### 計算ロジック

特になし。

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

該当なし。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| UV_EINVAL | パラメータ不正 | 値が0-255範囲外 / 無効なインターフェースアドレス | 正しい値を指定 |
| UV__ERR(errno) | OS APIエラー | setsockopt失敗 | エラー内容を確認 |

### リトライ仕様

リトライは不要。

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

該当なし。

## パフォーマンス要件

同期処理。setsockopt()の実行時間のみ。

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

- TTLを大きく設定するとマルチキャストパケットがネットワーク外に到達する可能性がある
- ループバック有効時はセキュリティ監視ツールからも受信可能

## 備考

- multicast_loopのデフォルト値はOSに依存するが、通常は有効（1）
- IPv4のIP_MULTICAST_TTLはchar型を使用するプラットフォームがある（Solaris等ではintに統一）

---

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

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

### 推奨読解順序

#### Step 1: 共通ヘルパー関数を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | udp.c (unix) | `src/unix/udp.c` | **L1088-1111行目**: uv__setsockopt() - IPv4/IPv6の自動切り替え |
| 1-2 | udp.c (unix) | `src/unix/udp.c` | **L1113-1129行目**: uv__setsockopt_maybe_char() - プラットフォーム依存の型サイズ処理 |

**読解のコツ**: Solaris/AIX/MVS/OpenBSDではchar型が必要な場合があり、uv__setsockopt_maybe_charが型を自動選択する。

#### Step 2: 各関数の実装を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | udp.c (unix) | `src/unix/udp.c` | **L1207-1229行目**: uv_udp_set_multicast_loop() |
| 2-2 | udp.c (unix) | `src/unix/udp.c` | **L1182-1204行目**: uv_udp_set_multicast_ttl() |
| 2-3 | udp.c (unix) | `src/unix/udp.c` | **L1231-1278行目**: uv_udp_set_multicast_interface() |

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

```
uv_udp_set_multicast_loop(handle, on)
    └─ uv__setsockopt_maybe_char(handle, IP_MULTICAST_LOOP, IPV6_MULTICAST_LOOP, on)
           └─ uv__setsockopt(handle, option4, option6, &arg, sizeof(arg))
                  └─ setsockopt(fd, IPPROTO_IP/IPV6, option, val, size)

uv_udp_set_multicast_ttl(handle, ttl)
    └─ uv__setsockopt_maybe_char(handle, IP_MULTICAST_TTL, IPV6_MULTICAST_HOPS, ttl)

uv_udp_set_multicast_interface(handle, interface_addr)
    ├─ uv_ip4_addr() / uv_ip6_addr() でアドレスパース
    └─ setsockopt(fd, IPPROTO_IP/IPV6, IP/IPV6_MULTICAST_IF, ...)
```

### データフロー図

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

on/ttl ──────────▶ uv__setsockopt_maybe_char() ──▶ setsockopt()
                         │                              │
                   型サイズ自動判定               カーネルソケットオプション
                   (char or int)                     更新
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| uv.h | `include/uv.h` | ヘッダ | API宣言（L770-773） |
| udp.c (unix) | `src/unix/udp.c` | ソース | Unix系実装 |
| udp.c (win) | `src/win/udp.c` | ソース | Windows版実装 |
