1 /* 2 * Copyright (c) 1990 The Regents of the University of California. 3 * All rights reserved. 4 * 5 * This code is derived from software contributed to Berkeley by 6 * Don Ahn. 7 * 8 * Libretto PCMCIA floppy support by David Horwitt (dhorwitt@ucsd.edu) 9 * aided by the Linux floppy driver modifications from David Bateman 10 * (dbateman@eng.uts.edu.au). 11 * 12 * Copyright (c) 1993, 1994 by 13 * jc@irbs.UUCP (John Capo) 14 * vak@zebub.msk.su (Serge Vakulenko) 15 * ache@astral.msk.su (Andrew A. Chernov) 16 * 17 * Copyright (c) 1993, 1994, 1995 by 18 * joerg_wunsch@uriah.sax.de (Joerg Wunsch) 19 * dufault@hda.com (Peter Dufault) 20 * 21 * Copyright (c) 2001 Joerg Wunsch, 22 * joerg_wunsch@uriah.sax.de (Joerg Wunsch) 23 * 24 * Redistribution and use in source and binary forms, with or without 25 * modification, are permitted provided that the following conditions 26 * are met: 27 * 1. Redistributions of source code must retain the above copyright 28 * notice, this list of conditions and the following disclaimer. 29 * 2. Redistributions in binary form must reproduce the above copyright 30 * notice, this list of conditions and the following disclaimer in the 31 * documentation and/or other materials provided with the distribution. 32 * 3. All advertising materials mentioning features or use of this software 33 * must display the following acknowledgement: 34 * This product includes software developed by the University of 35 * California, Berkeley and its contributors. 36 * 4. Neither the name of the University nor the names of its contributors 37 * may be used to endorse or promote products derived from this software 38 * without specific prior written permission. 39 * 40 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 41 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 42 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 43 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 44 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 45 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 46 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 47 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 48 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 49 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 50 * SUCH DAMAGE. 51 * 52 * $DragonFly: src/sys/dev/disk/fd/fd_pccard.c,v 1.2 2004/02/19 15:48:26 joerg Exp $ 53 */ 54 55 #include <sys/param.h> 56 #include <sys/systm.h> 57 #include <sys/buf.h> 58 #include <sys/bus.h> 59 #include <sys/kernel.h> 60 #include <sys/module.h> 61 #include <machine/bus.h> 62 63 #include "fdc.h" 64 #include "fdreg.h" 65 66 #include <bus/pccard/pccardvar.h> 67 #include <bus/pccard/pccarddevs.h> 68 69 #include "card_if.h" 70 71 static const struct pccard_product fdc_products[] = { 72 PCMCIA_CARD(YEDATA, EXTERNAL_FDD, 0), 73 { NULL } 74 }; 75 76 static void 77 fdctl_wr_pcmcia(fdc_p fdc, u_int8_t v) 78 { 79 bus_space_write_1(fdc->portt, fdc->porth, FDCTL+fdc->port_off, v); 80 } 81 82 static int fdc_pccard_match(device_t dev) 83 { 84 const struct pccard_product *pp; 85 86 if ((pp = pccard_product_lookup(dev, fdc_products, 87 sizeof(fdc_products[0]), NULL)) != NULL) { 88 device_set_desc(dev, pp->pp_name); 89 return (0); 90 } 91 return (ENXIO); 92 } 93 94 static int 95 fdc_pccard_probe(device_t dev) 96 { 97 int error; 98 struct fdc_data *fdc; 99 100 fdc = device_get_softc(dev); 101 bzero(fdc, sizeof *fdc); 102 fdc->fdc_dev = dev; 103 fdc->fdctl_wr = fdctl_wr_pcmcia; 104 105 fdc->flags |= FDC_ISPCMCIA | FDC_NODMA; 106 107 /* Attempt to allocate our resources for the duration of the probe */ 108 error = fdc_alloc_resources(fdc); 109 if (error) 110 goto out; 111 112 /* First - lets reset the floppy controller */ 113 fdout_wr(fdc, 0); 114 DELAY(100); 115 fdout_wr(fdc, FDO_FRST); 116 117 /* see if it can handle a command */ 118 if (fd_cmd(fdc, 3, NE7CMD_SPECIFY, NE7_SPEC_1(3, 240), 119 NE7_SPEC_2(2, 0), 0)) { 120 error = ENXIO; 121 goto out; 122 } 123 124 fdc->fdct = FDC_NE765; 125 126 out: 127 fdc_release_resources(fdc); 128 return (error); 129 } 130 131 static int 132 fdc_pccard_detach(device_t dev) 133 { 134 struct fdc_data *fdc; 135 int error; 136 137 fdc = device_get_softc(dev); 138 139 /* have our children detached first */ 140 if ((error = bus_generic_detach(dev))) 141 return (error); 142 143 if ((fdc->flags & FDC_ATTACHED) == 0) { 144 device_printf(dev, "already unloaded\n"); 145 return (0); 146 } 147 fdc->flags &= ~FDC_ATTACHED; 148 149 BUS_TEARDOWN_INTR(device_get_parent(dev), dev, fdc->res_irq, 150 fdc->fdc_intr); 151 fdc_release_resources(fdc); 152 device_printf(dev, "unload\n"); 153 return (0); 154 } 155 156 static device_method_t fdc_pccard_methods[] = { 157 /* Device interface */ 158 DEVMETHOD(device_probe, pccard_compat_probe), 159 DEVMETHOD(device_attach, pccard_compat_attach), 160 DEVMETHOD(device_detach, fdc_pccard_detach), 161 DEVMETHOD(device_shutdown, bus_generic_shutdown), 162 DEVMETHOD(device_suspend, bus_generic_suspend), 163 DEVMETHOD(device_resume, bus_generic_resume), 164 165 /* Card interface */ 166 DEVMETHOD(card_compat_match, fdc_pccard_match), 167 DEVMETHOD(card_compat_probe, fdc_pccard_probe), 168 DEVMETHOD(card_compat_attach, fdc_attach), 169 /* Device interface */ 170 171 /* Bus interface */ 172 DEVMETHOD(bus_print_child, fdc_print_child), 173 DEVMETHOD(bus_read_ivar, fdc_read_ivar), 174 /* Our children never use any other bus interface methods. */ 175 176 { 0, 0 } 177 }; 178 179 static driver_t fdc_pccard_driver = { 180 "fdc", 181 fdc_pccard_methods, 182 sizeof(struct fdc_data) 183 }; 184 185 DRIVER_MODULE(fdc, pccard, fdc_pccard_driver, fdc_devclass, 0, 0); 186