PCIe - DMA:一致与流式内存

use*_*930 3 linux memory driver dma pci-e

目前,我正在为 Linux 的 PCIe 驱动程序添加 DMA。当我阅读文档时,它通过使用 API 提到了一致或连贯的内存:

pci_set_consistent_dma_mask(...)
Run Code Online (Sandbox Code Playgroud)

但从来没有真正谈论过为什么要使用它或它的作用。似乎提到调用该函数以获得最佳实践和未来证明。我能收集到的最好结果是一致的 DMA 内存没有缓存效果,并且一旦正确设置(假设我正确读取),内存就会在设备(FPGA)和 CPU 之间写入,无需任何软件/驱动程序干预。所以我的问题是:

  1. 假设 PCIe 设备不需要一致的内存,那么为什么会有人使用它,或者在什么情况下使用一致的内存?
  2. 如果我使用一致的内存,那么我是否不需要在 PCIe 驱动程序中为 DMA 实现中断?如果为真,那么用户空间代码和设备如何知道传输已发生?
  3. 如果我连续传输很多小数据包,大约 50 字节,有时传输更大的数据包,大约 6 kB,哪种 DMA 内存更好:一致还是流式传输?

Bra*_*rad 5

可以这样想:“一致”意味着它会在 CPU 和总线之间自动保持一致,而无需专门对其进行任何同步。例如 - 假设我有一个用于入站和出站数据包的记忆环。它的寿命将是整个时间系统在使用,我将要检查它所有的时间。我想这是始终一致的,因为如果不是我将不得不(手动)齐平或同步高速缓存,如果这是昂贵的,我不得不这样做很时候我感动的戒指-这将是一场噩梦.

另一方面 - 让我们使用我正在传输的单个数据缓冲区。我不是一种“一次性”交易。我可以让设备传输它——也许需要很多 PCI 周期来完成 DMA。也许这是不一致的。没关系 - 但完成后我可以刷新/同步缓存/强制一致性。如果这样做需要一点额外的时间 - 没问题 - 因为我只做一次。

所以你可能会问“为什么不让一切都保持一致”。答案是通常会有一定程度的开销来使事情保持一致。根据架构,这可能很重要。所以在这种情况下,有一些规定允许不一致(流)映射,这些映射不做缓存一致性(但需要显式同步)。因此,允许不一致的传输可能会给您带来一些性能。

也请记住 - 在某些情况下,您永远不需要任何一致性。例如 - 从网络设备读取缓冲区到内存,然后将该内存写入磁盘控制器。这些数据可能永远不会被 CPU 读取/使用 - 所以为什么要在 CPU 缓存上放置任何开销来跟踪它。

至于你对“中断”的评论——这有点奇怪。在“正常”情况下 - 您可能在一致的内存中拥有一个控制结构(如 Tx/Rx 环),您可以通过轮询来告诉您事务是否已完成。但实际传输的数据将位于不同的内存中,该内存可能是流式传输或不一致的。