]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
of: address: Add parent_bus_addr to struct of_pci_range
authorFrank Li <Frank.Li@nxp.com>
Tue, 19 Nov 2024 19:44:19 +0000 (14:44 -0500)
committerBjorn Helgaas <bhelgaas@google.com>
Sat, 18 Jan 2025 21:04:23 +0000 (15:04 -0600)
Add a new field called 'parent_bus_addr' to struct of_pci_range to use
when retrieving parent bus address information.

Refer to the diagram below to better understand that the bus fabric in
some systems (like i.MX8QXP) does not always use a 1:1 address map
between input and output.

Currently, many controller drivers use the cpu_addr_fixup() callback
that would often hardcode address translation directly in the code, e.g.,
"cpu_addr & CDNS_PLAT_CPU_TO_BUS_ADDR" or "cpu_addr + BUS_IATU_OFFSET",
etc., even though those translations *should* be described via DT.

However, the cpu_addr_fixup() can be eliminated if DT correctly reflects
hardware behavior and drivers use 'parent_bus_addr' in struct of_pci_range.

            ┌─────────┐                    ┌────────────┐
 ┌─────┐    │         │ IA: 0x8ff8_0000    │            │
 │ CPU ├───►│   ┌────►├─────────────────┐  │ PCI        │
 └─────┘    │   │     │ IA: 0x8ff0_0000 │  │            │
  CPU Addr  │   │  ┌─►├─────────────┐   │  │ Controller │
0x7ff8_0000─┼───┘  │  │             │   │  │            │
            │      │  │             │   │  │            │   PCI Addr
0x7ff0_0000─┼──────┘  │             │   └──► IOSpace   ─┼────────────►
            │         │             │      │            │    0
0x7000_0000─┼────────►├─────────┐   │      │            │
            └─────────┘         │   └──────► CfgSpace  ─┼────────────►
             BUS Fabric         │          │            │    0
                                │          │            │
                                └──────────► MemSpace  ─┼────────────►
                        IA: 0x8000_0000    │            │  0x8000_0000
                                           └────────────┘

bus@5f000000 {
        compatible = "simple-bus";
        #address-cells = <1>;
        #size-cells = <1>;
        ranges = <0x80000000 0x0 0x70000000 0x10000000>;

        pcie@5f010000 {
                compatible = "fsl,imx8q-pcie";
                reg = <0x5f010000 0x10000>, <0x8ff00000 0x80000>;
                reg-names = "dbi", "config";
                #address-cells = <3>;
                #size-cells = <2>;
                device_type = "pci";
                bus-range = <0x00 0xff>;
                ranges = <0x81000000 0 0x00000000 0x8ff80000 0 0x00010000>,
                         <0x82000000 0 0x80000000 0x80000000 0 0x0ff00000>;
...
};
};

In the diagram above, the 'parent_bus_addr' field in struct of_pci_range
can indicate internal address (IA) address information.

Link: https://lore.kernel.org/r/20241119-pci_fixup_addr-v8-1-c4bfa5193288@nxp.com
Signed-off-by: Frank Li <Frank.Li@nxp.com>
[kwilczynski: commit log]
Signed-off-by: Krzysztof Wilczyński <kwilczynski@kernel.org>
Signed-off-by: Bjorn Helgaas <bhelgaas@google.com>
Reviewed-by: Rob Herring (Arm) <robh@kernel.org>
Acked-by: Manivannan Sadhasivam <manivannan.sadhasivam@linaro.org>
drivers/of/address.c
include/linux/of_address.h

index c5b925ac469f16b8ae4b8275b60210a2d583ff83..6373e69ebb0842298a4dc2a21cc69d2226663c08 100644 (file)
@@ -815,6 +815,8 @@ struct of_pci_range *of_pci_range_parser_one(struct of_pci_range_parser *parser,
        else
                range->cpu_addr = of_translate_address(parser->node,
                                parser->range + na);
+
+       range->parent_bus_addr = of_read_number(parser->range + na, parser->pna);
        range->size = of_read_number(parser->range + parser->pna + na, ns);
 
        parser->range += np;
index 9e034363788acc80f645ffab8c8ee0c8c762a9b2..0cff9036539168b0cf2826ee34417738a4836ace 100644 (file)
@@ -26,6 +26,7 @@ struct of_pci_range {
                u64 bus_addr;
        };
        u64 cpu_addr;
+       u64 parent_bus_addr;
        u64 size;
        u32 flags;
 };