1/* $NecBSD: nsp_pisa.c,v 1.4 1999/04/15 01:35:54 kmatsuda Exp $ */ 2/* $NetBSD$ */ 3 4/* 5 * [Ported for FreeBSD] 6 * Copyright (c) 2000 7 * Noriaki Mitsunaga, Mitsuru Iwasaki and Takanori Watanabe. 8 * All rights reserved. 9 * [NetBSD for NEC PC-98 series] 10 * Copyright (c) 1998 11 * NetBSD/pc98 porting staff. All rights reserved. 12 * 13 * Redistribution and use in source and binary forms, with or without 14 * modification, are permitted provided that the following conditions 15 * are met: 16 * 1. Redistributions of source code must retain the above copyright 17 * notice, this list of conditions and the following disclaimer. 18 * 2. Redistributions in binary form must reproduce the above copyright 19 * notice, this list of conditions and the following disclaimer in the 20 * documentation and/or other materials provided with the distribution. 21 * 3. The name of the author may not be used to endorse or promote products 22 * derived from this software without specific prior written permission. 23 * 24 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 25 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 26 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 27 * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, 28 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 29 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 30 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 31 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 32 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 33 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 34 * POSSIBILITY OF SUCH DAMAGE. 35 */ 36 37#include <sys/cdefs.h>
|
65 66#define PIO_MODE 0x100 /* pd_flags */ 67 68static int nspprobe(DEVPORT_PDEVICE devi); 69static int nspattach(DEVPORT_PDEVICE devi); 70 71static void nsp_card_unload (DEVPORT_PDEVICE); 72 73const struct pccard_product nsp_products[] = { 74 PCMCIA_CARD(IODATA3, CBSC16, 0), 75 PCMCIA_CARD(PANASONIC, KME, 0), 76 PCMCIA_CARD(WORKBIT2, NINJA_SCSI3, 0), 77 PCMCIA_CARD(WORKBIT, ULTRA_NINJA_16, 0), 78 { NULL } 79}; 80 81/* 82 * Additional code for FreeBSD new-bus PCCard frontend 83 */ 84 85static void 86nsp_pccard_intr(void * arg) 87{ 88 nspintr(arg); 89} 90 91static void 92nsp_release_resource(DEVPORT_PDEVICE dev) 93{ 94 struct nsp_softc *sc = device_get_softc(dev); 95 96 if (sc->nsp_intrhand) { 97 bus_teardown_intr(dev, sc->irq_res, sc->nsp_intrhand); 98 } 99 100 if (sc->port_res) { 101 bus_release_resource(dev, SYS_RES_IOPORT, 102 sc->port_rid, sc->port_res); 103 } 104 105 if (sc->irq_res) { 106 bus_release_resource(dev, SYS_RES_IRQ, 107 sc->irq_rid, sc->irq_res); 108 } 109 110 if (sc->mem_res) { 111 bus_release_resource(dev, SYS_RES_MEMORY, 112 sc->mem_rid, sc->mem_res); 113 } 114} 115 116static int 117nsp_alloc_resource(DEVPORT_PDEVICE dev) 118{ 119 struct nsp_softc *sc = device_get_softc(dev); 120 u_long ioaddr, iosize, maddr, msize; 121 int error; 122 123 error = bus_get_resource(dev, SYS_RES_IOPORT, 0, &ioaddr, &iosize); 124 if (error || iosize < NSP_IOSIZE) 125 return(ENOMEM); 126 127 sc->port_rid = 0; 128 sc->port_res = bus_alloc_resource(dev, SYS_RES_IOPORT, &sc->port_rid, 129 0, ~0, NSP_IOSIZE, RF_ACTIVE); 130 if (sc->port_res == NULL) { 131 nsp_release_resource(dev); 132 return(ENOMEM); 133 } 134 135 sc->irq_rid = 0; 136 sc->irq_res = bus_alloc_resource_any(dev, SYS_RES_IRQ, &sc->irq_rid, 137 RF_ACTIVE); 138 if (sc->irq_res == NULL) { 139 nsp_release_resource(dev); 140 return(ENOMEM); 141 } 142 143 error = bus_get_resource(dev, SYS_RES_MEMORY, 0, &maddr, &msize); 144 if (error) { 145 return(0); /* XXX */ 146 } 147 148 /* No need to allocate memory if not configured and it's in PIO mode */ 149 if (maddr == 0 || msize == 0) { 150 if ((DEVPORT_PDEVFLAGS(dev) & PIO_MODE) == 0) { 151 printf("Memory window was not configured. Configure or use in PIO mode."); 152 nsp_release_resource(dev); 153 return(ENOMEM); 154 } 155 /* no need to allocate memory if PIO mode */ 156 return(0); 157 } 158 159 sc->mem_rid = 0; 160 sc->mem_res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &sc->mem_rid, 161 RF_ACTIVE); 162 if (sc->mem_res == NULL) { 163 nsp_release_resource(dev); 164 return(ENOMEM); 165 } 166 167 return(0); 168} 169 170static int nsp_pccard_match(device_t dev) 171{ 172 const struct pccard_product *pp; 173 174 if ((pp = pccard_product_lookup(dev, nsp_products, 175 sizeof(nsp_products[0]), NULL)) != NULL) { 176 device_set_desc(dev, pp->pp_name); 177 return(0); 178 } 179 return(EIO); 180} 181 182static int 183nsp_pccard_probe(DEVPORT_PDEVICE dev) 184{ 185 struct nsp_softc *sc = device_get_softc(dev); 186 int error; 187 188 bzero(sc, sizeof(struct nsp_softc)); 189 190 error = nsp_alloc_resource(dev); 191 if (error) { 192 return(error); 193 } 194 195 if (nspprobe(dev) == 0) { 196 nsp_release_resource(dev); 197 return(ENXIO); 198 } 199 200 nsp_release_resource(dev); 201 202 return(0); 203} 204 205static int 206nsp_pccard_attach(DEVPORT_PDEVICE dev) 207{ 208 struct nsp_softc *sc = device_get_softc(dev); 209 int error; 210 211 error = nsp_alloc_resource(dev); 212 if (error) { 213 return(error); 214 } 215 216 error = bus_setup_intr(dev, sc->irq_res, INTR_TYPE_CAM | INTR_ENTROPY, 217 nsp_pccard_intr, (void *)sc, &sc->nsp_intrhand); 218 if (error) { 219 nsp_release_resource(dev); 220 return(error); 221 } 222 223 if (nspattach(dev) == 0) { 224 nsp_release_resource(dev); 225 return(ENXIO); 226 } 227 228 return(0); 229} 230 231static void 232nsp_pccard_detach(DEVPORT_PDEVICE dev) 233{ 234 nsp_card_unload(dev); 235 nsp_release_resource(dev); 236} 237 238static device_method_t nsp_pccard_methods[] = { 239 /* Device interface */ 240 DEVMETHOD(device_probe, pccard_compat_probe), 241 DEVMETHOD(device_attach, pccard_compat_attach), 242 DEVMETHOD(device_detach, nsp_pccard_detach), 243 244 /* Card interface */ 245 DEVMETHOD(card_compat_match, nsp_pccard_match), 246 DEVMETHOD(card_compat_probe, nsp_pccard_probe), 247 DEVMETHOD(card_compat_attach, nsp_pccard_attach), 248 249 { 0, 0 } 250}; 251 252static driver_t nsp_pccard_driver = { 253 "nsp", 254 nsp_pccard_methods, 255 sizeof(struct nsp_softc), 256}; 257 258static devclass_t nsp_devclass; 259 260MODULE_DEPEND(nsp, scsi_low, 1, 1, 1); 261DRIVER_MODULE(nsp, pccard, nsp_pccard_driver, nsp_devclass, 0, 0); 262 263static void 264nsp_card_unload(DEVPORT_PDEVICE devi) 265{ 266 struct nsp_softc *sc = DEVPORT_PDEVGET_SOFTC(devi); 267 intrmask_t s; 268 269 printf("%s: unload\n",sc->sc_sclow.sl_xname); 270 s = splcam(); 271 scsi_low_deactivate((struct scsi_low_softc *)sc); 272 scsi_low_dettach(&sc->sc_sclow); 273 splx(s); 274} 275 276static int 277nspprobe(DEVPORT_PDEVICE devi) 278{ 279 int rv; 280 struct nsp_softc *sc = device_get_softc(devi); 281 282 rv = nspprobesubr(rman_get_bustag(sc->port_res), 283 rman_get_bushandle(sc->port_res), 284 DEVPORT_PDEVFLAGS(devi)); 285 286 return rv; 287} 288 289static int 290nspattach(DEVPORT_PDEVICE devi) 291{ 292 struct nsp_softc *sc; 293 struct scsi_low_softc *slp; 294 u_int32_t flags = DEVPORT_PDEVFLAGS(devi); 295 u_int iobase = DEVPORT_PDEVIOBASE(devi); 296 intrmask_t s; 297 char dvname[16]; 298 299 strcpy(dvname,"nsp"); 300 301 if (iobase == 0) 302 { 303 printf("%s: no ioaddr is given\n", dvname); 304 return (0); 305 } 306 307 sc = DEVPORT_PDEVALLOC_SOFTC(devi); 308 if (sc == NULL) { 309 return (0); 310 } 311 312 slp = &sc->sc_sclow; 313 slp->sl_dev = devi; 314 sc->sc_iot = rman_get_bustag(sc->port_res); 315 sc->sc_ioh = rman_get_bushandle(sc->port_res); 316 317 if(sc->mem_res == NULL){ 318 printf("WARNING: CANNOT GET Memory RESOURCE going PIO mode"); 319 flags |= PIO_MODE; 320 } 321 322 if((flags & PIO_MODE) == 0) { 323 sc->sc_memt = rman_get_bustag(sc->mem_res); 324 sc->sc_memh = rman_get_bushandle(sc->mem_res); 325 } else { 326 sc->sc_memh = 0; 327 } 328 /* slp->sl_irq = devi->pd_irq; */ 329 sc->sc_iclkdiv = CLKDIVR_20M; 330 sc->sc_clkdiv = CLKDIVR_40M; 331 332 slp->sl_hostid = NSP_HOSTID; 333 slp->sl_cfgflags = flags; 334 335 s = splcam(); 336 nspattachsubr(sc); 337 splx(s); 338 339 return(NSP_IOSIZE); 340}
|