# 機能設計書 53-AHCIドライバ

## 概要

本ドキュメントは、FreeBSDにおけるSATA AHCI（Advanced Host Controller Interface）コントローラドライバの設計を記述する。AHCIはSerial ATA（SATA）ストレージデバイスへのアクセスを提供するホストコントローラインタフェース仕様の実装である。

### 本機能の処理概要

AHCIドライバは、SATA AHCIコントローラを制御し、SATA HDD/SSDデバイスへのブロックI/Oアクセスを提供する。CAM（Common Access Method）ストレージサブシステムと連携し、上位のファイルシステム層にストレージデバイスへの統一的なアクセスインタフェースを提供する。

**業務上の目的・背景**：SATA AHCIは現代のPC/サーバにおける標準的なストレージインタフェースであり、HDD/SSDへのアクセスに不可欠である。AHCIはNCQ（Native Command Queuing）、ホットプラグ、ポートマルチプライヤ等の高度な機能をサポートし、ストレージ性能と信頼性を向上させる。

**機能の利用シーン**：システム起動時のSATAデバイス検出、ファイルシステムへのディスクI/O、ホットプラグによるデバイスの動的追加/削除、SATAポートマルチプライヤ経由の複数デバイスアクセス。

**主要な処理内容**：
1. AHCIコントローラの検出・初期化（PCI/FDT）
2. SATAポート（チャネル）の初期化・管理
3. コマンドスロットの管理とDMA転送
4. 割り込み処理（MSI/MSI-X/レガシー対応）
5. NCQ（Native Command Queuing）サポート
6. ホットプラグ検出と処理
7. エンクロージャ管理（ahciem）
8. 電力管理（サスペンド/レジューム）
9. エラーリカバリとリセット処理

**関連システム・外部連携**：CAM（Common Access Method）ストレージサブシステムとの連携。CAM SIM（SCSI Interface Module）としてCAMに登録される。

**権限による制御**：カーネルドライバであるため、カーネル権限で動作。ユーザ空間からのアクセスはCAM経由のデバイスノード（/dev/da*, /dev/ada*）を通じて行われる。

## 関連画面

| 画面No | 画面名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| - | （カーネルドライバのため関連画面なし） | - | - |

## 機能種別

デバイスドライバ / ブロックI/O

## 入力仕様

### 入力パラメータ

| パラメータ名 | 型 | 必須 | 説明 | バリデーション |
|-------------|-----|-----|------|---------------|
| PCI Device ID | uint32 | Yes | AHCIコントローラのPCIデバイスID | AHCIクラスコードに一致 |
| AHCI BAR | resource | Yes | AHCIレジスタベースアドレス | 有効なメモリマップドI/O |
| CCB (CAM Control Block) | struct ccb | Yes | CAMからのI/Oリクエスト | 有効なCCBポインタ |

### 入力データソース

- PCI構成空間（デバイス検出）
- CAMサブシステム（I/Oリクエスト）
- AHCIレジスタ（ステータス読み取り）

## 出力仕様

### 出力データ

| 項目名 | 型 | 説明 |
|--------|-----|------|
| I/O完了通知 | CCB status | CAMへのI/O完了コールバック |
| デバイス情報 | ATA IDENTIFY | 検出されたSATAデバイスの情報 |
| 割り込み通知 | IRQ | I/O完了・エラー・ホットプラグイベント |

### 出力先

- CAMサブシステム（I/O完了通知）
- デバイスノード（/dev/ada*, /dev/da*）
- sysctl（統計情報）
- dmesg（デバイス検出ログ）

## 処理フロー

### 処理シーケンス

