aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/pci/dwc/pcie-designware.h
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2017-05-08 22:03:25 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2017-05-08 22:03:25 -0400
commit857f8640147c9fb43f20e43cbca6452710e1ca5d (patch)
tree76a92068d703b8001ca790ffa096d435fa24ae81 /drivers/pci/dwc/pcie-designware.h
parent8f3207c7eab9d885cc64c778416537034a7d9c5b (diff)
parent3146c8f4de9b0858794a902f273aec13f168596e (diff)
Merge tag 'pci-v4.12-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/helgaas/pci
Pull PCI updates from Bjorn Helgaas: - add framework for supporting PCIe devices in Endpoint mode (Kishon Vijay Abraham I) - use non-postable PCI config space mappings when possible (Lorenzo Pieralisi) - clean up and unify mmap of PCI BARs (David Woodhouse) - export and unify Function Level Reset support (Christoph Hellwig) - avoid FLR for Intel 82579 NICs (Sasha Neftin) - add pci_request_irq() and pci_free_irq() helpers (Christoph Hellwig) - short-circuit config access failures for disconnected devices (Keith Busch) - remove D3 sleep delay when possible (Adrian Hunter) - freeze PME scan before suspending devices (Lukas Wunner) - stop disabling MSI/MSI-X in pci_device_shutdown() (Prarit Bhargava) - disable boot interrupt quirk for ASUS M2N-LR (Stefan Assmann) - add arch-specific alignment control to improve device passthrough by avoiding multiple BARs in a page (Yongji Xie) - add sysfs sriov_drivers_autoprobe to control VF driver binding (Bodong Wang) - allow slots below PCI-to-PCIe "reverse bridges" (Bjorn Helgaas) - fix crashes when unbinding host controllers that don't support removal (Brian Norris) - add driver for MicroSemi Switchtec management interface (Logan Gunthorpe) - add driver for Faraday Technology FTPCI100 host bridge (Linus Walleij) - add i.MX7D support (Andrey Smirnov) - use generic MSI support for Aardvark (Thomas Petazzoni) - make Rockchip driver modular (Brian Norris) - advertise 128-byte Read Completion Boundary support for Rockchip (Shawn Lin) - advertise PCI_EXP_LNKSTA_SLC for Rockchip root port (Shawn Lin) - convert atomic_t to refcount_t in HV driver (Elena Reshetova) - add CPU IRQ affinity in HV driver (K. Y. Srinivasan) - fix PCI bus removal in HV driver (Long Li) - add support for ThunderX2 DMA alias topology (Jayachandran C) - add ThunderX pass2.x 2nd node MCFG quirk (Tomasz Nowicki) - add ITE 8893 bridge DMA alias quirk (Jarod Wilson) - restrict Cavium ACS quirk only to CN81xx/CN83xx/CN88xx devices (Manish Jaggi) * tag 'pci-v4.12-changes' of git://git.kernel.org/pub/scm/linux/kernel/git/helgaas/pci: (146 commits) PCI: Don't allow unbinding host controllers that aren't prepared ARM: DRA7: clockdomain: Change the CLKTRCTRL of CM_PCIE_CLKSTCTRL to SW_WKUP MAINTAINERS: Add PCI Endpoint maintainer Documentation: PCI: Add userguide for PCI endpoint test function tools: PCI: Add sample test script to invoke pcitest tools: PCI: Add a userspace tool to test PCI endpoint Documentation: misc-devices: Add Documentation for pci-endpoint-test driver misc: Add host side PCI driver for PCI test function device PCI: Add device IDs for DRA74x and DRA72x dt-bindings: PCI: dra7xx: Add DT bindings to enable unaligned access PCI: dwc: dra7xx: Workaround for errata id i870 dt-bindings: PCI: dra7xx: Add DT bindings for PCI dra7xx EP mode PCI: dwc: dra7xx: Add EP mode support PCI: dwc: dra7xx: Facilitate wrapper and MSI interrupts to be enabled independently dt-bindings: PCI: Add DT bindings for PCI designware EP mode PCI: dwc: designware: Add EP mode support Documentation: PCI: Add binding documentation for pci-test endpoint function ixgbe: Use pcie_flr() instead of duplicating it IB/hfi1: Use pcie_flr() instead of duplicating it PCI: imx6: Fix spelling mistake: "contol" -> "control" ...
Diffstat (limited to 'drivers/pci/dwc/pcie-designware.h')
-rw-r--r--drivers/pci/dwc/pcie-designware.h135
1 files changed, 131 insertions, 4 deletions
diff --git a/drivers/pci/dwc/pcie-designware.h b/drivers/pci/dwc/pcie-designware.h
index cd3b8713fe50..c6a840575796 100644
--- a/drivers/pci/dwc/pcie-designware.h
+++ b/drivers/pci/dwc/pcie-designware.h
@@ -18,6 +18,9 @@
18#include <linux/msi.h> 18#include <linux/msi.h>
19#include <linux/pci.h> 19#include <linux/pci.h>
20 20
21#include <linux/pci-epc.h>
22#include <linux/pci-epf.h>
23
21/* Parameters for the waiting for link up routine */ 24/* Parameters for the waiting for link up routine */
22#define LINK_WAIT_MAX_RETRIES 10 25#define LINK_WAIT_MAX_RETRIES 10
23#define LINK_WAIT_USLEEP_MIN 90000 26#define LINK_WAIT_USLEEP_MIN 90000
@@ -89,6 +92,16 @@
89#define PCIE_GET_ATU_OUTB_UNR_REG_OFFSET(region) \ 92#define PCIE_GET_ATU_OUTB_UNR_REG_OFFSET(region) \
90 ((0x3 << 20) | ((region) << 9)) 93 ((0x3 << 20) | ((region) << 9))
91 94
95#define PCIE_GET_ATU_INB_UNR_REG_OFFSET(region) \
96 ((0x3 << 20) | ((region) << 9) | (0x1 << 8))
97
98#define MSI_MESSAGE_CONTROL 0x52
99#define MSI_CAP_MMC_SHIFT 1
100#define MSI_CAP_MME_SHIFT 4
101#define MSI_CAP_MME_MASK (7 << MSI_CAP_MME_SHIFT)
102#define MSI_MESSAGE_ADDR_L32 0x54
103#define MSI_MESSAGE_ADDR_U32 0x58
104
92/* 105/*
93 * Maximum number of MSI IRQs can be 256 per controller. But keep 106 * Maximum number of MSI IRQs can be 256 per controller. But keep
94 * it 32 as of now. Probably we will never need more than 32. If needed, 107 * it 32 as of now. Probably we will never need more than 32. If needed,
@@ -99,6 +112,20 @@
99 112
100struct pcie_port; 113struct pcie_port;
101struct dw_pcie; 114struct dw_pcie;
115struct dw_pcie_ep;
116
117enum dw_pcie_region_type {
118 DW_PCIE_REGION_UNKNOWN,
119 DW_PCIE_REGION_INBOUND,
120 DW_PCIE_REGION_OUTBOUND,
121};
122
123enum dw_pcie_device_mode {
124 DW_PCIE_UNKNOWN_TYPE,
125 DW_PCIE_EP_TYPE,
126 DW_PCIE_LEG_EP_TYPE,
127 DW_PCIE_RC_TYPE,
128};
102 129
103struct dw_pcie_host_ops { 130struct dw_pcie_host_ops {
104 int (*rd_own_conf)(struct pcie_port *pp, int where, int size, u32 *val); 131 int (*rd_own_conf)(struct pcie_port *pp, int where, int size, u32 *val);
@@ -142,35 +169,116 @@ struct pcie_port {
142 DECLARE_BITMAP(msi_irq_in_use, MAX_MSI_IRQS); 169 DECLARE_BITMAP(msi_irq_in_use, MAX_MSI_IRQS);
143}; 170};
144 171
172enum dw_pcie_as_type {
173 DW_PCIE_AS_UNKNOWN,
174 DW_PCIE_AS_MEM,
175 DW_PCIE_AS_IO,
176};
177
178struct dw_pcie_ep_ops {
179 void (*ep_init)(struct dw_pcie_ep *ep);
180 int (*raise_irq)(struct dw_pcie_ep *ep, enum pci_epc_irq_type type,
181 u8 interrupt_num);
182};
183
184struct dw_pcie_ep {
185 struct pci_epc *epc;
186 struct dw_pcie_ep_ops *ops;
187 phys_addr_t phys_base;
188 size_t addr_size;
189 u8 bar_to_atu[6];
190 phys_addr_t *outbound_addr;
191 unsigned long ib_window_map;
192 unsigned long ob_window_map;
193 u32 num_ib_windows;
194 u32 num_ob_windows;
195};
196
145struct dw_pcie_ops { 197struct dw_pcie_ops {
146 u32 (*readl_dbi)(struct dw_pcie *pcie, u32 reg); 198 u64 (*cpu_addr_fixup)(u64 cpu_addr);
147 void (*writel_dbi)(struct dw_pcie *pcie, u32 reg, u32 val); 199 u32 (*read_dbi)(struct dw_pcie *pcie, void __iomem *base, u32 reg,
200 size_t size);
201 void (*write_dbi)(struct dw_pcie *pcie, void __iomem *base, u32 reg,
202 size_t size, u32 val);
148 int (*link_up)(struct dw_pcie *pcie); 203 int (*link_up)(struct dw_pcie *pcie);
204 int (*start_link)(struct dw_pcie *pcie);
205 void (*stop_link)(struct dw_pcie *pcie);
149}; 206};
150 207
151struct dw_pcie { 208struct dw_pcie {
152 struct device *dev; 209 struct device *dev;
153 void __iomem *dbi_base; 210 void __iomem *dbi_base;
211 void __iomem *dbi_base2;
154 u32 num_viewport; 212 u32 num_viewport;
155 u8 iatu_unroll_enabled; 213 u8 iatu_unroll_enabled;
156 struct pcie_port pp; 214 struct pcie_port pp;
215 struct dw_pcie_ep ep;
157 const struct dw_pcie_ops *ops; 216 const struct dw_pcie_ops *ops;
158}; 217};
159 218
160#define to_dw_pcie_from_pp(port) container_of((port), struct dw_pcie, pp) 219#define to_dw_pcie_from_pp(port) container_of((port), struct dw_pcie, pp)
161 220
221#define to_dw_pcie_from_ep(endpoint) \
222 container_of((endpoint), struct dw_pcie, ep)
223
162int dw_pcie_read(void __iomem *addr, int size, u32 *val); 224int dw_pcie_read(void __iomem *addr, int size, u32 *val);
163int dw_pcie_write(void __iomem *addr, int size, u32 val); 225int dw_pcie_write(void __iomem *addr, int size, u32 val);
164 226
165u32 dw_pcie_readl_dbi(struct dw_pcie *pci, u32 reg); 227u32 __dw_pcie_read_dbi(struct dw_pcie *pci, void __iomem *base, u32 reg,
166void dw_pcie_writel_dbi(struct dw_pcie *pci, u32 reg, u32 val); 228 size_t size);
229void __dw_pcie_write_dbi(struct dw_pcie *pci, void __iomem *base, u32 reg,
230 size_t size, u32 val);
167int dw_pcie_link_up(struct dw_pcie *pci); 231int dw_pcie_link_up(struct dw_pcie *pci);
168int dw_pcie_wait_for_link(struct dw_pcie *pci); 232int dw_pcie_wait_for_link(struct dw_pcie *pci);
169void dw_pcie_prog_outbound_atu(struct dw_pcie *pci, int index, 233void dw_pcie_prog_outbound_atu(struct dw_pcie *pci, int index,
170 int type, u64 cpu_addr, u64 pci_addr, 234 int type, u64 cpu_addr, u64 pci_addr,
171 u32 size); 235 u32 size);
236int dw_pcie_prog_inbound_atu(struct dw_pcie *pci, int index, int bar,
237 u64 cpu_addr, enum dw_pcie_as_type as_type);
238void dw_pcie_disable_atu(struct dw_pcie *pci, int index,
239 enum dw_pcie_region_type type);
172void dw_pcie_setup(struct dw_pcie *pci); 240void dw_pcie_setup(struct dw_pcie *pci);
173 241
242static inline void dw_pcie_writel_dbi(struct dw_pcie *pci, u32 reg, u32 val)
243{
244 __dw_pcie_write_dbi(pci, pci->dbi_base, reg, 0x4, val);
245}
246
247static inline u32 dw_pcie_readl_dbi(struct dw_pcie *pci, u32 reg)
248{
249 return __dw_pcie_read_dbi(pci, pci->dbi_base, reg, 0x4);
250}
251
252static inline void dw_pcie_writew_dbi(struct dw_pcie *pci, u32 reg, u16 val)
253{
254 __dw_pcie_write_dbi(pci, pci->dbi_base, reg, 0x2, val);
255}
256
257static inline u16 dw_pcie_readw_dbi(struct dw_pcie *pci, u32 reg)
258{
259 return __dw_pcie_read_dbi(pci, pci->dbi_base, reg, 0x2);
260}
261
262static inline void dw_pcie_writeb_dbi(struct dw_pcie *pci, u32 reg, u8 val)
263{
264 __dw_pcie_write_dbi(pci, pci->dbi_base, reg, 0x1, val);
265}
266
267static inline u8 dw_pcie_readb_dbi(struct dw_pcie *pci, u32 reg)
268{
269 return __dw_pcie_read_dbi(pci, pci->dbi_base, reg, 0x1);
270}
271
272static inline void dw_pcie_writel_dbi2(struct dw_pcie *pci, u32 reg, u32 val)
273{
274 __dw_pcie_write_dbi(pci, pci->dbi_base2, reg, 0x4, val);
275}
276
277static inline u32 dw_pcie_readl_dbi2(struct dw_pcie *pci, u32 reg)
278{
279 return __dw_pcie_read_dbi(pci, pci->dbi_base2, reg, 0x4);
280}
281
174#ifdef CONFIG_PCIE_DW_HOST 282#ifdef CONFIG_PCIE_DW_HOST
175irqreturn_t dw_handle_msi_irq(struct pcie_port *pp); 283irqreturn_t dw_handle_msi_irq(struct pcie_port *pp);
176void dw_pcie_msi_init(struct pcie_port *pp); 284void dw_pcie_msi_init(struct pcie_port *pp);
@@ -195,4 +303,23 @@ static inline int dw_pcie_host_init(struct pcie_port *pp)
195 return 0; 303 return 0;
196} 304}
197#endif 305#endif
306
307#ifdef CONFIG_PCIE_DW_EP
308void dw_pcie_ep_linkup(struct dw_pcie_ep *ep);
309int dw_pcie_ep_init(struct dw_pcie_ep *ep);
310void dw_pcie_ep_exit(struct dw_pcie_ep *ep);
311#else
312static inline void dw_pcie_ep_linkup(struct dw_pcie_ep *ep)
313{
314}
315
316static inline int dw_pcie_ep_init(struct dw_pcie_ep *ep)
317{
318 return 0;
319}
320
321static inline void dw_pcie_ep_exit(struct dw_pcie_ep *ep)
322{
323}
324#endif
198#endif /* _PCIE_DESIGNWARE_H */ 325#endif /* _PCIE_DESIGNWARE_H */