# 機能設計書 67-MACTripleDES

## 概要

本ドキュメントは、VBCorLibライブラリにおけるMACTripleDESクラスの機能設計を記述する。MACTripleDESは、Triple DES（3DES）暗号化アルゴリズムを使用したMessage Authentication Code（MAC）の実装を提供するクラスである。

### 本機能の処理概要

MACTripleDESクラスは、CBC-MAC（Cipher Block Chaining Message Authentication Code）をTriple DES暗号化アルゴリズムで実装したメッセージ認証コード機能を提供する。秘密鍵とメッセージを組み合わせて固定長の認証コード（64ビット/8バイト）を生成し、メッセージの完全性と認証を提供する。

**業務上の目的・背景**：MACTripleDESは、対称鍵暗号ベースのMACであり、HMACとは異なるアプローチでメッセージ認証を行う。金融業界のレガシーシステムや、ISO 8731-1等の規格に準拠する必要がある場合に使用される。

**機能の利用シーン**：
- 金融取引の認証
- レガシー銀行システムとの互換性
- ISO 8731-1/9797-1準拠システム
- EMV（チップカード）関連の認証
- 特定のSWIFTメッセージ認証

**主要な処理内容**：
1. Triple DES鍵の設定と暗号化器の初期化
2. CBC-MACモードでの暗号化処理
3. 入力データのブロック単位での処理（TransformBlock）
4. 最終ブロックの処理と認証コードの算出（TransformFinalBlock）
5. バイト配列またはストリームからの一括ハッシュ計算（ComputeHash）

**関連システム・外部連携**：
- TripleDESCryptoServiceProvider: 内部で使用する暗号化アルゴリズム
- CryptoStream: ストリーム暗号化との連携
- SingleBlockStream: 最終ブロックの取得用内部ストリーム

**権限による制御**：特になし。Windowsの暗号化サービスプロバイダー（CSP）へのアクセスが必要。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| - | - | - | 画面機能マッピングに記載なし |

## 機能種別

計算処理 / 暗号化処理 / データ変換

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| Key | Byte() | No | MAC計算に使用するTriple DES鍵（16または24バイト） | 有効な3DES鍵長であること |
| Padding | PaddingMode | No | パディングモード | デフォルトはZeros |
| Source | Variant | Yes | ハッシュ計算対象（Byte配列またはStream） | Byte配列またはStreamオブジェクトであること |
| Index | Long | No | Byte配列の開始インデックス | 0以上かつ配列範囲内 |
| Count | Long | No | 処理するバイト数 | 0以上かつ配列範囲内 |
| RgbKey | Byte() | No | Init用の鍵パラメータ | 有効な3DES鍵長であること |
| StrTripleDES | String | No | Init用のTripleDES実装名 | CryptoConfigで解決可能な名前 |

### 入力データソース

- アプリケーションから直接渡されるバイト配列
- Streamインターフェースを実装したオブジェクト（FileStream、MemoryStreamなど）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| Hash | Byte()(8バイト) | 計算されたMAC値（64ビット） |
| HashSize | Long | ハッシュサイズ（常に64ビット） |
| TransformBlock戻り値 | Long | 処理されたバイト数 |
| TransformFinalBlock戻り値 | Byte() | 処理された入力データのコピー |

### 出力先

- 呼び出し元アプリケーションへの戻り値として返却
- OutputBufferパラメータへのデータコピー（TransformBlock使用時）

## 処理フロー

### 処理シーケンス

```
1. インスタンス初期化（Class_Initialize）
   └─ TripleDESCryptoServiceProviderを生成
   └─ IVを8バイトのゼロで初期化
   └─ PaddingをZerosに設定
   └─ SingleBlockStreamを8バイトで初期化

2. 鍵の設定（Key Letプロパティ / Init）
   └─ ハッシュ開始後は変更不可
   └─ 既存のCryptoStreamを破棄

3. ハッシュ計算開始（StartHash）
   └─ CreateEncryptorでCBC暗号化器を生成
   └─ CryptoStreamをWriteモードで作成

4. データ処理（TransformBlock / ComputeHash）
   └─ CryptoStreamへデータを書き込み
   └─ CBC-MACによる暗号化処理

5. 最終処理（EndHash）
   └─ FlushFinalBlockを呼び出し
   └─ 最終暗号化ブロックがMAC値

6. ハッシュ取得（Hash Get）
   └─ SingleBlockStreamから8バイトのMAC値を取得
```

