xref: /OK3568_Linux_fs/kernel/drivers/pci/pci-bridge-emul.h (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0 */
2*4882a593Smuzhiyun #ifndef __PCI_BRIDGE_EMUL_H__
3*4882a593Smuzhiyun #define __PCI_BRIDGE_EMUL_H__
4*4882a593Smuzhiyun 
5*4882a593Smuzhiyun #include <linux/kernel.h>
6*4882a593Smuzhiyun 
7*4882a593Smuzhiyun /* PCI configuration space of a PCI-to-PCI bridge. */
8*4882a593Smuzhiyun struct pci_bridge_emul_conf {
9*4882a593Smuzhiyun 	__le16 vendor;
10*4882a593Smuzhiyun 	__le16 device;
11*4882a593Smuzhiyun 	__le16 command;
12*4882a593Smuzhiyun 	__le16 status;
13*4882a593Smuzhiyun 	__le32 class_revision;
14*4882a593Smuzhiyun 	u8 cache_line_size;
15*4882a593Smuzhiyun 	u8 latency_timer;
16*4882a593Smuzhiyun 	u8 header_type;
17*4882a593Smuzhiyun 	u8 bist;
18*4882a593Smuzhiyun 	__le32 bar[2];
19*4882a593Smuzhiyun 	u8 primary_bus;
20*4882a593Smuzhiyun 	u8 secondary_bus;
21*4882a593Smuzhiyun 	u8 subordinate_bus;
22*4882a593Smuzhiyun 	u8 secondary_latency_timer;
23*4882a593Smuzhiyun 	u8 iobase;
24*4882a593Smuzhiyun 	u8 iolimit;
25*4882a593Smuzhiyun 	__le16 secondary_status;
26*4882a593Smuzhiyun 	__le16 membase;
27*4882a593Smuzhiyun 	__le16 memlimit;
28*4882a593Smuzhiyun 	__le16 pref_mem_base;
29*4882a593Smuzhiyun 	__le16 pref_mem_limit;
30*4882a593Smuzhiyun 	__le32 prefbaseupper;
31*4882a593Smuzhiyun 	__le32 preflimitupper;
32*4882a593Smuzhiyun 	__le16 iobaseupper;
33*4882a593Smuzhiyun 	__le16 iolimitupper;
34*4882a593Smuzhiyun 	u8 capabilities_pointer;
35*4882a593Smuzhiyun 	u8 reserve[3];
36*4882a593Smuzhiyun 	__le32 romaddr;
37*4882a593Smuzhiyun 	u8 intline;
38*4882a593Smuzhiyun 	u8 intpin;
39*4882a593Smuzhiyun 	__le16 bridgectrl;
40*4882a593Smuzhiyun };
41*4882a593Smuzhiyun 
42*4882a593Smuzhiyun /* PCI configuration space of the PCIe capabilities */
43*4882a593Smuzhiyun struct pci_bridge_emul_pcie_conf {
44*4882a593Smuzhiyun 	u8 cap_id;
45*4882a593Smuzhiyun 	u8 next;
46*4882a593Smuzhiyun 	__le16 cap;
47*4882a593Smuzhiyun 	__le32 devcap;
48*4882a593Smuzhiyun 	__le16 devctl;
49*4882a593Smuzhiyun 	__le16 devsta;
50*4882a593Smuzhiyun 	__le32 lnkcap;
51*4882a593Smuzhiyun 	__le16 lnkctl;
52*4882a593Smuzhiyun 	__le16 lnksta;
53*4882a593Smuzhiyun 	__le32 slotcap;
54*4882a593Smuzhiyun 	__le16 slotctl;
55*4882a593Smuzhiyun 	__le16 slotsta;
56*4882a593Smuzhiyun 	__le16 rootctl;
57*4882a593Smuzhiyun 	__le16 rootcap;
58*4882a593Smuzhiyun 	__le32 rootsta;
59*4882a593Smuzhiyun 	__le32 devcap2;
60*4882a593Smuzhiyun 	__le16 devctl2;
61*4882a593Smuzhiyun 	__le16 devsta2;
62*4882a593Smuzhiyun 	__le32 lnkcap2;
63*4882a593Smuzhiyun 	__le16 lnkctl2;
64*4882a593Smuzhiyun 	__le16 lnksta2;
65*4882a593Smuzhiyun 	__le32 slotcap2;
66*4882a593Smuzhiyun 	__le16 slotctl2;
67*4882a593Smuzhiyun 	__le16 slotsta2;
68*4882a593Smuzhiyun };
69*4882a593Smuzhiyun 
70*4882a593Smuzhiyun struct pci_bridge_emul;
71*4882a593Smuzhiyun 
72*4882a593Smuzhiyun typedef enum { PCI_BRIDGE_EMUL_HANDLED,
73*4882a593Smuzhiyun 	       PCI_BRIDGE_EMUL_NOT_HANDLED } pci_bridge_emul_read_status_t;
74*4882a593Smuzhiyun 
75*4882a593Smuzhiyun struct pci_bridge_emul_ops {
76*4882a593Smuzhiyun 	/*
77*4882a593Smuzhiyun 	 * Called when reading from the regular PCI bridge
78*4882a593Smuzhiyun 	 * configuration space. Return PCI_BRIDGE_EMUL_HANDLED when the
79*4882a593Smuzhiyun 	 * operation has handled the read operation and filled in the
80*4882a593Smuzhiyun 	 * *value, or PCI_BRIDGE_EMUL_NOT_HANDLED when the read should
81*4882a593Smuzhiyun 	 * be emulated by the common code by reading from the
82*4882a593Smuzhiyun 	 * in-memory copy of the configuration space.
83*4882a593Smuzhiyun 	 */
84*4882a593Smuzhiyun 	pci_bridge_emul_read_status_t (*read_base)(struct pci_bridge_emul *bridge,
85*4882a593Smuzhiyun 						   int reg, u32 *value);
86*4882a593Smuzhiyun 
87*4882a593Smuzhiyun 	/*
88*4882a593Smuzhiyun 	 * Same as ->read_base(), except it is for reading from the
89*4882a593Smuzhiyun 	 * PCIe capability configuration space.
90*4882a593Smuzhiyun 	 */
91*4882a593Smuzhiyun 	pci_bridge_emul_read_status_t (*read_pcie)(struct pci_bridge_emul *bridge,
92*4882a593Smuzhiyun 						   int reg, u32 *value);
93*4882a593Smuzhiyun 	/*
94*4882a593Smuzhiyun 	 * Called when writing to the regular PCI bridge configuration
95*4882a593Smuzhiyun 	 * space. old is the current value, new is the new value being
96*4882a593Smuzhiyun 	 * written, and mask indicates which parts of the value are
97*4882a593Smuzhiyun 	 * being changed.
98*4882a593Smuzhiyun 	 */
99*4882a593Smuzhiyun 	void (*write_base)(struct pci_bridge_emul *bridge, int reg,
100*4882a593Smuzhiyun 			   u32 old, u32 new, u32 mask);
101*4882a593Smuzhiyun 
102*4882a593Smuzhiyun 	/*
103*4882a593Smuzhiyun 	 * Same as ->write_base(), except it is for writing from the
104*4882a593Smuzhiyun 	 * PCIe capability configuration space.
105*4882a593Smuzhiyun 	 */
106*4882a593Smuzhiyun 	void (*write_pcie)(struct pci_bridge_emul *bridge, int reg,
107*4882a593Smuzhiyun 			   u32 old, u32 new, u32 mask);
108*4882a593Smuzhiyun };
109*4882a593Smuzhiyun 
110*4882a593Smuzhiyun struct pci_bridge_reg_behavior;
111*4882a593Smuzhiyun 
112*4882a593Smuzhiyun struct pci_bridge_emul {
113*4882a593Smuzhiyun 	struct pci_bridge_emul_conf conf;
114*4882a593Smuzhiyun 	struct pci_bridge_emul_pcie_conf pcie_conf;
115*4882a593Smuzhiyun 	struct pci_bridge_emul_ops *ops;
116*4882a593Smuzhiyun 	struct pci_bridge_reg_behavior *pci_regs_behavior;
117*4882a593Smuzhiyun 	struct pci_bridge_reg_behavior *pcie_cap_regs_behavior;
118*4882a593Smuzhiyun 	void *data;
119*4882a593Smuzhiyun 	bool has_pcie;
120*4882a593Smuzhiyun };
121*4882a593Smuzhiyun 
122*4882a593Smuzhiyun enum {
123*4882a593Smuzhiyun 	PCI_BRIDGE_EMUL_NO_PREFETCHABLE_BAR = BIT(0),
124*4882a593Smuzhiyun };
125*4882a593Smuzhiyun 
126*4882a593Smuzhiyun int pci_bridge_emul_init(struct pci_bridge_emul *bridge,
127*4882a593Smuzhiyun 			 unsigned int flags);
128*4882a593Smuzhiyun void pci_bridge_emul_cleanup(struct pci_bridge_emul *bridge);
129*4882a593Smuzhiyun 
130*4882a593Smuzhiyun int pci_bridge_emul_conf_read(struct pci_bridge_emul *bridge, int where,
131*4882a593Smuzhiyun 			      int size, u32 *value);
132*4882a593Smuzhiyun int pci_bridge_emul_conf_write(struct pci_bridge_emul *bridge, int where,
133*4882a593Smuzhiyun 			       int size, u32 value);
134*4882a593Smuzhiyun 
135*4882a593Smuzhiyun #endif /* __PCI_BRIDGE_EMUL_H__ */
136