队列模型 - 📘 一、命令结构概览(Figure 87) (第104页)
我们现在对 NVM Express® Base Specification, revision 2.0b 第 93 页 的内容进行中文深入解析与教学讲解。这页主要介绍 通用命令格式(Common Command Format) 中的数据传输字段,尤其聚焦在 PRP / SGL 的寻址方式、MPTR(Metadata Pointer) 和 DPTR(Data Pointer) 的定义与行为。
📘 一、命令结构概览(Figure 87)
| 字节范围(Bytes) | 字段名 | 描述说明 |
|---|---|---|
| 03:00 | CDW0 | 包含了 PSDT、FUSE、Opcode 等基础字段(详见 Figure 86) |
| 07:04 | NSID | 命名空间标识符(详见前页) |
| 11:08 | CDW2 | 命令特定字段(可选) |
| 15:12 | CDW3 | 命令特定字段(可选) |
| 23:16 | MPTR(Metadata Pointer) | 元数据地址指针,行为依赖于 PSDT 的设置 |
| 39:24 | DPTR(Data Pointer) | 命令所用数据的地址指针,包括 PRP 或 SGL 格式 |
| 43:40 | CDW10 | 命令特定字段(可选) |
| 47:44 | CDW11 | 命令特定字段(可选) |
🧩 二、MPTR(Metadata Pointer)字段详解
MPTR 用于提供命令所需的元数据地址。其行为由 CDW0.PSDT 字段的值决定:
✅ 情况 1:PSDT = 00b(使用 PRP)
- MPTR 指向一段连续的物理元数据缓冲区
- 地址需要 dword 对齐(低两位
00b) - 控制器不强制检查对齐,但可能返回
Invalid Field in Command - 若未报错,将默认低位为
00b
✅ 情况 2:PSDT = 01b(使用 SGL,MPTR 指向物理元数据缓冲区)
- MPTR 同样指向连续物理缓冲区,对齐要求由 Identify Controller 中的
SGLS[17]决定
✅ 情况 3:PSDT = 10b(SGL segment)
- MPTR 指向一个只包含 一个 SGL 描述符 的 segment
- 地址需 qword 对齐(低三位
000b) - 描述符如果是 SGL Data Block,即可表示全部元数据的传输
- 控制器可选是否强制检查对齐
📦 三、DPTR(Data Pointer)字段详解
DPTR 是数据传输的核心字段,它的结构依据 PSDT 的不同而不同。
✅ 情况 1:PSDT = 00b → 使用 PRP(适用于 NVMe over PCIe)
📍PRP1:
- 第一个页面地址或 PRP List 指针
📍PRP2:
- 用于两种情况:
- 数据跨越一页时 → 指向第二页
- 数据跨越多页时 → 是 PRP List 的地址指针
PRP 地址使用规则:
| 情况 | PRP2 行为 |
|---|---|
| 数据 ≤ 1 页,无偏移 | PRP2 保留 |
| 数据 = 1 页,有偏移 | PRP2 是第二页地址 |
| 数据 = 2 页,PRP1 offset = 0h | PRP2 是第二页地址 |
| 数据 ≥ 2 页,有 offset | PRP2 是 PRP List 指针 |
| 数据 ≥ 2 页,offset = 0h | PRP2 是 PRP List 指针 |
✅ 情况 2:PSDT = 01b 或 10b → 使用 SGL
- DPTR 被解释为:
- SGL Entry 1 (SGL1):表示第一个 SGL segment
- 若为 SGL Data Block / Keyed SGL Block / Transport SGL → 可描述完整传输
- 若不够用 → 使用 SGL Segment 或 Last Segment 继续扩展(参见 §4.1.2)
📌 SGL 描述符类型与 Transport 实现有关,可参阅 NVMe Transport binding specification 获取每种传输(如 TCP、RDMA)的支持列表。
📘 四、数据传输模式小结对比(PRP vs SGL)
| 比较项目 | PRP 模式(00b) | SGL 模式(01b / 10b) |
|---|---|---|
| 适用场景 | NVMe over PCIe(Admin / I/O) | Fabrics 环境下必须使用 |
| 寻址方式 | 基于页对齐 | 可表示任意内存布局(支持段结构) |
| 支持元数据传输 | 使用 MPTR | 使用 MPTR(可扩展为 SGL segment) |
| 对齐要求 | PRP1 / PRP2 均需页对齐 | SGL 地址需按类型进行对齐 |
| 灵活性 | 适合页内数据块传输 | 更强(适合分散数据) |
🧠 五、总结与关键点
| 字段 | 核心用途 | 依赖字段 | 特别注意事项 |
|---|---|---|---|
| MPTR | 指向元数据 | PSDT | 对齐要求:dword / qword / SGL 定义依赖 PSDT 值 |
| DPTR | 指向数据 | PSDT | PRP or SGL 互斥,PRP1/2 和 SGL1 定义互斥使用 |
| PRP1/2 | 页面级寻址 | PSDT=00b | 跨页数据用 PRP2 或 PRP List 表示 |
| SGL1 | 灵活描述数据段 | PSDT=01b/10b | 支持嵌套 segment,适用于复杂数据结构 |
如果你希望进一步解析:
- SGL 描述符的结构与类型定义(§4.1.2)
- PRP List 的具体结构、跨页链表机制
- 如何在实际命令中设置 MPTR / DPTR 字段进行高效数据传输
我可以继续带你逐步拆解。你希望我们下一步深入哪一部分?