我对使用PCIe设备的DMA传输感到有点困惑。
比如说,我有一个从PCIe设备,我想使用DMA事务将一个数据块从设备传输到RAM。请注意,该设备是从属设备,并且没有DMA“机器”。
我知道我需要先在RAM中获取一个可DMA的缓冲区(通过分配一个连贯的缓冲区,或者通过映射一个页面)。
但下一步是什么? 启动从地址S到地址D的N个字节的DMA传输的API是什么?
现代系统是否可以向从属 pci设备发出DMA传输?如果是这样,那么Linux API是什么?
正如here所说:
[ISA] 在最初的IBM PC中,只有一个Intel 8237 DMA控制器[...] 与ISA不同,PCI架构没有中央DMA控制器。相反,任何PCI组件都可以请求控制总线(“成为总线主控”)并请求读取和写入系统存储器
PCI总线没有“中央”DMA控制器 - 相反,每个设备都可以是DMA“控制器”。
答案 0 :(得分:0)
首先,现代PC内没有奴隶和奴隶。有南桥(在PCI)或Root Complex(PCI-express设备树的根),还有一些其他PCI / PCIe演员,如桥,焊接芯片,插卡,硬件调试器等。我会假设你是询问插卡或其他外围设备,如焊接声卡或以太网芯片。
根据“事务层数据包”(TLP,“PCIe的最上层”)的 this detailed description,有“总线主控权(DMA)”:
在PCIe上,它的异国情调明显减少。 ...总线上的任何人都可以在总线上发送读写TLP,就像Root Complex一样。这允许外设直接访问CPU的内存(DMA)或与对等外设交换TLP(在交换实体支持的范围内)。
此外,插入设备的DMA功能也有一些好处:DMA attack。并且PCIe被列为能够启动DMA传输:
如果外部设备有FireWire,ExpressCard,Thunderbolt或其他扩展端口(如PCI和 PCI-Express ),系设备直接到物理地址空间。
我认为,没有用于编程从外围设备本身启动的DMA传输的通用API。这取决于设备是什么,何时应该启动DMA以及将要发送什么。