```
1. デバイス検出（probe）
   └─ PCI構成空間からAHCIコントローラを識別
2. デバイスアタッチ（attach）
   └─ AHCIレジスタマッピング、割り込み設定、DMA初期化
3. チャネル初期化
   └─ 各SATAポートの初期化、コマンドリスト・FIS受信バッファ割り当て
4. デバイス検出
   └─ SATAポートに接続されたデバイスの検出・識別
5. I/Oリクエスト処理
   └─ CAMからのCCBを受け取り、AHCIコマンドスロットに設定
6. DMA転送実行
   └─ PRDTの設定とコマンド発行
7. 割り込み処理
   └─ I/O完了、エラー、ホットプラグイベントの処理
8. エラーリカバリ
   └─ コマンドタイムアウト、リンクエラー時のリセット処理
```

### フローチャート

```mermaid
flowchart TD
    A[PCI probe] --> B{AHCIコントローラ?}
    B -->|Yes| C[attach - レジスタマッピング]
    B -->|No| Z[スキップ]
    C --> D[割り込み設定 MSI/MSI-X]
    D --> E[チャネル初期化]
    E --> F[DMAメモリ割り当て]
    F --> G[コマンドリスト/FIS初期化]
    G --> H[SATAデバイス検出]
    H --> I[CAM SIM登録]
    I --> J[I/O待ち受け]
    J --> K{CCBリクエスト}
    K --> L[コマンドスロット割り当て]
    L --> M[PRDT設定]
    M --> N[コマンド発行]
    N --> O{割り込み}
    O -->|完了| P[CCBコールバック]
    O -->|エラー| Q[エラーリカバリ]
    O -->|ホットプラグ| R[デバイス追加/削除]
    P --> J
    Q --> J
    R --> J
```

## ビジネスルール

### 業務ルール

| ルールNo | ルール名 | 内容 | 適用条件 |
|---------|---------|------|---------|
| BR-53-01 | NCQサポート | デバイスがNCQ対応の場合、最大32コマンドの同時発行が可能 | NCQ対応デバイス接続時 |
| BR-53-02 | ホットプラグ検出 | SATAポートの接続/切断を割り込みで検出 | ホットプラグ対応コントローラ |
| BR-53-03 | FBS対応 | FIS-Based Switching対応コントローラでポートマルチプライヤを効率的に管理 | FBS対応コントローラ |
| BR-53-04 | 電力管理 | サスペンド時にチャネル状態を保存、レジューム時に復元 | ACPIサスペンド/レジューム |

### 計算ロジック

PRDTエントリ数の計算: DMAセグメント数に応じてPRDTエントリを設定。最大セグメント数はAHCI仕様により65535エントリ。

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

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

該当なし（カーネルドライバ）。

### テーブル別操作詳細

該当なし。

## エラー処理

### エラーケース一覧

| エラーコード | エラー種別 | 発生条件 | 対処方法 |
|------------|----------|---------|---------|
| CAM_CMD_TIMEOUT | タイムアウト | コマンド応答なし | ポートリセット後リトライ |
| CAM_UNCOR_PARITY | データエラー | CRC/パリティエラー | リンクリセット後リトライ |
| CAM_ATA_STATUS_ERROR | ATAエラー | デバイスがエラーステータスを返した | エラーログ取得、上位に通知 |

### リトライ仕様

コマンドタイムアウト時はソフトリセット、失敗時はハードリセット（COMRESET）を実行。リセット後にコマンドをリトライ。

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

NCQモードでは最大32コマンドを同時に発行可能。コマンドスロット管理により、発行済みコマンドの追跡と完了通知を行う。

## パフォーマンス要件

- SATA 6Gbps（SATA III）の帯域幅を最大限活用
- NCQによるコマンドキューイングで順次I/Oのオーバーヘッドを削減
- MSI/MSI-X割り込みによる低レイテンシの割り込み処理

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

- カーネルドライバとして動作するため、バッファオーバーフロー等の脆弱性は特権昇格につながる可能性がある
- DMA操作のバウンダリチェックが適切に行われている

## 備考

- FreeBSDのAHCIドライバはAlexander Motin (mav@FreeBSD.org) により開発
- PCI接続（ahci_pci.c）、FDT接続（ahci_fsl_fdt.c、ahci_mv_fdt.c）、汎用（ahci_generic.c）の複数バックエンドを持つ