### フローチャート

```mermaid
flowchart TD
    A[開始] --> B[インスタンス生成]
    B --> C[TripleDES初期化]
    C --> D[IV=0x0000000000000000]
    D --> E[Padding=Zeros]
    E --> F{鍵が設定済み?}
    F -->|No| G[デフォルト鍵生成]
    F -->|Yes| H[鍵を設定]
    G --> H
    H --> I[CreateEncryptor]
    I --> J[CryptoStream作成]
    J --> K[データ処理]
    K --> L{全データ処理完了?}
    L -->|No| K
    L -->|Yes| M[FlushFinalBlock]
    M --> N[最終ブロックがMAC]
    N --> O[MAC値返却]
    O --> P[終了]
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-67-01 | 鍵長制限 | 16バイト（2KEY-3DES）または24バイト（3KEY-3DES）のみ受け付け | 鍵設定時 |
| BR-67-02 | IV固定 | 初期化ベクトルは常に8バイトのゼロ | 常時 |
| BR-67-03 | ハッシュ開始後の鍵変更禁止 | ハッシュ計算開始後は鍵を変更できない | Key設定時にmHashStartedがTrueの場合 |
| BR-67-04 | パディングモード | デフォルトはPaddingMode.Zeros | - |
| BR-67-05 | 再利用可能 | CanReuseTransformは常にTrue | - |

### 計算ロジック

**CBC-MACアルゴリズム**:
```
MAC = E_K(P_n XOR E_K(P_{n-1} XOR ... E_K(P_1 XOR IV)))

ここで:
- E_K: Triple DES暗号化関数（鍵K使用）
- P_i: メッセージのi番目のブロック（8バイト）
- IV: 初期化ベクトル（8バイトのゼロ）
- n: ブロック数
- XOR: 排他的論理和

