我在自定义驱动程序中使用dma_alloc_coherent()
来获取虚拟地址和总线地址。
res->KernelAddress = (u64)dma_alloc_coherent( &DevExt->pdev->dev, size, &res->BusAddress, GFP_ATOMIC );
打印(%llx)总线地址(res-> BusAddress)时,我得到了80009000。 我检查了/ proc / iomem的日志以验证范围,但是有多个条目。
/ proc / iomem的日志如下所示:
10000000-10000fff : /pcie-controller@10003000/pci@1,0
10003000-100037ff : pcie-pads
10003800-10003fff : pcie-afi
10004000-10004fff : /pcie-controller@10003000/pci@3,0
40000000-4fffffff : pcie-config-space
50100000-57ffffff : pcie-non-prefetchable
50800000-52ffffff : PCI Bus 0000:01
50800000-5087ffff : 0000:01:00.0
51000000-51ffffff : 0000:01:00.0
52000000-52ffffff : 0000:01:00.0
58000000-7fffffff : pcie-prefetchable
58000000-58ffffff : PCI Bus 0000:01
58000000-58ffffff : 0000:01:00.0
80000000-d82fffff : System RAM
80080000-810fafff : Kernel code
8123f000-814b3fff : Kernel data
d9300000-efffffff : System RAM
f0200000-275ffffff : System RAM
276600000-2767fffff : System RAM
dma_mmap_coherent()
之后使用dma_alloc_coherent()
进行正确的映射?谢谢!
答案 0 :(得分:0)
来自https://medium.com/@visualskyrim/test-your-redux-container-with-enzyme-a0e10c0574ec(此文件的某些详细信息现在已过时,但这是该问题的最佳概述):
本质上,寻址内存的三种方法是(这是“真实内存”, 即正常的RAM,请参阅稍后的其他详细信息):
CPU未翻译。这是“物理”地址。实际地址 CPU在内存总线上驱动零时看到的是0。
CPU转换的地址。这是“虚拟”地址, 完全在CPU本身内部,而CPU做适当的处理 翻译成“ CPU未翻译”。
总线地址。这是其他设备看到的内存地址, 不是CPU。现在,理论上可能会有很多不同的总线 地址,每个设备以特定于设备的方式查看内存,但是 幸运的是,大多数硬件设计师并没有积极地尝试 事情比必要的要复杂,因此您可以假设所有 外部硬件以相同的方式看到内存。
现在,在普通PC上,总线地址与物理地址完全相同 地址,事情确实很简单。但是,它们就是这么简单 因为内存和设备共享相同的地址空间,即 通常在其他PCI / ISA设置上不一定是正确的。
最重要的是,您的问题的答案取决于体系结构。
在您的/proc/iomem
代码段中,请注意该列表是嵌套的。 80009000
地址似乎分为两部分,因为其中一个部分是另一部分的子集。 如果该地址是物理内存地址,则可以,它是一个“内核代码地址”,要从dma_alloc_coherent
返回是一件奇怪的事情。这使我相信物理地址与架构上的总线地址不相同。
dma_alloc_coherent
还在内核虚拟地址空间中映射内存,因此您无需执行任何其他操作即可从代码中访问它。 (dma_mmap_coherent
用于将内存映射到用户虚拟地址空间。)