Re: [RFC] Changing pci_iounmap to take 'bar' argument

From: Russell King
Date: Sat May 28 2005 - 15:09:48 EST


On Thu, May 26, 2005 at 08:21:07AM -0700, Linus Torvalds wrote:
>
>
> On Thu, 26 May 2005, Benjamin Herrenschmidt wrote:
> >
> > foo = pci_iomap(dev, bar, pci_resource_len(dev, bar));
>
> Btw, this kind of code should be just
>
> foo = pci_iomap(dev, bar, 0);
>
> because the third argument is _not_ a length, it's a _maximum_ length we
> need to map, with zero meaning "everything" (as does ~0ul, of course, but
> zero is obviously easier).
>
> The only people who want to use non-zero are things like frame-buffers
> that might have hundreds of megabytes of memory, but the kernel only needs
> to map the actual thing visible on the screen.

Note also that framebuffer drivers may also wish to map a bar from a
specific offset and length. Eg, CyberPro has one BAR which is something
like 16MB large, with the framebuffer in the low addresses and the
registers at 8MB in. (poor example I know.)

I believe the IXP folk have issues similar to this though, but more
extreme.

> Yeah. It shouldn't be a problem on 64-bit architectures, and even on
> 32-bit ones the IO-port range really _should_ be fairly small, and a small
> amount of special casing should hopefully fix it.
>
> A lot of architectures end up having to separate PIO and MMIO anyway,
> which is - together with hysterical raisins, of course - why the existing
> interfaces just assumed that was possible.

Maybe the interface is just wrong. Maybe it should be:

struct map {
void __iomem *cpu;
/* whatever platform data is required */
};

err = pci_iomap(dev, bar, size, &map);
...
pci_iounmap(&map);

The reason I suggest this is that we've had problems with the PCI DMA API -
remember that driver people whinged about having to store the dma_addr_t
cookie and we introduced the following crap:

#define DECLARE_PCI_UNMAP_ADDR(ADDR_NAME) dma_addr_t ADDR_NAME;
#define DECLARE_PCI_UNMAP_LEN(LEN_NAME) __u32 LEN_NAME;
#define pci_unmap_addr(PTR, ADDR_NAME) ((PTR)->ADDR_NAME)
#define pci_unmap_addr_set(PTR, ADDR_NAME, VAL) (((PTR)->ADDR_NAME) = (VAL))
#define pci_unmap_len(PTR, LEN_NAME) ((PTR)->LEN_NAME)
#define pci_unmap_len_set(PTR, LEN_NAME, VAL) (((PTR)->LEN_NAME) = (VAL))

Let's not make this same mistake again! (just like we unknowingly
repeated it for the new DMA API... which should have contained the
returned cookies - the platform specific data which may be just the
CPU address for trivial x86 cases - inside a structure with macros
for accessing them. Magically all the above mess vanishes.)


--
Russell King
Linux kernel 2.6 ARM Linux - http://www.arm.linux.org.uk/
maintainer of: 2.6 Serial core
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/