---

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

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

### 推奨読解順序

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

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | ahci.h | `sys/dev/ahci/ahci.h` | AHCIレジスタ定義、ATA定数、構造体定義 |

**読解のコツ**: ahci.hはATA/AHCIハードウェアレジスタの定義を含む。**30-80行目**のATA_DATA, ATA_FEATURE, ATA_STATUS等の定数はATAコマンドプロトコルの理解に重要。ATA_S_BUSY(0x80)、ATA_S_READY(0x40)等のステータスビットはI/O完了判定に使用される。

#### Step 2: コアドライバを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | ahci.c | `sys/dev/ahci/ahci.c` | AHCIドライバのコア実装 |

**主要処理フロー**:
1. **53-79行目**: ローカルプロトタイプ宣言 - ahci_intr, ahci_ch_init, ahci_begin_transaction等
2. **54-56行目**: 割り込みハンドラ（ahci_intr, ahci_intr_one, ahci_intr_one_edge）
3. **57-60行目**: チャネルライフサイクル（init, deinit, suspend, resume）
4. **65-66行目**: トランザクション処理（begin_transaction, dmasetprd）
5. **67-69行目**: コマンド実行・タイムアウト・完了処理
6. **70行目**: ahci_setup_fis - FIS（Frame Information Structure）の構築
7. **71-75行目**: DMAメモリ管理
8. **76-78行目**: ポート制御（reset, start, stop）

#### Step 3: PCI接続を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 3-1 | ahci_pci.c | `sys/dev/ahci/ahci_pci.c` | PCI AHCIコントローラのprobe/attach |

#### Step 4: エンクロージャ管理を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 4-1 | ahciem.c | `sys/dev/ahci/ahciem.c` | AHCIエンクロージャ管理（LEDインジケータ等） |

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

```
CAMサブシステム (cam_xpt.c)
    |
    +-- ahci_action() [ahci.c]  (CAM SIMアクションハンドラ)
        |
        +-- ahci_begin_transaction()
        |   +-- ahci_setup_fis()      (FIS構築)
        |   +-- ahci_dmasetprd()      (PRDTセットアップ)
        |   +-- ahci_execute_transaction()  (コマンド発行)
        |
        +-- ahci_ch_intr()             (割り込みハンドラ)
            +-- ahci_ch_intr_main()
                +-- ahci_end_transaction()  (完了処理)
                    +-- xpt_done()         (CAMコールバック)

ahci_pci_probe() / ahci_pci_attach()  (PCI接続)
    +-- ahci_ch_init()
        +-- ahci_dmainit()
        +-- ahci_slotsalloc()
        +-- ahci_reset()
        +-- ahci_start()
```

### データフロー図

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

CAM CCB      ────▶ ahci_begin_transaction()  ────▶ AHCIレジスタ書き込み
(I/Oリクエスト)        |                              (コマンド発行)
                    ahci_setup_fis()
                    ahci_dmasetprd()
                        |
AHCIレジスタ ◀──── ahci_ch_intr()           ────▶ CAM xpt_done()
(割り込み)          ahci_end_transaction()          (I/O完了通知)
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| ahci.h | `sys/dev/ahci/ahci.h` | ヘッダ | AHCIレジスタ定義、構造体 |
| ahci.c | `sys/dev/ahci/ahci.c` | ソース | AHCIドライバコア実装 |
| ahci_pci.c | `sys/dev/ahci/ahci_pci.c` | ソース | PCI AHCIコントローラ対応 |
| ahci_generic.c | `sys/dev/ahci/ahci_generic.c` | ソース | 汎用AHCI対応 |
| ahci_fsl_fdt.c | `sys/dev/ahci/ahci_fsl_fdt.c` | ソース | Freescale FDT対応 |
| ahci_mv_fdt.c | `sys/dev/ahci/ahci_mv_fdt.c` | ソース | Marvell FDT対応 |
| ahciem.c | `sys/dev/ahci/ahciem.c` | ソース | エンクロージャ管理 |
