aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/pci/setup-bus.c
diff options
context:
space:
mode:
authorYinghai Lu <yinghai@kernel.org>2009-12-22 18:02:21 -0500
committerJesse Barnes <jbarnes@virtuousgeek.org>2010-02-22 19:16:59 -0500
commit7cc5997d1dada3bdeed95a59c2f4f6c66cbb0767 (patch)
treed93b2e63dbc6ee0a45bdbe222a0c9a74005249b1 /drivers/pci/setup-bus.c
parentb0fc889c4311835ae7d02f433154bc20cad9ee11 (diff)
PCI: separate pci_setup_bridge to small functions
This is a good cleanup in itself, and makes it easier to modify specific resource types in later code. Signed-off-by: Yinghai Lu <yinghai@kernel.org> Acked-by: Linus Torvalds <torvalds@linux-foundation.org> Signed-off-by: Jesse Barnes <jbarnes@virtuousgeek.org>
Diffstat (limited to 'drivers/pci/setup-bus.c')
-rw-r--r--drivers/pci/setup-bus.c66
1 files changed, 50 insertions, 16 deletions
diff --git a/drivers/pci/setup-bus.c b/drivers/pci/setup-bus.c
index c48cd377b3f5..1bd41ac2abd9 100644
--- a/drivers/pci/setup-bus.c
+++ b/drivers/pci/setup-bus.c
@@ -134,18 +134,12 @@ EXPORT_SYMBOL(pci_setup_cardbus);
134 config space writes, so it's quite possible that an I/O window of 134 config space writes, so it's quite possible that an I/O window of
135 the bridge will have some undesirable address (e.g. 0) after the 135 the bridge will have some undesirable address (e.g. 0) after the
136 first write. Ditto 64-bit prefetchable MMIO. */ 136 first write. Ditto 64-bit prefetchable MMIO. */
137static void pci_setup_bridge(struct pci_bus *bus) 137static void pci_setup_bridge_io(struct pci_bus *bus)
138{ 138{
139 struct pci_dev *bridge = bus->self; 139 struct pci_dev *bridge = bus->self;
140 struct resource *res; 140 struct resource *res;
141 struct pci_bus_region region; 141 struct pci_bus_region region;
142 u32 l, bu, lu, io_upper16; 142 u32 l, io_upper16;
143
144 if (pci_is_enabled(bridge))
145 return;
146
147 dev_info(&bridge->dev, "PCI bridge to [bus %02x-%02x]\n",
148 bus->secondary, bus->subordinate);
149 143
150 /* Set up the top and bottom of the PCI I/O segment for this bus. */ 144 /* Set up the top and bottom of the PCI I/O segment for this bus. */
151 res = bus->resource[0]; 145 res = bus->resource[0];
@@ -158,8 +152,7 @@ static void pci_setup_bridge(struct pci_bus *bus)
158 /* Set up upper 16 bits of I/O base/limit. */ 152 /* Set up upper 16 bits of I/O base/limit. */
159 io_upper16 = (region.end & 0xffff0000) | (region.start >> 16); 153 io_upper16 = (region.end & 0xffff0000) | (region.start >> 16);
160 dev_info(&bridge->dev, " bridge window %pR\n", res); 154 dev_info(&bridge->dev, " bridge window %pR\n", res);
161 } 155 } else {
162 else {
163 /* Clear upper 16 bits of I/O base/limit. */ 156 /* Clear upper 16 bits of I/O base/limit. */
164 io_upper16 = 0; 157 io_upper16 = 0;
165 l = 0x00f0; 158 l = 0x00f0;
@@ -171,21 +164,35 @@ static void pci_setup_bridge(struct pci_bus *bus)
171 pci_write_config_dword(bridge, PCI_IO_BASE, l); 164 pci_write_config_dword(bridge, PCI_IO_BASE, l);
172 /* Update upper 16 bits of I/O base/limit. */ 165 /* Update upper 16 bits of I/O base/limit. */
173 pci_write_config_dword(bridge, PCI_IO_BASE_UPPER16, io_upper16); 166 pci_write_config_dword(bridge, PCI_IO_BASE_UPPER16, io_upper16);
167}
168
169static void pci_setup_bridge_mmio(struct pci_bus *bus)
170{
171 struct pci_dev *bridge = bus->self;
172 struct resource *res;
173 struct pci_bus_region region;
174 u32 l;
174 175
175 /* Set up the top and bottom of the PCI Memory segment 176 /* Set up the top and bottom of the PCI Memory segment for this bus. */
176 for this bus. */
177 res = bus->resource[1]; 177 res = bus->resource[1];
178 pcibios_resource_to_bus(bridge, &region, res); 178 pcibios_resource_to_bus(bridge, &region, res);
179 if (res->flags & IORESOURCE_MEM) { 179 if (res->flags & IORESOURCE_MEM) {
180 l = (region.start >> 16) & 0xfff0; 180 l = (region.start >> 16) & 0xfff0;
181 l |= region.end & 0xfff00000; 181 l |= region.end & 0xfff00000;
182 dev_info(&bridge->dev, " bridge window %pR\n", res); 182 dev_info(&bridge->dev, " bridge window %pR\n", res);
183 } 183 } else {
184 else {
185 l = 0x0000fff0; 184 l = 0x0000fff0;
186 dev_info(&bridge->dev, " bridge window [mem disabled]\n"); 185 dev_info(&bridge->dev, " bridge window [mem disabled]\n");
187 } 186 }
188 pci_write_config_dword(bridge, PCI_MEMORY_BASE, l); 187 pci_write_config_dword(bridge, PCI_MEMORY_BASE, l);
188}
189
190static void pci_setup_bridge_mmio_pref(struct pci_bus *bus)
191{
192 struct pci_dev *bridge = bus->self;
193 struct resource *res;
194 struct pci_bus_region region;
195 u32 l, bu, lu;
189 196
190 /* Clear out the upper 32 bits of PREF limit. 197 /* Clear out the upper 32 bits of PREF limit.
191 If PCI_PREF_BASE_UPPER32 was non-zero, this temporarily 198 If PCI_PREF_BASE_UPPER32 was non-zero, this temporarily
@@ -204,8 +211,7 @@ static void pci_setup_bridge(struct pci_bus *bus)
204 lu = upper_32_bits(region.end); 211 lu = upper_32_bits(region.end);
205 } 212 }
206 dev_info(&bridge->dev, " bridge window %pR\n", res); 213 dev_info(&bridge->dev, " bridge window %pR\n", res);
207 } 214 } else {
208 else {
209 l = 0x0000fff0; 215 l = 0x0000fff0;
210 dev_info(&bridge->dev, " bridge window [mem pref disabled]\n"); 216 dev_info(&bridge->dev, " bridge window [mem pref disabled]\n");
211 } 217 }
@@ -214,10 +220,38 @@ static void pci_setup_bridge(struct pci_bus *bus)
214 /* Set the upper 32 bits of PREF base & limit. */ 220 /* Set the upper 32 bits of PREF base & limit. */
215 pci_write_config_dword(bridge, PCI_PREF_BASE_UPPER32, bu); 221 pci_write_config_dword(bridge, PCI_PREF_BASE_UPPER32, bu);
216 pci_write_config_dword(bridge, PCI_PREF_LIMIT_UPPER32, lu); 222 pci_write_config_dword(bridge, PCI_PREF_LIMIT_UPPER32, lu);
223}
224
225static void __pci_setup_bridge(struct pci_bus *bus, unsigned long type)
226{
227 struct pci_dev *bridge = bus->self;
228
229 if (pci_is_enabled(bridge))
230 return;
231
232 dev_info(&bridge->dev, "PCI bridge to [bus %02x-%02x]\n",
233 bus->secondary, bus->subordinate);
234
235 if (type & IORESOURCE_IO)
236 pci_setup_bridge_io(bus);
237
238 if (type & IORESOURCE_MEM)
239 pci_setup_bridge_mmio(bus);
240
241 if (type & IORESOURCE_PREFETCH)
242 pci_setup_bridge_mmio_pref(bus);
217 243
218 pci_write_config_word(bridge, PCI_BRIDGE_CONTROL, bus->bridge_ctl); 244 pci_write_config_word(bridge, PCI_BRIDGE_CONTROL, bus->bridge_ctl);
219} 245}
220 246
247static void pci_setup_bridge(struct pci_bus *bus)
248{
249 unsigned long type = IORESOURCE_IO | IORESOURCE_MEM |
250 IORESOURCE_PREFETCH;
251
252 __pci_setup_bridge(bus, type);
253}
254
221/* Check whether the bridge supports optional I/O and 255/* Check whether the bridge supports optional I/O and
222 prefetchable memory ranges. If not, the respective 256 prefetchable memory ranges. If not, the respective
223 base/limit registers must be read-only and read as 0. */ 257 base/limit registers must be read-only and read as 0. */