1 /* $NetBSD: ioasic.c,v 1.3 1999/12/06 11:52:36 simonb Exp $ */ 2 3 /* 4 * Copyright (c) 1994, 1995 Carnegie-Mellon University. 5 * All rights reserved. 6 * 7 * Author: Keith Bostic, Chris G. Demetriou, Jonathan Stone 8 * 9 * Permission to use, copy, modify and distribute this software and 10 * its documentation is hereby granted, provided that both the copyright 11 * notice and this permission notice appear in all copies of the 12 * software, derivative works or modified versions, and any portions 13 * thereof, and that both notices appear in supporting documentation. 14 * 15 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS" 16 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND 17 * FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE. 18 * 19 * Carnegie Mellon requests users of this software to return to 20 * 21 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU 22 * School of Computer Science 23 * Carnegie Mellon University 24 * Pittsburgh PA 15213-3890 25 * 26 * any improvements or extensions that they make and grant Carnegie the 27 * rights to redistribute these changes. 28 */ 29 30 #include <sys/param.h> 31 #include <sys/systm.h> 32 #include <sys/device.h> 33 34 #include <machine/bus.h> 35 #include <dev/tc/tcvar.h> 36 #include <dev/tc/ioasicvar.h> 37 38 #include <pmax/pmax/pmaxtype.h> 39 #include <pmax/pmax/asic.h> 40 #include <pmax/pmax/kmin.h> 41 #include <pmax/pmax/maxine.h> 42 #include <pmax/pmax/kn03.h> 43 #include <pmax/pmax/turbochannel.h> /* interrupt enable declaration */ 44 45 #include "opt_dec_3min.h" 46 #include "opt_dec_maxine.h" 47 #include "opt_dec_3maxplus.h" 48 49 #define C(x) ((void *)(x)) 50 #define ARRAY_SIZEOF(x) (sizeof((x)) / sizeof((x)[0])) 51 52 #if defined(DEC_3MIN) 53 static struct ioasic_dev kmin_ioasic_devs[] = { 54 { "lance", 0x0C0000, C(KMIN_LANCE_SLOT), IOASIC_INTR_LANCE, }, 55 { "scc", 0x100000, C(KMIN_SCC0_SLOT), IOASIC_INTR_SCC_0, }, 56 { "scc", 0x180000, C(KMIN_SCC1_SLOT), IOASIC_INTR_SCC_1, }, 57 { "mc146818", 0x200000, C(-1), 0 }, 58 { "asc", 0x300000, C(KMIN_SCSI_SLOT), IOASIC_INTR_SCSI, }, 59 }; 60 static int kmin_builtin_ndevs = ARRAY_SIZEOF(kmin_ioasic_devs); 61 static int kmin_ioasic_ndevs = ARRAY_SIZEOF(kmin_ioasic_devs); 62 #endif 63 64 #if defined(DEC_MAXINE) 65 static struct ioasic_dev xine_ioasic_devs[] = { 66 { "lance", 0x0C0000, C(XINE_LANCE_SLOT), IOASIC_INTR_LANCE }, 67 { "scc", 0x100000, C(XINE_SCC0_SLOT), IOASIC_INTR_SCC_0 }, 68 { "mc146818", 0x200000, C(-1), 0 }, 69 { "isdn", 0x240000, C(XINE_ISDN_SLOT), XINE_INTR_ISDN, }, 70 { "dtop", 0x280000, C(XINE_DTOP_SLOT), XINE_INTR_DTOP, }, 71 { "fdc", 0x2C0000, C(XINE_FLOPPY_SLOT), 0 }, 72 { "asc", 0x300000, C(XINE_SCSI_SLOT), IOASIC_INTR_SCSI, }, 73 { "(TC0)", 0x0, C(0), XINE_INTR_TC_0, }, 74 { "(TC1)", 0x0, C(1), XINE_INTR_TC_1, }, 75 { "(TC2)", 0x0, C(2), XINE_INTR_VINT, }, 76 }; 77 static int xine_builtin_ndevs = ARRAY_SIZEOF(xine_ioasic_devs) - 3; 78 static int xine_ioasic_ndevs = ARRAY_SIZEOF(xine_ioasic_devs); 79 #endif 80 81 #if defined(DEC_3MAXPLUS) 82 static struct ioasic_dev kn03_ioasic_devs[] = { 83 { "lance", 0x0C0000, C(KN03_LANCE_SLOT), IOASIC_INTR_LANCE, }, 84 { "z8530 ", 0x100000, C(KN03_SCC0_SLOT), IOASIC_INTR_SCC_0, }, 85 { "z8530 ", 0x180000, C(KN03_SCC1_SLOT), IOASIC_INTR_SCC_1, }, 86 { "mc146818", 0x200000, C(-1), 0, }, 87 { "asc", 0x300000, C(KN03_SCSI_SLOT), IOASIC_INTR_SCSI, }, 88 { "(TC0)", 0x0, C(0), KN03_INTR_TC_0, }, 89 { "(TC1)", 0x0, C(1), KN03_INTR_TC_1, }, 90 { "(TC2)", 0x0, C(2), KN03_INTR_TC_2, }, 91 }; 92 static int kn03_builtin_ndevs = ARRAY_SIZEOF(kn03_ioasic_devs) - 3; 93 static int kn03_ioasic_ndevs = ARRAY_SIZEOF(kn03_ioasic_devs); 94 #endif 95 96 static int ioasicmatch __P((struct device *, struct cfdata *, void *)); 97 static void ioasicattach __P((struct device *, struct device *, void *)); 98 99 const struct cfattach ioasic_ca = { 100 sizeof(struct ioasic_softc), ioasicmatch, ioasicattach 101 }; 102 103 tc_addr_t ioasic_base = 0; 104 105 static int 106 ioasicmatch(parent, cfdata, aux) 107 struct device *parent; 108 struct cfdata *cfdata; 109 void *aux; 110 { 111 struct tc_attach_args *ta = aux; 112 113 /* Make sure that we're looking for this type of device. */ 114 if (strncmp("IOCTL ", ta->ta_modname, TC_ROM_LLEN)) 115 return (0); 116 117 if (cfdata->cf_unit > 0) 118 return (0); 119 120 return (1); 121 } 122 123 static void 124 ioasicattach(parent, self, aux) 125 struct device *parent, *self; 126 void *aux; 127 { 128 struct ioasic_softc *sc = (struct ioasic_softc *)self; 129 struct tc_attach_args *ta = aux; 130 struct ioasic_dev *ioasic_devs; 131 int ioasic_ndevs, builtin_ndevs; 132 int i, imsk; 133 134 sc->sc_bst = ta->ta_memt; 135 if (bus_space_map(ta->ta_memt, ta->ta_addr, 136 0x400000, 0, &sc->sc_bsh)) { 137 printf("%s: unable to map device\n", sc->sc_dv.dv_xname); 138 return; 139 } 140 sc->sc_dmat = ta->ta_dmat; 141 sc->sc_cookie = ta->ta_cookie; 142 143 sc->sc_base = ta->ta_addr; /* XXX XXX XXX */ 144 145 printf("\n"); 146 147 switch (systype) { 148 #if defined(DEC_3MIN) 149 case DS_3MIN: 150 ioasic_devs = kmin_ioasic_devs; 151 ioasic_ndevs = kmin_ioasic_ndevs; 152 builtin_ndevs = kmin_builtin_ndevs; 153 break; 154 #endif 155 #if defined(DEC_MAXINE) 156 case DS_MAXINE: 157 ioasic_devs = xine_ioasic_devs; 158 ioasic_ndevs = xine_ioasic_ndevs; 159 builtin_ndevs = xine_builtin_ndevs; 160 break; 161 #endif 162 #if defined(DEC_3MAXPLUS) 163 case DS_3MAXPLUS: 164 ioasic_devs = kn03_ioasic_devs; 165 ioasic_ndevs = kn03_ioasic_ndevs; 166 builtin_ndevs = kn03_builtin_ndevs; 167 break; 168 #endif 169 default: 170 panic("ioasicmatch: how did we get here?"); 171 } 172 173 /* 174 * Turn off all device interrupt bits. 175 * (This _does_ include TC option slot bits. 176 */ 177 imsk = bus_space_read_4(sc->sc_bst, sc->sc_bsh, IOASIC_IMSK); 178 for (i = 0; i < ioasic_ndevs; i++) 179 imsk &= ~ioasic_devs[i].iad_intrbits; 180 bus_space_write_4(sc->sc_bst, sc->sc_bsh, IOASIC_IMSK, imsk); 181 182 /* 183 * Try to configure each device. 184 */ 185 ioasic_attach_devs(sc, ioasic_devs, builtin_ndevs); 186 } 187 188 #if 1 /* XXX for now XXX */ 189 void 190 ioasic_intr_establish(dev, cookie, level, handler, val) 191 struct device *dev; 192 void *cookie; 193 int level; 194 int (*handler) __P((void *)); 195 void *val; 196 { 197 (*tc_enable_interrupt)((unsigned)cookie, handler, val, 1); 198 } 199 200 #else /* XXX eventually XXX */ 201 202 void 203 ioasic_intr_establish(ioa, cookie, level, func, arg) 204 struct device *ioa; 205 void *cookie, *arg; 206 int level; 207 int (*func) __P((void *)); 208 { 209 struct ioasic_softc *sc = (void *)ioasic_cd.cd_devs[0]; 210 int i, intrbits; 211 212 for (i = 0; i < ioasic_ndevs; i++) { 213 if (ioasic_devs[i].iad_cookie == cookie) 214 goto found; 215 } 216 panic("ioasic_intr_establish: invalid cookie %d", (int)cookie); 217 found: 218 219 intrtab[(int)cookie].ih_func = func; 220 intrtab[(int)cookie].ih_arg = arg; 221 222 intrbits = ioasic_devs[i].iad_intrbits; 223 i = bus_space_read_4(sc->sc_bst, sc->sc_bsh, IOASIC_IMSK); 224 i |= intrbits; 225 bus_space_write_4(sc->sc_bst, sc->sc_bsh, IOASIC_IMSK, i); 226 } 227 228 void 229 ioasic_intr_disestablish(ioa, cookie) 230 struct device *ioa; 231 void *cookie; 232 { 233 panic("ioasic_intr_disestablish: cookie %d", (int)cookie); 234 } 235 #endif 236