pci_pci.c (94573) | pci_pci.c (102441) |
---|---|
1/*- 2 * Copyright (c) 1994,1995 Stefan Esser, Wolfgang StanglMeier 3 * Copyright (c) 2000 Michael Smith <msmith@freebsd.org> 4 * Copyright (c) 2000 BSDi 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions --- 13 unchanged lines hidden (view full) --- 22 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 24 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 25 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 28 * SUCH DAMAGE. 29 * | 1/*- 2 * Copyright (c) 1994,1995 Stefan Esser, Wolfgang StanglMeier 3 * Copyright (c) 2000 Michael Smith <msmith@freebsd.org> 4 * Copyright (c) 2000 BSDi 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions --- 13 unchanged lines hidden (view full) --- 22 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 24 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 25 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 28 * SUCH DAMAGE. 29 * |
30 * $FreeBSD: head/sys/dev/pci/pci_pci.c 94573 2002-04-13 05:52:35Z imp $ | 30 * $FreeBSD: head/sys/dev/pci/pci_pci.c 102441 2002-08-26 15:57:08Z jhb $ |
31 */ 32 33/* 34 * PCI:PCI bridge support. 35 */ 36 37#include <sys/param.h> 38#include <sys/systm.h> 39#include <sys/kernel.h> 40#include <sys/bus.h> 41 42#include <machine/resource.h> 43 44#include <pci/pcivar.h> 45#include <pci/pcireg.h> | 31 */ 32 33/* 34 * PCI:PCI bridge support. 35 */ 36 37#include <sys/param.h> 38#include <sys/systm.h> 39#include <sys/kernel.h> 40#include <sys/bus.h> 41 42#include <machine/resource.h> 43 44#include <pci/pcivar.h> 45#include <pci/pcireg.h> |
46#include <pci/pcib_private.h> |
|
46 47#include "pcib_if.h" 48#include "opt_pci.h" 49 | 47 48#include "pcib_if.h" 49#include "opt_pci.h" 50 |
50/* 51 * Bridge-specific data. 52 */ 53struct pcib_softc 54{ 55 device_t dev; 56 u_int16_t command; /* command register */ 57 u_int8_t secbus; /* secondary bus number */ 58 u_int8_t subbus; /* subordinate bus number */ 59 pci_addr_t pmembase; /* base address of prefetchable memory */ 60 pci_addr_t pmemlimit; /* topmost address of prefetchable memory */ 61 pci_addr_t membase; /* base address of memory window */ 62 pci_addr_t memlimit; /* topmost address of memory window */ 63 u_int32_t iobase; /* base address of port window */ 64 u_int32_t iolimit; /* topmost address of port window */ 65 u_int16_t secstat; /* secondary bus status register */ 66 u_int16_t bridgectl; /* bridge control register */ 67 u_int8_t seclat; /* secondary bus latency timer */ 68}; 69 | |
70static int pcib_probe(device_t dev); 71static int pcib_attach(device_t dev); | 51static int pcib_probe(device_t dev); 52static int pcib_attach(device_t dev); |
72static int pcib_read_ivar(device_t dev, device_t child, int which, uintptr_t *result); 73static int pcib_write_ivar(device_t dev, device_t child, int which, uintptr_t value); 74static struct resource *pcib_alloc_resource(device_t dev, device_t child, int type, int *rid, 75 u_long start, u_long end, u_long count, u_int flags); 76static int pcib_maxslots(device_t dev); 77static u_int32_t pcib_read_config(device_t dev, int b, int s, int f, int reg, int width); 78static void pcib_write_config(device_t dev, int b, int s, int f, int reg, u_int32_t val, int width); | |
79static int pcib_route_interrupt(device_t pcib, device_t dev, int pin); 80 81static device_method_t pcib_methods[] = { 82 /* Device interface */ 83 DEVMETHOD(device_probe, pcib_probe), 84 DEVMETHOD(device_attach, pcib_attach), 85 DEVMETHOD(device_shutdown, bus_generic_shutdown), 86 DEVMETHOD(device_suspend, bus_generic_suspend), --- 20 unchanged lines hidden (view full) --- 107}; 108 109static driver_t pcib_driver = { 110 "pcib", 111 pcib_methods, 112 sizeof(struct pcib_softc), 113}; 114 | 53static int pcib_route_interrupt(device_t pcib, device_t dev, int pin); 54 55static device_method_t pcib_methods[] = { 56 /* Device interface */ 57 DEVMETHOD(device_probe, pcib_probe), 58 DEVMETHOD(device_attach, pcib_attach), 59 DEVMETHOD(device_shutdown, bus_generic_shutdown), 60 DEVMETHOD(device_suspend, bus_generic_suspend), --- 20 unchanged lines hidden (view full) --- 81}; 82 83static driver_t pcib_driver = { 84 "pcib", 85 pcib_methods, 86 sizeof(struct pcib_softc), 87}; 88 |
115static devclass_t pcib_devclass; | 89devclass_t pcib_devclass; |
116 117DRIVER_MODULE(pcib, pci, pcib_driver, pcib_devclass, 0, 0); 118 119/* 120 * Generic device interface 121 */ 122static int 123pcib_probe(device_t dev) 124{ 125 if ((pci_get_class(dev) == PCIC_BRIDGE) && 126 (pci_get_subclass(dev) == PCIS_BRIDGE_PCI)) { 127 device_set_desc(dev, "PCI-PCI bridge"); 128 return(-10000); 129 } 130 return(ENXIO); 131} 132 | 90 91DRIVER_MODULE(pcib, pci, pcib_driver, pcib_devclass, 0, 0); 92 93/* 94 * Generic device interface 95 */ 96static int 97pcib_probe(device_t dev) 98{ 99 if ((pci_get_class(dev) == PCIC_BRIDGE) && 100 (pci_get_subclass(dev) == PCIS_BRIDGE_PCI)) { 101 device_set_desc(dev, "PCI-PCI bridge"); 102 return(-10000); 103 } 104 return(ENXIO); 105} 106 |
133static int 134pcib_attach(device_t dev) | 107void 108pcib_attach_common(device_t dev) |
135{ 136 struct pcib_softc *sc; | 109{ 110 struct pcib_softc *sc; |
137 device_t child; | |
138 u_int8_t iolow; 139 140 sc = device_get_softc(dev); 141 sc->dev = dev; 142 143 /* 144 * Get current bridge configuration. 145 */ --- 68 unchanged lines hidden (view full) --- 214 */ 215 216 /* 217 * XXX If the subordinate bus number is less than the secondary bus number, 218 * we should pick a better value. One sensible alternative would be to 219 * pick 255; the only tradeoff here is that configuration transactions 220 * would be more widely routed than absolutely necessary. 221 */ | 111 u_int8_t iolow; 112 113 sc = device_get_softc(dev); 114 sc->dev = dev; 115 116 /* 117 * Get current bridge configuration. 118 */ --- 68 unchanged lines hidden (view full) --- 187 */ 188 189 /* 190 * XXX If the subordinate bus number is less than the secondary bus number, 191 * we should pick a better value. One sensible alternative would be to 192 * pick 255; the only tradeoff here is that configuration transactions 193 * would be more widely routed than absolutely necessary. 194 */ |
195} |
|
222 | 196 |
197static int 198pcib_attach(device_t dev) 199{ 200 struct pcib_softc *sc; 201 device_t child; 202 203 pcib_attach_common(dev); 204 sc = device_get_softc(dev); |
|
223 if (sc->secbus != 0) { 224 child = device_add_child(dev, "pci", -1); 225 if (child != NULL) 226 return(bus_generic_attach(dev)); 227 } 228 229 /* no secondary bus; we should have fixed this */ 230 return(0); 231} 232 | 205 if (sc->secbus != 0) { 206 child = device_add_child(dev, "pci", -1); 207 if (child != NULL) 208 return(bus_generic_attach(dev)); 209 } 210 211 /* no secondary bus; we should have fixed this */ 212 return(0); 213} 214 |
233static int | 215int |
234pcib_read_ivar(device_t dev, device_t child, int which, uintptr_t *result) 235{ 236 struct pcib_softc *sc = device_get_softc(dev); 237 238 switch (which) { 239 case PCIB_IVAR_BUS: 240 *result = sc->secbus; 241 return(0); 242 } 243 return(ENOENT); 244} 245 | 216pcib_read_ivar(device_t dev, device_t child, int which, uintptr_t *result) 217{ 218 struct pcib_softc *sc = device_get_softc(dev); 219 220 switch (which) { 221 case PCIB_IVAR_BUS: 222 *result = sc->secbus; 223 return(0); 224 } 225 return(ENOENT); 226} 227 |
246static int | 228int |
247pcib_write_ivar(device_t dev, device_t child, int which, uintptr_t value) 248{ 249 struct pcib_softc *sc = device_get_softc(dev); 250 251 switch (which) { 252 case PCIB_IVAR_BUS: 253 sc->secbus = value; 254 break; --- 24 unchanged lines hidden (view full) --- 279 return (0); 280 return (1); 281} 282 283/* 284 * We have to trap resource allocation requests and ensure that the bridge 285 * is set up to, or capable of handling them. 286 */ | 229pcib_write_ivar(device_t dev, device_t child, int which, uintptr_t value) 230{ 231 struct pcib_softc *sc = device_get_softc(dev); 232 233 switch (which) { 234 case PCIB_IVAR_BUS: 235 sc->secbus = value; 236 break; --- 24 unchanged lines hidden (view full) --- 261 return (0); 262 return (1); 263} 264 265/* 266 * We have to trap resource allocation requests and ensure that the bridge 267 * is set up to, or capable of handling them. 268 */ |
287static struct resource * | 269struct resource * |
288pcib_alloc_resource(device_t dev, device_t child, int type, int *rid, 289 u_long start, u_long end, u_long count, u_int flags) 290{ 291 struct pcib_softc *sc = device_get_softc(dev); 292 293 /* 294 * If this is a "default" allocation against this rid, we can't work 295 * out where it's coming from (we should actually never see these) so we --- 92 unchanged lines hidden (view full) --- 388 * Bridge is OK decoding this resource, so pass it up. 389 */ 390 return(bus_generic_alloc_resource(dev, child, type, rid, start, end, count, flags)); 391} 392 393/* 394 * PCIB interface. 395 */ | 270pcib_alloc_resource(device_t dev, device_t child, int type, int *rid, 271 u_long start, u_long end, u_long count, u_int flags) 272{ 273 struct pcib_softc *sc = device_get_softc(dev); 274 275 /* 276 * If this is a "default" allocation against this rid, we can't work 277 * out where it's coming from (we should actually never see these) so we --- 92 unchanged lines hidden (view full) --- 370 * Bridge is OK decoding this resource, so pass it up. 371 */ 372 return(bus_generic_alloc_resource(dev, child, type, rid, start, end, count, flags)); 373} 374 375/* 376 * PCIB interface. 377 */ |
396static int | 378int |
397pcib_maxslots(device_t dev) 398{ 399 return(PCI_SLOTMAX); 400} 401 402/* 403 * Since we are a child of a PCI bus, its parent must support the pcib interface. 404 */ | 379pcib_maxslots(device_t dev) 380{ 381 return(PCI_SLOTMAX); 382} 383 384/* 385 * Since we are a child of a PCI bus, its parent must support the pcib interface. 386 */ |
405static u_int32_t | 387u_int32_t |
406pcib_read_config(device_t dev, int b, int s, int f, int reg, int width) 407{ 408 return(PCIB_READ_CONFIG(device_get_parent(device_get_parent(dev)), b, s, f, reg, width)); 409} 410 | 388pcib_read_config(device_t dev, int b, int s, int f, int reg, int width) 389{ 390 return(PCIB_READ_CONFIG(device_get_parent(device_get_parent(dev)), b, s, f, reg, width)); 391} 392 |
411static void | 393void |
412pcib_write_config(device_t dev, int b, int s, int f, int reg, u_int32_t val, int width) 413{ 414 PCIB_WRITE_CONFIG(device_get_parent(device_get_parent(dev)), b, s, f, reg, val, width); 415} 416 417/* 418 * Route an interrupt across a PCI bridge. 419 */ --- 32 unchanged lines hidden --- | 394pcib_write_config(device_t dev, int b, int s, int f, int reg, u_int32_t val, int width) 395{ 396 PCIB_WRITE_CONFIG(device_get_parent(device_get_parent(dev)), b, s, f, reg, val, width); 397} 398 399/* 400 * Route an interrupt across a PCI bridge. 401 */ --- 32 unchanged lines hidden --- |