If I have only the physical address of device buffer (PCIe), how can I map this buffer to user-space?

不问归期 提交于 2019-12-02 08:09:05

The Linux kernel, at least, versions 2.6.x use the ioremap() function.

void *vaddr = ioremap (phys_addr, size_addr);
if (vaddr) {
  /* do stuff with the memory using vaddr pointer */
  iounmap (vaddr);
}

You should make a previous call to request_mem_region() to check if that memory space is already reclaimed by another driver, and politely request that memory to be owned by your code (driver). The complete example should look like this:

void *vaddr;
if (request_mem_region (phys_addr, size_addr, "my_driver")) {
  vaddr = ioremap (phys_addr, size_addr);
  if (vaddr) {
    /* do stuff with the memory */
    iounmap (vaddr);
  }
  release_mem_region (phys_addr, size_addr);
}

You can check your ownership by checking /proc/iomem, which will reflect the address range and the owner of every piece of memory in your system.

UPDATE: I don't really know if this works for 64-bit kernels. It does for 32-bit. If 64-bit kernel don't have these kernel functions, they will have similar ones, I guess.

Mapping PCI resource is dependent on the architecture.

BARs are already available to userspace with the sysfs files /sys/bus/pci/devices/*/resource*, which support mmap.

This is implemented by the function pci_mmap_resource in drivers/pci/pci-sysfs.c, which ends up calling pci_mmap_page_range.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!