1 /* $NetBSD: pci_machdep.c,v 1.7 2001/10/29 23:37:37 thorpej Exp $ */ 2 3 /* 4 * Copyright (c) 1996 Christopher G. Demetriou. All rights reserved. 5 * Copyright (c) 1994 Charles M. Hannum. 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 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. All advertising materials mentioning features or use of this software 16 * must display the following acknowledgement: 17 * This product includes software developed by Charles M. Hannum. 18 * 4. The name of the author may not be used to endorse or promote products 19 * derived from this software without specific prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 22 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 23 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 24 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 25 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 26 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 27 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 28 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 29 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 30 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 31 */ 32 33 /* 34 * Machine-specific functions for PCI autoconfiguration. 35 * 36 * On PCs, there are two methods of generating PCI configuration cycles. 37 * We try to detect the appropriate mechanism for this machine and set 38 * up a few function pointers to access the correct method directly. 39 * 40 * The configuration method can be hard-coded in the config file by 41 * using `options PCI_CONF_MODE=N', where `N' is the configuration mode 42 * as defined section 3.6.4.1, `Generating Configuration Cycles'. 43 */ 44 #include "opt_openpic.h" 45 46 #include <sys/types.h> 47 #include <sys/param.h> 48 #include <sys/device.h> 49 #include <sys/errno.h> 50 #include <sys/extent.h> 51 #include <sys/malloc.h> 52 #include <sys/queue.h> 53 #include <sys/systm.h> 54 #include <sys/time.h> 55 56 #include <uvm/uvm.h> 57 58 #define _POWERPC_BUS_DMA_PRIVATE 59 #include <machine/bus.h> 60 #include <machine/pio.h> 61 #include <machine/intr.h> 62 63 #include <dev/isa/isavar.h> 64 #include <dev/pci/pcivar.h> 65 #include <dev/pci/pcireg.h> 66 #include <dev/pci/pciconf.h> 67 68 #include <sandpoint/isa/icu.h> 69 70 struct powerpc_bus_dma_tag pci_bus_dma_tag = { 71 0, /* _bounce_thresh */ 72 _bus_dmamap_create, 73 _bus_dmamap_destroy, 74 _bus_dmamap_load, 75 _bus_dmamap_load_mbuf, 76 _bus_dmamap_load_uio, 77 _bus_dmamap_load_raw, 78 _bus_dmamap_unload, 79 NULL, /* _dmamap_sync */ 80 _bus_dmamem_alloc, 81 _bus_dmamem_free, 82 _bus_dmamem_map, 83 _bus_dmamem_unmap, 84 _bus_dmamem_mmap, 85 }; 86 87 #define PCI_CONFIG_ENABLE 0x80000000UL 88 89 void 90 pci_attach_hook(parent, self, pba) 91 struct device *parent, *self; 92 struct pcibus_attach_args *pba; 93 { 94 } 95 96 int 97 pci_bus_maxdevs(pc, busno) 98 pci_chipset_tag_t pc; 99 int busno; 100 { 101 102 /* 103 * Bus number is irrelevant. Configuration Mechanism 1 is in 104 * use, can have devices 0-32 (i.e. the `normal' range). 105 */ 106 return (32); 107 } 108 109 pcitag_t 110 pci_make_tag(pc, bus, device, function) 111 pci_chipset_tag_t pc; 112 int bus, device, function; 113 { 114 pcitag_t tag; 115 116 if (bus >= 256 || device >= 32 || function >= 8) 117 panic("pci_make_tag: bad request"); 118 119 tag = PCI_CONFIG_ENABLE | 120 (bus << 16) | (device << 11) | (function << 8); 121 return tag; 122 } 123 124 void 125 pci_decompose_tag(pc, tag, bp, dp, fp) 126 pci_chipset_tag_t pc; 127 pcitag_t tag; 128 int *bp, *dp, *fp; 129 { 130 131 if (bp != NULL) 132 *bp = (tag >> 16) & 0xff; 133 if (dp != NULL) 134 *dp = (tag >> 11) & 0x1f; 135 if (fp != NULL) 136 *fp = (tag >> 8) & 0x7; 137 return; 138 } 139 140 /* 141 * The Kahlua documentation says that "reg" should be left-shifted by two 142 * and be in bits 2-7. Apparently not. It doesn't work that way, and the 143 * DINK32 ROM doesn't do it that way (I peeked at 0xfec00000 after running 144 * the DINK32 "pcf" command). 145 */ 146 #define SP_PCI(tag, reg) ((tag) | (reg)) 147 148 pcireg_t 149 pci_conf_read(pc, tag, reg) 150 pci_chipset_tag_t pc; 151 pcitag_t tag; 152 int reg; 153 { 154 pcireg_t data; 155 156 out32rb(SANDPOINT_PCI_CONFIG_ADDR, SP_PCI(tag,reg)); 157 data = in32rb(SANDPOINT_PCI_CONFIG_DATA); 158 out32rb(SANDPOINT_PCI_CONFIG_ADDR, 0); 159 return data; 160 } 161 162 void 163 pci_conf_write(pc, tag, reg, data) 164 pci_chipset_tag_t pc; 165 pcitag_t tag; 166 int reg; 167 pcireg_t data; 168 { 169 out32rb(SANDPOINT_PCI_CONFIG_ADDR, SP_PCI(tag, reg)); 170 out32rb(SANDPOINT_PCI_CONFIG_DATA, data); 171 out32rb(SANDPOINT_PCI_CONFIG_ADDR, 0); 172 } 173 174 int 175 pci_intr_map(pa, ihp) 176 struct pci_attach_args *pa; 177 pci_intr_handle_t *ihp; 178 { 179 int pin = pa->pa_intrpin; 180 int line = pa->pa_intrline; 181 182 if (pin == 0) { 183 /* No IRQ used. */ 184 goto bad; 185 } 186 187 if (pin > 4) { 188 printf("pci_intr_map: bad interrupt pin %d\n", pin); 189 goto bad; 190 } 191 192 /* 193 * Section 6.2.4, `Miscellaneous Functions', says that 255 means 194 * `unknown' or `no connection' on a PC. We assume that a device with 195 * `no connection' either doesn't have an interrupt (in which case the 196 * pin number should be 0, and would have been noticed above), or 197 * wasn't configured by the BIOS (in which case we punt, since there's 198 * no real way we can know how the interrupt lines are mapped in the 199 * hardware). 200 * 201 * XXX 202 * Since IRQ 0 is only used by the clock, and we can't actually be sure 203 * that the BIOS did its job, we also recognize that as meaning that 204 * the BIOS has not configured the device. 205 */ 206 if (line == 255) { 207 printf("pci_intr_map: no mapping for pin %c\n", '@' + pin); 208 goto bad; 209 } else { 210 /* 211 * Sandpoint has 4 PCI slots. 212 * Sandpoint rev. X2 has them in a weird order. Counting 213 * from center out toward the edge, we have: 214 * Slot 1 (dev 14?) (labelled 1) 215 * Slot 0 (dev 13?) (labelled 2) 216 * Slot 3 (dev 16) (labelled 3) 217 * Slot 2 (dev 15) (labelled 4) 218 * To keep things confusing, we will consistently use a zero- 219 * based numbering scheme where Motorola's is usually 1-based. 220 */ 221 if (line < 13 || line > 16) { 222 printf("pci_intr_map: bad interrupt line %d\n", line); 223 goto bad; 224 } 225 } 226 /* 227 * In the PCI configuration code, we simply assign the dev 228 * number to the interrupt line. We extract it here for the 229 * interrupt, but subtract off the lowest dev (13) to get 230 * the IRQ. 231 */ 232 #if defined(OPENPIC_SERIAL_MODE) 233 line -= 11; 234 #else 235 line -= 13; 236 #endif 237 238 *ihp = line; 239 return 0; 240 241 bad: 242 *ihp = -1; 243 return 1; 244 } 245 246 const char * 247 pci_intr_string(pc, ih) 248 pci_chipset_tag_t pc; 249 pci_intr_handle_t ih; 250 { 251 static char irqstr[8]; /* 4 + 2 + NULL + sanity */ 252 253 if (ih < 0 || ih >= ICU_LEN) 254 panic("pci_intr_string: bogus handle 0x%x\n", ih); 255 256 sprintf(irqstr, "irq %d", ih); 257 return (irqstr); 258 259 } 260 261 const struct evcnt * 262 pci_intr_evcnt(pc, ih) 263 pci_chipset_tag_t pc; 264 pci_intr_handle_t ih; 265 { 266 267 /* XXX for now, no evcnt parent reported */ 268 return NULL; 269 } 270 271 void * 272 pci_intr_establish(pc, ih, level, func, arg) 273 pci_chipset_tag_t pc; 274 pci_intr_handle_t ih; 275 int level, (*func) __P((void *)); 276 void *arg; 277 { 278 #if 0 279 if (ih < SANDPOINT_INTR_PCI0 || ih > SANDPOINT_INTR_PCI3) 280 panic("pci_intr_establish: bogus handle 0x%x\n", ih); 281 #endif 282 283 /* 284 * ih is the value assigned in pci_intr_map(), above. 285 * For the Sandpoint, this is the zero-based slot #, 286 * configured when the bus is set up. 287 */ 288 return intr_establish(ih, IST_LEVEL, level, func, arg); 289 } 290 291 void 292 pci_intr_disestablish(pc, cookie) 293 pci_chipset_tag_t pc; 294 void *cookie; 295 { 296 intr_disestablish(cookie); 297 } 298 299 void 300 pci_conf_interrupt(pci_chipset_tag_t pc, int bus, int dev, int pin, int swiz, 301 int *iline) 302 { 303 if (bus == 0) { 304 *iline = dev; 305 } else { 306 /* 307 * If we are not on bus zero, we're behind a bridge, so we 308 * swizzle. 309 * 310 * The documentation lies about this. In slot 3 (numbering 311 * from 0) aka device 16, INTD# becomes an interrupt for 312 * slot 2. INTC# becomes an interrupt for slot 1, etc. 313 * In slot 2 aka device 16, INTD# becomes an interrupt for 314 * slot 1, etc. 315 * 316 * Verified for INTD# on device 16, INTC# on device 16, 317 * INTD# on device 15, INTD# on device 13, and INTC# on 318 * device 14. I presume that the rest follow the same 319 * pattern. 320 * 321 * Slot 0 is device 13, and is the base for the rest. 322 */ 323 *iline = 13 + ((swiz + dev + 3) & 3); 324 } 325 } 326