Linux kernel 实现PCIe Linux设备驱动程序(希望从内核驱动程序访问我的卡寄存器)

Linux kernel 实现PCIe Linux设备驱动程序(希望从内核驱动程序访问我的卡寄存器),linux-kernel,pci,Linux Kernel,Pci,我正在编写设备驱动程序以访问PCIe卡上FPGA中的内存。 卡引导并被探测/发现:- /proc/iomem 80000000-840fffff : PCI Bus #03 80000000-83ffffff : 0000:03:00.0 84000000-840fffff : 0000:03:00.0 因此,在读取ldd/etc时,我在80000000处编码了一个对request\u mem\u region的调用,并通过ioremap\u nocache 1) 我是否需要请求\u

我正在编写设备驱动程序以访问PCIe卡上FPGA中的内存。
卡引导并被探测/发现:-

/proc/iomem

80000000-840fffff : PCI Bus #03
  80000000-83ffffff : 0000:03:00.0
  84000000-840fffff : 0000:03:00.0
因此,在读取ldd/etc时,我在
80000000
处编码了一个对
request\u mem\u region
的调用,并通过
ioremap\u nocache

1) 我是否需要
请求\u mem\u region
以及
ioremap\u nocache
,我不能只使用后者吗

/
insmod
my设备驱动程序之后的proc/iomem:-

80000000-840fffff : PCI Bus #03
  80000000-83ffffff : 0000:03:00.0
    80000000-8003ffff : fp2
  84000000-840fffff : 0000:03:00.0
2) 在我看来不太合适

无论如何,读取不起作用(它不是像下面那样编码的,它有检查等):-

产出:-

address:0xfd500000, data:0xffffffff
我可以从mmap用户空间读取
x80000000+已知的\u REG\u位置

3) 我试过
\uuuuraw\ureadl
/
readl
,但也没有成功

4) 我可以在当前映射的地址读取吗

我为设备()编写了一个PCI驱动程序。但是寄存器空间的映射应该是相同的。我是这样做的

dm7820_device->pci[region].virt_addr = ioremap_nocache(address, length);
if (dm7820_device->pci[region].virt_addr == NULL) {
    printk(KERN_ERR "%s: ERROR: BAR%u remapping FAILED\n",
        &((dm7820_device->device_name)[0]), region);
    dm7820_release_resources();
    return -ENOMEM;
}

if (request_mem_region(address, length, &((dm7820_device->device_name)[0])) == NULL) {
    printk(KERN_ERR "%s: ERROR: I/O memory range %#lx-%#lx allocation FAILED\n",
        &((dm7820_device->device_name)[0]), address, (address + length - 1));
    dm7820_release_resources();
    return -EBUSY;
}
地址和长度值是从
pci\u resource\u start()
pci\u resource\u length()
调用返回的

然后您可以使用
ioread32()
使用
dm7820\u设备->pci[region]访问它。virt\u addr+


如果您有任何问题,请告诉我。

您的.tar文件需要密码。查看代码会很有帮助。我认为您的评论应该指向@willtake
dm7820_device->pci[region].virt_addr = ioremap_nocache(address, length);
if (dm7820_device->pci[region].virt_addr == NULL) {
    printk(KERN_ERR "%s: ERROR: BAR%u remapping FAILED\n",
        &((dm7820_device->device_name)[0]), region);
    dm7820_release_resources();
    return -ENOMEM;
}

if (request_mem_region(address, length, &((dm7820_device->device_name)[0])) == NULL) {
    printk(KERN_ERR "%s: ERROR: I/O memory range %#lx-%#lx allocation FAILED\n",
        &((dm7820_device->device_name)[0]), address, (address + length - 1));
    dm7820_release_resources();
    return -EBUSY;
}