本文将mark下NVMe CMB机制相关notes。

1. What

CMB(Controller Memory Buffer)是指SSD控制器内部的读写缓冲区,与HMB(Host Memory Buffer)的不同处在于所使用的内存地址位于控制器自己的内存中,而不是位于主机内存中,但它们使用队列的方式都是一样的。

NVMe CMB是NVMe SSD上的一块内存空间,可以通过PCIe MMIO BAR的方式暴露到主机内存空间中,并可由主机直接读写。这一块内存空间可以用来放置一些NVMe上特定的数据结构(如 SQ,CQ等),也可以将需要传输的数据直接放在CMB中。

2. CMB 的功能

CMB 至少需要NVMe设备增加下面两个额外的寄存器,其中CMBLOC表示CMB的位置,CMBSZ表示CMB的大小,另外其中还附带了一些feature的标志位。关于这两个寄存器的细节可以阅读NVMe spec中的相关内容:

  • 3.1.3.11 Offset 38h: CMBLOC – Controller Memory Buffer Location
  • 3.1.3.12 Offset 3Ch: CMBSZ – Controller Memory Buffer Size

下图展示了CMBSZ中所包含的一些feature的介绍:

  1. Write Data Support (WDS): 对于将数据从主机写入到设备的命令(如Write),可以直接写入到CMB中
  2. Read Data Support (RDS): 对于将数据从设备读取到主机的命令(如Read),可以直接从CMB中读取
  3. PRP SGL List Support (LISTS): 可以将PRP List和SGL List放在CMB中
  4. Completion Queue Support (CQS): 可以将CQ放在CMB中
  5. Submission Queue Support (SQS): 可以将SQ放在CMB中

PRP List的定义如下:

3. 使用CMB的例子

3.1 将CQ和SQ都放在CMB中

以写SQ为例,原来是主机先把请求写到内存的SQ,然后写Doorbell通知SSD,然后SSD再从内存中的SQ将命令拷贝过来。

现在是主机直接写到CMB中的SQ,然后写Doorbell通知SSD。

两个相比较,后者少了一次one read from the controller to the host,将SQ放在CMB上降低了执行命令的延迟。

Submission Queues in host memory require the controller to perform a PCI Express read from host memory in order to fetch the queue entries. Submission Queues in controller memory enable host software to directly write the entire Submission Queue Entry to the controller’s internal memory space, avoiding one read from the controller to the host. This approach reduces latency in command execution and improves efficiency in a PCI Express fabric topology that may include multiple switches.

3.2 让CMB支持数据传输,优化NIC和NVMe SSD之间的数据传输

原本将数据从NIC发送到SSD需要从内存中转一次,现在不需要,直接发送到CMB里就好。

3.2 让CMB支持数据传输,优化NVMe SSD之间的数据传输

利用了p2p功能,在NVMe设备之间直接传数据到CMB上即可,完全无需CPU和内存的介入,也不需要Root Complex参与其中。

4. Spec关键notes

5. p2p操作序列


RDMA网卡利用p2p将数据写入到NVMe盘

  1. driver计算出要写入到NVMe盘的数据量,从CMB中分配一段连续的buffer
  2. RDMA利用p2p(在RDMA的MTT中,将VA映射到CMB的MMIO地址即可)将数据写入到CMB中的buffer
  3. driver往submission queue中下发写盘的命令
  4. driver更新SQ tail doorbell寄存器
  5. NVMe controller根据command中的metadata与CMB buffer中的内容,将数据刷到NVMe盘中

6. 总结

在CMB之前,像SQ、CQ、PRP List、Write Data、Read Data都是放置在HMB(DRAM)中;有了CMB之后,SQ、CQ、PRP List、Write Data、Read Data可以放置在CMB(MMIO)中。

driver为了效率,将与NVMe controller交互的信息,由DRAM移动到了MMIO(CMB)中。CMB的RDS和WDS可以支持p2p,同时SQS这些feature可以提升NVMe controller的执行效率(比如避免了NVMe controller DMA读取SQE这些信息,直接从CMB中读取即可)。


参考资料:

  1. NVMe 1.3 spec
  2. NVME CMB详解
  3. Enabling the NVMe™ CMB and PMR Ecosystem
  4. Controller Memory Buffers