※CBC暗号化の最終ブロックがMAC値となる
```

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

本機能はデータベース操作を行わない。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| CryptographicException | 暗号例外 | ハッシュ開始後に鍵を変更しようとした場合 | Initializeを呼び出してリセット後に鍵を設定 |
| ArgumentNullException | 引数Null例外 | Sourceがnullの場合 | 有効なByte配列またはStreamを渡す |
| ArgumentException | 引数例外 | Sourceが無効な型の場合 | Byte配列またはStreamオブジェクトを渡す |
| InvalidOperationException | 無効操作例外 | TransformFinalBlock前にHashプロパティにアクセス | TransformFinalBlockを先に呼び出す |
| ObjectDisposedException | 破棄済み例外 | Clear後にメソッドを呼び出した場合 | 新しいインスタンスを作成 |
| InvalidCastException | キャスト例外 | StrTripleDESで指定した名前がTripleDESでない場合 | 有効なTripleDES実装名を指定 |

### リトライ仕様

エラー発生時のリトライは行わない。

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

本機能はトランザクション管理を行わない（メモリ内処理のみ）。

## パフォーマンス要件

- Triple DESはAESより遅いため、大量データには不向き
- ブロック暗号ベースのため、HMACより計算コストが高い場合がある
- CSPベースの実装によりハードウェアアクセラレーションの恩恵を受ける可能性

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

- Triple DESは現在では推奨されない（NISTにより2023年以降非推奨）
- 新規開発ではAES-CMACまたはHMAC-SHA256以上を推奨
- レガシーシステムとの互換性が必須の場合のみ使用
- 秘密鍵は安全に管理し、ログ出力や永続化を避ける
- Clear()メソッドで使用後に鍵情報を消去する
- CBC-MACには既知の脆弱性（可変長メッセージに対する攻撃）がある

## 備考

- .NET FrameworkのSystem.Security.Cryptography.MACTripleDESクラスと互換性のあるAPI設計
- ISO 9797-1（MAC Algorithm 1）に準拠
- 内部でCryptoStreamを使用してCBC暗号化を行う
- HMACとは異なり、ブロック暗号ベースのMAC

---

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

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

### 推奨読解順序

#### Step 1: MACTripleDESクラスの構造を理解する

MACTripleDESはHMACクラスと異なり、HMACBaseを使用せず独自の実装を持つ。

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | MACTripleDES.cls | `Source/CorLib/System.Security.Cryptography/MACTripleDES.cls` | メインクラスの構造 |

**主要処理フロー**:
1. **47-52行目**: メンバ変数 - mTripleDES, mStream, mHashStream, mDisposed, mHashStarted
2. **313-318行目**: Class_Initialize - TripleDESの初期化、IV設定、Padding設定
3. **349-353行目**: StartHash - 暗号化器とCryptoStreamの作成
4. **355-359行目**: EndHash - FlushFinalBlockの呼び出し
5. **124-131行目**: Hash Get - mHashStreamから取得
6. **138-139行目**: HashSize = 64

#### Step 2: データフローを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | CryptoStream.cls | `Source/CorLib/System.Security.Cryptography/CryptoStream.cls` | ストリームベースの暗号化処理 |
| 2-2 | SingleBlockStream.cls | `Source/CorLib/System.Security.Cryptography/SingleBlockStream.cls` | 最終ブロック取得用の内部ストリーム |

**読解のコツ**: MACTripleDESは、CryptoStreamを介してTripleDES暗号化を行い、その結果をSingleBlockStreamに書き込む。SingleBlockStreamは最後のブロックのみを保持し、それがMAC値となる。

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

```
MACTripleDES
    │
    ├─ Class_Initialize
    │      ├─ TripleDESCryptoServiceProvider.New
    │      ├─ IV = {0,0,0,0,0,0,0,0}
    │      ├─ Padding = Zeros
    │      └─ SingleBlockStream.Init(8)
    │
    ├─ StartHash()
    │      ├─ mTripleDES.CreateEncryptor()
    │      └─ CryptoStream.New(mHashStream, encryptor, WriteMode)
    │
    ├─ TransformBlock() / ComputeHash()
    │      └─ mStream.WriteBlock()
    │
    ├─ EndHash()
    │      └─ mStream.FlushFinalBlock()
    │
    └─ Hash Get
           └─ mHashStream.Hash
```

### データフロー図

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

Triple DES鍵 ──────────────┐
                          ▼
                    ┌─────────────┐
                    │TripleDES    │
                    │CreateEncryptr│
                    │ (CBC Mode)  │
                    └─────────────┘
                          │
                          ▼
メッセージ ──────────▶ ┌─────────────┐
(Source)              │ CryptoStream│
                      │ (WriteMode) │
                      └─────────────┘
                          │
                          ▼
                    ┌─────────────┐
                    │SingleBlock  │
                    │   Stream    │ ──────▶ MAC値(8バイト)
                    │ (最終ブロック) │
                    └─────────────┘
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| MACTripleDES.cls | `Source/CorLib/System.Security.Cryptography/MACTripleDES.cls` | ソース | メインクラス |
| TripleDESCryptoServiceProvider.cls | `Source/CorLib/System.Security.Cryptography/TripleDESCryptoServiceProvider.cls` | ソース | Triple DES実装 |
| CryptoStream.cls | `Source/CorLib/System.Security.Cryptography/CryptoStream.cls` | ソース | ストリーム暗号化 |
| SingleBlockStream.cls | `Source/CorLib/System.Security.Cryptography/SingleBlockStream.cls` | ソース | 最終ブロック取得用 |
| HashAlgorithm.cls | `Source/CorLib/System.Security.Cryptography/HashAlgorithm.cls` | ソース | ハッシュインターフェース |
| KeyedHashAlgorithm.cls | `Source/CorLib/System.Security.Cryptography/KeyedHashAlgorithm.cls` | ソース | 鍵付きハッシュインターフェース |
