Commit 14868d78 authored by Bjorn Helgaas's avatar Bjorn Helgaas

Merge branch 'remotes/lorenzo/pci/misc'

- Add macros for PCI Configuration Mechanism #1 and use them in the
  ftpci100, mt7621, and tegra drivers (Pali Rohár)

* remotes/lorenzo/pci/misc:
  PCI: tegra: Use PCI_CONF1_EXT_ADDRESS() macro
  PCI: mt7621: Use PCI_CONF1_EXT_ADDRESS() macro
  PCI: ftpci100: Use PCI_CONF1_ADDRESS() macro
  PCI: Add standard PCI Config Address macros
parents e302baff 8bb7ff12
...@@ -103,13 +103,6 @@ ...@@ -103,13 +103,6 @@
#define FARADAY_PCI_DMA_MEM2_BASE 0x00000000 #define FARADAY_PCI_DMA_MEM2_BASE 0x00000000
#define FARADAY_PCI_DMA_MEM3_BASE 0x00000000 #define FARADAY_PCI_DMA_MEM3_BASE 0x00000000
/* Defines for PCI configuration command register */
#define PCI_CONF_ENABLE BIT(31)
#define PCI_CONF_WHERE(r) ((r) & 0xFC)
#define PCI_CONF_BUS(b) (((b) & 0xFF) << 16)
#define PCI_CONF_DEVICE(d) (((d) & 0x1F) << 11)
#define PCI_CONF_FUNCTION(f) (((f) & 0x07) << 8)
/** /**
* struct faraday_pci_variant - encodes IP block differences * struct faraday_pci_variant - encodes IP block differences
* @cascaded_irq: this host has cascaded IRQs from an interrupt controller * @cascaded_irq: this host has cascaded IRQs from an interrupt controller
...@@ -190,11 +183,8 @@ static int faraday_raw_pci_read_config(struct faraday_pci *p, int bus_number, ...@@ -190,11 +183,8 @@ static int faraday_raw_pci_read_config(struct faraday_pci *p, int bus_number,
unsigned int fn, int config, int size, unsigned int fn, int config, int size,
u32 *value) u32 *value)
{ {
writel(PCI_CONF_BUS(bus_number) | writel(PCI_CONF1_ADDRESS(bus_number, PCI_SLOT(fn),
PCI_CONF_DEVICE(PCI_SLOT(fn)) | PCI_FUNC(fn), config),
PCI_CONF_FUNCTION(PCI_FUNC(fn)) |
PCI_CONF_WHERE(config) |
PCI_CONF_ENABLE,
p->base + FTPCI_CONFIG); p->base + FTPCI_CONFIG);
*value = readl(p->base + FTPCI_DATA); *value = readl(p->base + FTPCI_DATA);
...@@ -225,11 +215,8 @@ static int faraday_raw_pci_write_config(struct faraday_pci *p, int bus_number, ...@@ -225,11 +215,8 @@ static int faraday_raw_pci_write_config(struct faraday_pci *p, int bus_number,
{ {
int ret = PCIBIOS_SUCCESSFUL; int ret = PCIBIOS_SUCCESSFUL;
writel(PCI_CONF_BUS(bus_number) | writel(PCI_CONF1_ADDRESS(bus_number, PCI_SLOT(fn),
PCI_CONF_DEVICE(PCI_SLOT(fn)) | PCI_FUNC(fn), config),
PCI_CONF_FUNCTION(PCI_FUNC(fn)) |
PCI_CONF_WHERE(config) |
PCI_CONF_ENABLE,
p->base + FTPCI_CONFIG); p->base + FTPCI_CONFIG);
switch (size) { switch (size) {
......
...@@ -415,13 +415,6 @@ static inline u32 pads_readl(struct tegra_pcie *pcie, unsigned long offset) ...@@ -415,13 +415,6 @@ static inline u32 pads_readl(struct tegra_pcie *pcie, unsigned long offset)
* address (access to which generates correct config transaction) falls in * address (access to which generates correct config transaction) falls in
* this 4 KiB region. * this 4 KiB region.
*/ */
static unsigned int tegra_pcie_conf_offset(u8 bus, unsigned int devfn,
unsigned int where)
{
return ((where & 0xf00) << 16) | (bus << 16) | (PCI_SLOT(devfn) << 11) |
(PCI_FUNC(devfn) << 8) | (where & 0xff);
}
static void __iomem *tegra_pcie_map_bus(struct pci_bus *bus, static void __iomem *tegra_pcie_map_bus(struct pci_bus *bus,
unsigned int devfn, unsigned int devfn,
int where) int where)
...@@ -443,7 +436,9 @@ static void __iomem *tegra_pcie_map_bus(struct pci_bus *bus, ...@@ -443,7 +436,9 @@ static void __iomem *tegra_pcie_map_bus(struct pci_bus *bus,
unsigned int offset; unsigned int offset;
u32 base; u32 base;
offset = tegra_pcie_conf_offset(bus->number, devfn, where); offset = PCI_CONF1_EXT_ADDRESS(bus->number, PCI_SLOT(devfn),
PCI_FUNC(devfn), where) &
~PCI_CONF1_ENABLE;
/* move 4 KiB window to offset within the FPCI region */ /* move 4 KiB window to offset within the FPCI region */
base = 0xfe100000 + ((offset & ~(SZ_4K - 1)) >> 8); base = 0xfe100000 + ((offset & ~(SZ_4K - 1)) >> 8);
......
...@@ -30,6 +30,8 @@ ...@@ -30,6 +30,8 @@
#include <linux/reset.h> #include <linux/reset.h>
#include <linux/sys_soc.h> #include <linux/sys_soc.h>
#include "../pci.h"
/* MediaTek-specific configuration registers */ /* MediaTek-specific configuration registers */
#define PCIE_FTS_NUM 0x70c #define PCIE_FTS_NUM 0x70c
#define PCIE_FTS_NUM_MASK GENMASK(15, 8) #define PCIE_FTS_NUM_MASK GENMASK(15, 8)
...@@ -120,19 +122,12 @@ static inline void pcie_port_write(struct mt7621_pcie_port *port, ...@@ -120,19 +122,12 @@ static inline void pcie_port_write(struct mt7621_pcie_port *port,
writel_relaxed(val, port->base + reg); writel_relaxed(val, port->base + reg);
} }
static inline u32 mt7621_pcie_get_cfgaddr(unsigned int bus, unsigned int slot,
unsigned int func, unsigned int where)
{
return (((where & 0xf00) >> 8) << 24) | (bus << 16) | (slot << 11) |
(func << 8) | (where & 0xfc) | 0x80000000;
}
static void __iomem *mt7621_pcie_map_bus(struct pci_bus *bus, static void __iomem *mt7621_pcie_map_bus(struct pci_bus *bus,
unsigned int devfn, int where) unsigned int devfn, int where)
{ {
struct mt7621_pcie *pcie = bus->sysdata; struct mt7621_pcie *pcie = bus->sysdata;
u32 address = mt7621_pcie_get_cfgaddr(bus->number, PCI_SLOT(devfn), u32 address = PCI_CONF1_EXT_ADDRESS(bus->number, PCI_SLOT(devfn),
PCI_FUNC(devfn), where); PCI_FUNC(devfn), where);
writel_relaxed(address, pcie->base + RALINK_PCI_CONFIG_ADDR); writel_relaxed(address, pcie->base + RALINK_PCI_CONFIG_ADDR);
...@@ -147,7 +142,7 @@ static struct pci_ops mt7621_pcie_ops = { ...@@ -147,7 +142,7 @@ static struct pci_ops mt7621_pcie_ops = {
static u32 read_config(struct mt7621_pcie *pcie, unsigned int dev, u32 reg) static u32 read_config(struct mt7621_pcie *pcie, unsigned int dev, u32 reg)
{ {
u32 address = mt7621_pcie_get_cfgaddr(0, dev, 0, reg); u32 address = PCI_CONF1_EXT_ADDRESS(0, dev, 0, reg);
pcie_write(pcie, address, RALINK_PCI_CONFIG_ADDR); pcie_write(pcie, address, RALINK_PCI_CONFIG_ADDR);
return pcie_read(pcie, RALINK_PCI_CONFIG_DATA); return pcie_read(pcie, RALINK_PCI_CONFIG_DATA);
...@@ -156,7 +151,7 @@ static u32 read_config(struct mt7621_pcie *pcie, unsigned int dev, u32 reg) ...@@ -156,7 +151,7 @@ static u32 read_config(struct mt7621_pcie *pcie, unsigned int dev, u32 reg)
static void write_config(struct mt7621_pcie *pcie, unsigned int dev, static void write_config(struct mt7621_pcie *pcie, unsigned int dev,
u32 reg, u32 val) u32 reg, u32 val)
{ {
u32 address = mt7621_pcie_get_cfgaddr(0, dev, 0, reg); u32 address = PCI_CONF1_EXT_ADDRESS(0, dev, 0, reg);
pcie_write(pcie, address, RALINK_PCI_CONFIG_ADDR); pcie_write(pcie, address, RALINK_PCI_CONFIG_ADDR);
pcie_write(pcie, val, RALINK_PCI_CONFIG_DATA); pcie_write(pcie, val, RALINK_PCI_CONFIG_DATA);
......
...@@ -776,4 +776,49 @@ static inline pci_power_t mid_pci_get_power_state(struct pci_dev *pdev) ...@@ -776,4 +776,49 @@ static inline pci_power_t mid_pci_get_power_state(struct pci_dev *pdev)
} }
#endif #endif
/*
* Config Address for PCI Configuration Mechanism #1
*
* See PCI Local Bus Specification, Revision 3.0,
* Section 3.2.2.3.2, Figure 3-2, p. 50.
*/
#define PCI_CONF1_BUS_SHIFT 16 /* Bus number */
#define PCI_CONF1_DEV_SHIFT 11 /* Device number */
#define PCI_CONF1_FUNC_SHIFT 8 /* Function number */
#define PCI_CONF1_BUS_MASK 0xff
#define PCI_CONF1_DEV_MASK 0x1f
#define PCI_CONF1_FUNC_MASK 0x7
#define PCI_CONF1_REG_MASK 0xfc /* Limit aligned offset to a maximum of 256B */
#define PCI_CONF1_ENABLE BIT(31)
#define PCI_CONF1_BUS(x) (((x) & PCI_CONF1_BUS_MASK) << PCI_CONF1_BUS_SHIFT)
#define PCI_CONF1_DEV(x) (((x) & PCI_CONF1_DEV_MASK) << PCI_CONF1_DEV_SHIFT)
#define PCI_CONF1_FUNC(x) (((x) & PCI_CONF1_FUNC_MASK) << PCI_CONF1_FUNC_SHIFT)
#define PCI_CONF1_REG(x) ((x) & PCI_CONF1_REG_MASK)
#define PCI_CONF1_ADDRESS(bus, dev, func, reg) \
(PCI_CONF1_ENABLE | \
PCI_CONF1_BUS(bus) | \
PCI_CONF1_DEV(dev) | \
PCI_CONF1_FUNC(func) | \
PCI_CONF1_REG(reg))
/*
* Extension of PCI Config Address for accessing extended PCIe registers
*
* No standardized specification, but used on lot of non-ECAM-compliant ARM SoCs
* or on AMD Barcelona and new CPUs. Reserved bits [27:24] of PCI Config Address
* are used for specifying additional 4 high bits of PCI Express register.
*/
#define PCI_CONF1_EXT_REG_SHIFT 16
#define PCI_CONF1_EXT_REG_MASK 0xf00
#define PCI_CONF1_EXT_REG(x) (((x) & PCI_CONF1_EXT_REG_MASK) << PCI_CONF1_EXT_REG_SHIFT)
#define PCI_CONF1_EXT_ADDRESS(bus, dev, func, reg) \
(PCI_CONF1_ADDRESS(bus, dev, func, reg) | \
PCI_CONF1_EXT_REG(reg))
#endif /* DRIVERS_PCI_H */ #endif /* DRIVERS_PCI_H */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment