Re: [dpdk-dev] [PATCH v5 2/3] PCI: support MMIO in rte_pci_ioport_map/unap/read/write
From: 谢华伟(此时此刻) <hidden>
Date: 2021-01-21 06:30:19
On 2021/1/12 16:23, Maxime Coquelin wrote:
Title should be something like: "bus/pci: support MMIO in PCI ioport accessors On 10/22/20 5:51 PM, 谢华伟(此时此刻) wrote:quoted
From: "huawei.xhw" <redacted> If IO BAR, we get PIO address. If MMIO BAR, we get mapped virtual address. We distinguish PIO and MMIO by their address like how kernel does. ioread/write8/16/32 is provided to access PIO/MMIO. BTW, for virtio on arch other than x86, BAR flag indicates PIO but is mapped.No acronym in the commit message.
BTW? fixed. PIO(programmed IO) and MMIO(memory mapped IO) explained.
Also, I am not sure to understand this comment. Does it means in the case of ARM for example, the IORESOURCE_IO flag is set but the base address is above PIO_MAX?
ARM doesn't have PIO but only MMIO. The device sets IORESOURCE_IO flag anyway. Should i remove this message as it causes confuse?
quoted
Signed-off-by: huawei.xhw <redacted>As in previous patch, we need your full name for the sign-off.
fixed.
quoted
--- drivers/bus/pci/linux/pci.c | 4 -- drivers/bus/pci/linux/pci_uio.c | 123 ++++++++++++++++++++++++++-------------- 2 files changed, 82 insertions(+), 45 deletions(-)diff --git a/drivers/bus/pci/linux/pci.c b/drivers/bus/pci/linux/pci.c index 0f38abf..0dc99e9 100644 --- a/drivers/bus/pci/linux/pci.c +++ b/drivers/bus/pci/linux/pci.c@@ -715,8 +715,6 @@ int rte_pci_write_config(const struct rte_pci_device *device, break; #endif case RTE_PCI_KDRV_IGB_UIO: - pci_uio_ioport_read(p, data, len, offset); - break;I think this part should be in patch 1.
Patch 1 handles IO port map. Patch 2 unifies IO/MMIO. Patch 3 handles vfio. I feel current split is more clear.
quoted
case RTE_PCI_KDRV_UIO_GENERIC: pci_uio_ioport_read(p, data, len, offset); break;@@ -736,8 +734,6 @@ int rte_pci_write_config(const struct rte_pci_device *device, break; #endif case RTE_PCI_KDRV_IGB_UIO: - pci_uio_ioport_write(p, data, len, offset); - break;Same here.quoted
case RTE_PCI_KDRV_UIO_GENERIC: pci_uio_ioport_write(p, data, len, offset); break;diff --git a/drivers/bus/pci/linux/pci_uio.c b/drivers/bus/pci/linux/pci_uio.c index 01f2a40..c19382f 100644 --- a/drivers/bus/pci/linux/pci_uio.c +++ b/drivers/bus/pci/linux/pci_uio.c@@ -379,14 +379,9 @@ char buf[BUFSIZ]; uint64_t phys_addr, end_addr, flags; unsigned long base; + bool iobar; int i; - if (rte_eal_iopl_init() != 0) { - RTE_LOG(ERR, EAL, "%s(): insufficient ioport permissions for PCI device %s\n", - __func__, dev->name); - return -1; - } - /* open and read addresses of the corresponding resource in sysfs */ snprintf(filename, sizeof(filename), "%s/" PCI_PRI_FMT "/resource", rte_pci_get_sysfs_path(), dev->addr.domain, dev->addr.bus,@@ -408,15 +403,30 @@ &end_addr, &flags) < 0) goto error; - if (!(flags & IORESOURCE_IO)) { - RTE_LOG(ERR, EAL, "%s(): bar resource other than IO is not supported\n", __func__); + if (flags & IORESOURCE_IO) { + iobar = 1; + base = (unsigned long)phys_addr; + RTE_LOG(INFO, EAL, "%s(): PIO BAR %08lx detected\n", __func__, base); + } else if (flags & IORESOURCE_MEM) { + iobar = 0; + base = (unsigned long)dev->mem_resource[bar].addr; + RTE_LOG(INFO, EAL, "%s(): MMIO BAR %08lx detected\n", __func__, base); + } else { + RTE_LOG(ERR, EAL, "%s(): unknown BAR type\n", __func__); + goto error; + } + + + if (iobar && rte_eal_iopl_init() != 0) { + RTE_LOG(ERR, EAL, "%s(): insufficient ioport permissions for PCI device %s\n", + __func__, dev->name); goto error; } - base = (unsigned long)phys_addr; - RTE_LOG(INFO, EAL, "%s(): PIO BAR %08lx detected\n", __func__, base); - if (base > UINT16_MAX) + if (iobar && (base > UINT16_MAX)) { + RTE_LOG(ERR, EAL, "%s(): %08lx too large PIO resource\n", __func__, base); goto error; + }It looks like above check could be moved directly to (flags & IORESOURCE_IO) case, so iobar boolean is not needed.
yes, code is more clear with your suggestion.