Deleted Added
full compact
pccard.c (121521) pccard.c (121905)
1/* $NetBSD: pcmcia.c,v 1.23 2000/07/28 19:17:02 drochner Exp $ */
2
3/*
4 * Copyright (c) 1997 Marc Horowitz. All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:

--- 16 unchanged lines hidden (view full) ---

25 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */
31
32#include <sys/cdefs.h>
1/* $NetBSD: pcmcia.c,v 1.23 2000/07/28 19:17:02 drochner Exp $ */
2
3/*
4 * Copyright (c) 1997 Marc Horowitz. All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:

--- 16 unchanged lines hidden (view full) ---

25 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */
31
32#include <sys/cdefs.h>
33__FBSDID("$FreeBSD: head/sys/dev/pccard/pccard.c 121521 2003-10-26 00:51:40Z imp $");
33__FBSDID("$FreeBSD: head/sys/dev/pccard/pccard.c 121905 2003-11-02 20:18:19Z imp $");
34
35#include <sys/param.h>
36#include <sys/systm.h>
37#include <sys/malloc.h>
38#include <sys/module.h>
39#include <sys/kernel.h>
40#include <sys/queue.h>
41#include <sys/sysctl.h>

--- 216 unchanged lines hidden (view full) ---

258 */
259 pccard_function_init(pf);
260 if (sc->sc_enabled_count == 0)
261 POWER_ENABLE_SOCKET(device_get_parent(dev), dev);
262 if (pccard_function_enable(pf) == 0 &&
263 pccard_set_default_descr(child) == 0 &&
264 device_probe_and_attach(child) == 0) {
265 DEVPRINTF((sc->dev, "function %d CCR at %d "
34
35#include <sys/param.h>
36#include <sys/systm.h>
37#include <sys/malloc.h>
38#include <sys/module.h>
39#include <sys/kernel.h>
40#include <sys/queue.h>
41#include <sys/sysctl.h>

--- 216 unchanged lines hidden (view full) ---

258 */
259 pccard_function_init(pf);
260 if (sc->sc_enabled_count == 0)
261 POWER_ENABLE_SOCKET(device_get_parent(dev), dev);
262 if (pccard_function_enable(pf) == 0 &&
263 pccard_set_default_descr(child) == 0 &&
264 device_probe_and_attach(child) == 0) {
265 DEVPRINTF((sc->dev, "function %d CCR at %d "
266 "offset %x: %x %x %x %x, %x %x %x %x, %x\n",
266 "offset %x mask %x: "
267 "%x %x %x %x, %x %x %x %x, %x\n",
267 pf->number, pf->pf_ccr_window, pf->pf_ccr_offset,
268 pf->number, pf->pf_ccr_window, pf->pf_ccr_offset,
268 pccard_ccr_read(pf, 0x00),
269 pf->ccr_mask, pccard_ccr_read(pf, 0x00),
269 pccard_ccr_read(pf, 0x02), pccard_ccr_read(pf, 0x04),
270 pccard_ccr_read(pf, 0x06), pccard_ccr_read(pf, 0x0A),
271 pccard_ccr_read(pf, 0x0C), pccard_ccr_read(pf, 0x0E),
272 pccard_ccr_read(pf, 0x10), pccard_ccr_read(pf, 0x12)));
273 } else {
274 if (pf->cfe != NULL)
275 pccard_function_disable(pf);
276 }

--- 246 unchanged lines hidden (view full) ---

523 BUS_RELEASE_RESOURCE(device_get_parent(pf->sc->dev),
524 pf->sc->dev, rle->type, rle->rid, rle->res);
525 rle->res = NULL;
526 }
527 }
528 resource_list_free(&devi->resources);
529}
530
270 pccard_ccr_read(pf, 0x02), pccard_ccr_read(pf, 0x04),
271 pccard_ccr_read(pf, 0x06), pccard_ccr_read(pf, 0x0A),
272 pccard_ccr_read(pf, 0x0C), pccard_ccr_read(pf, 0x0E),
273 pccard_ccr_read(pf, 0x10), pccard_ccr_read(pf, 0x12)));
274 } else {
275 if (pf->cfe != NULL)
276 pccard_function_disable(pf);
277 }

--- 246 unchanged lines hidden (view full) ---

524 BUS_RELEASE_RESOURCE(device_get_parent(pf->sc->dev),
525 pf->sc->dev, rle->type, rle->rid, rle->res);
526 rle->res = NULL;
527 }
528 }
529 resource_list_free(&devi->resources);
530}
531
532static void
533pccard_mfc_adjust_iobase(struct pccard_function *pf, bus_addr_t addr,
534 bus_addr_t offset, bus_size_t size)
535{
536 bus_addr_t iosize;
537 bus_size_t tmp;
538
539 if (addr != 0) {
540 if (pf->pf_mfc_iomax == 0) {
541 pf->pf_mfc_iobase = addr + offset;
542 pf->pf_mfc_iomax = pf->pf_mfc_iobase + size;
543 } else {
544 /* this makes the assumption that nothing overlaps */
545 if (pf->pf_mfc_iobase > addr + offset)
546 pf->pf_mfc_iobase = addr + offset;
547 if (pf->pf_mfc_iomax < addr + offset + size)
548 pf->pf_mfc_iomax = addr + offset + size;
549 }
550 }
551
552 tmp = pf->pf_mfc_iomax - pf->pf_mfc_iobase;
553 /* round up to nearest (2^n)-1 */
554 for (iosize = 1; iosize < tmp; iosize <<= 1)
555 ;
556 iosize--;
557
558 DEVPRINTF((pf->dev, "MFC: I/O base 0x%x IOSIZE %lld\n",
559 pf->pf_mfc_iobase, (uint64_t) iosize));
560 pccard_ccr_write(pf, PCCARD_CCR_IOBASE0,
561 pf->pf_mfc_iobase & 0xff);
562 pccard_ccr_write(pf, PCCARD_CCR_IOBASE1,
563 (pf->pf_mfc_iobase >> 8) & 0xff);
564 pccard_ccr_write(pf, PCCARD_CCR_IOBASE2, 0);
565 pccard_ccr_write(pf, PCCARD_CCR_IOBASE3, 0);
566 pccard_ccr_write(pf, PCCARD_CCR_IOSIZE, iosize);
567}
568
531/* Enable a PCCARD function */
532static int
533pccard_function_enable(struct pccard_function *pf)
534{
535 struct pccard_function *tmp;
536 int reg;
537 device_t dev = pf->sc->dev;
538

--- 71 unchanged lines hidden (view full) ---

610 if ((pf->cfe->flags & PCCARD_CFE_IO16) == 0)
611 reg |= PCCARD_CCR_STATUS_IOIS8;
612 if (pf->cfe->flags & PCCARD_CFE_AUDIO)
613 reg |= PCCARD_CCR_STATUS_AUDIO;
614 pccard_ccr_write(pf, PCCARD_CCR_STATUS, reg);
615
616 pccard_ccr_write(pf, PCCARD_CCR_SOCKETCOPY, 0);
617
569/* Enable a PCCARD function */
570static int
571pccard_function_enable(struct pccard_function *pf)
572{
573 struct pccard_function *tmp;
574 int reg;
575 device_t dev = pf->sc->dev;
576

--- 71 unchanged lines hidden (view full) ---

648 if ((pf->cfe->flags & PCCARD_CFE_IO16) == 0)
649 reg |= PCCARD_CCR_STATUS_IOIS8;
650 if (pf->cfe->flags & PCCARD_CFE_AUDIO)
651 reg |= PCCARD_CCR_STATUS_AUDIO;
652 pccard_ccr_write(pf, PCCARD_CCR_STATUS, reg);
653
654 pccard_ccr_write(pf, PCCARD_CCR_SOCKETCOPY, 0);
655
618 if (pccard_mfc(pf->sc)) {
619 long tmp, iosize;
656 if (pccard_mfc(pf->sc))
657 pccard_mfc_adjust_iobase(pf, 0, 0, 0);
620
658
621 tmp = pf->pf_mfc_iomax - pf->pf_mfc_iobase;
622 /* round up to nearest (2^n)-1 */
623 for (iosize = 1; iosize < tmp; iosize <<= 1)
624 ;
625 iosize--;
626
627 pccard_ccr_write(pf, PCCARD_CCR_IOBASE0,
628 pf->pf_mfc_iobase & 0xff);
629 pccard_ccr_write(pf, PCCARD_CCR_IOBASE1,
630 (pf->pf_mfc_iobase >> 8) & 0xff);
631 pccard_ccr_write(pf, PCCARD_CCR_IOBASE2, 0);
632 pccard_ccr_write(pf, PCCARD_CCR_IOBASE3, 0);
633
634 pccard_ccr_write(pf, PCCARD_CCR_IOSIZE, iosize);
635 }
636
637#ifdef PCCARDDEBUG
638 if (pccard_debug) {
639 STAILQ_FOREACH(tmp, &pf->sc->card.pf_head, pf_list) {
640 device_printf(tmp->sc->dev,
641 "function %d CCR at %d offset %x: "
642 "%x %x %x %x, %x %x %x %x, %x\n",
643 tmp->number, tmp->pf_ccr_window,
644 tmp->pf_ccr_offset,

--- 402 unchanged lines hidden (view full) ---

1047
1048static struct resource *
1049pccard_alloc_resource(device_t dev, device_t child, int type, int *rid,
1050 u_long start, u_long end, u_long count, u_int flags)
1051{
1052 struct pccard_ivar *dinfo;
1053 struct resource_list_entry *rle = 0;
1054 int passthrough = (device_get_parent(child) != dev);
659#ifdef PCCARDDEBUG
660 if (pccard_debug) {
661 STAILQ_FOREACH(tmp, &pf->sc->card.pf_head, pf_list) {
662 device_printf(tmp->sc->dev,
663 "function %d CCR at %d offset %x: "
664 "%x %x %x %x, %x %x %x %x, %x\n",
665 tmp->number, tmp->pf_ccr_window,
666 tmp->pf_ccr_offset,

--- 402 unchanged lines hidden (view full) ---

1069
1070static struct resource *
1071pccard_alloc_resource(device_t dev, device_t child, int type, int *rid,
1072 u_long start, u_long end, u_long count, u_int flags)
1073{
1074 struct pccard_ivar *dinfo;
1075 struct resource_list_entry *rle = 0;
1076 int passthrough = (device_get_parent(child) != dev);
1077 int isdefault = (start == 0 && end == ~0UL && count == 1);
1055 struct resource *r = NULL;
1056
1078 struct resource *r = NULL;
1079
1080 /* XXX I'm no longer sure this is right */
1057 if (passthrough) {
1058 return (BUS_ALLOC_RESOURCE(device_get_parent(dev), child,
1059 type, rid, start, end, count, flags));
1060 }
1061
1062 dinfo = device_get_ivars(child);
1063 rle = resource_list_find(&dinfo->resources, type, *rid);
1064
1081 if (passthrough) {
1082 return (BUS_ALLOC_RESOURCE(device_get_parent(dev), child,
1083 type, rid, start, end, count, flags));
1084 }
1085
1086 dinfo = device_get_ivars(child);
1087 rle = resource_list_find(&dinfo->resources, type, *rid);
1088
1065 if (rle == NULL)
1066 return (NULL); /* no resource of that type/rid */
1067
1068 if (rle->res == NULL) {
1069 switch(type) {
1070 case SYS_RES_IOPORT:
1071 r = bus_alloc_resource(dev, type, rid, start, end,
1072 count, rman_make_alignment_flags(count));
1073 if (r == NULL)
1074 goto bad;
1075 resource_list_add(&dinfo->resources, type, *rid,
1076 rman_get_start(r), rman_get_end(r), count);
1077 rle = resource_list_find(&dinfo->resources, type, *rid);
1078 if (!rle)
1079 goto bad;
1080 rle->res = r;
1081 break;
1082 case SYS_RES_MEMORY:
1083 break;
1084 case SYS_RES_IRQ:
1085 break;
1086 }
1087 return (rle->res);
1089 if (rle == NULL && isdefault)
1090 return (NULL); /* no resource of that type/rid */
1091 if (rle == NULL || rle->res == NULL) {
1092 /* Do we want this device to own it? */
1093 /* XXX I think so, but that might be lame XXX */
1094 r = bus_alloc_resource(dev, type, rid, start, end,
1095 count, flags /* XXX aligment? */);
1096 if (r == NULL)
1097 goto bad;
1098 resource_list_add(&dinfo->resources, type, *rid,
1099 rman_get_start(r), rman_get_end(r), count);
1100 rle = resource_list_find(&dinfo->resources, type, *rid);
1101 if (!rle)
1102 goto bad;
1103 rle->res = r;
1088 }
1104 }
1105 /*
1106 * XXX the following looks wrong, in theory, but likely it is
1107 * XXX needed because of how the CIS code allocates resources
1108 * XXX for this device.
1109 */
1089 if (rman_get_device(rle->res) != dev)
1090 return (NULL);
1091 bus_release_resource(dev, type, *rid, rle->res);
1092 rle->res = NULL;
1093 switch(type) {
1094 case SYS_RES_IOPORT:
1095 case SYS_RES_MEMORY:
1096 if (!(flags & RF_ALIGNMENT_MASK))

--- 150 unchanged lines hidden (view full) ---

1247 func->intr_handler = NULL;
1248 func->intr_handler_arg = NULL;
1249 func->intr_handler_cookie = NULL;
1250 }
1251
1252 return (ret);
1253}
1254
1110 if (rman_get_device(rle->res) != dev)
1111 return (NULL);
1112 bus_release_resource(dev, type, *rid, rle->res);
1113 rle->res = NULL;
1114 switch(type) {
1115 case SYS_RES_IOPORT:
1116 case SYS_RES_MEMORY:
1117 if (!(flags & RF_ALIGNMENT_MASK))

--- 150 unchanged lines hidden (view full) ---

1268 func->intr_handler = NULL;
1269 func->intr_handler_arg = NULL;
1270 func->intr_handler_cookie = NULL;
1271 }
1272
1273 return (ret);
1274}
1275
1276static int
1277pccard_activate_resource(device_t brdev, device_t child, int type, int rid,
1278 struct resource *r)
1279{
1280 struct pccard_ivar *ivar = PCCARD_IVAR(child);
1281 struct pccard_function *pf = ivar->fcn;
1282
1283 switch(type) {
1284 case SYS_RES_IOPORT:
1285 /*
1286 * We need to adjust IOBASE[01] and IOSIZE if we're an MFC
1287 * card.
1288 */
1289 if (pccard_mfc(pf->sc))
1290 pccard_mfc_adjust_iobase(pf, rman_get_start(r), 0,
1291 rman_get_size(r));
1292 break;
1293 default:
1294 break;
1295 }
1296 return (bus_generic_activate_resource(brdev, child, type, rid, r));
1297}
1298
1299static int
1300pccard_deactivate_resource(device_t brdev, device_t child, int type,
1301 int rid, struct resource *r)
1302{
1303 /* XXX undo pccard_activate_resource? XXX */
1304 return (bus_generic_deactivate_resource(brdev, child, type, rid, r));
1305}
1306
1255static device_method_t pccard_methods[] = {
1256 /* Device interface */
1257 DEVMETHOD(device_probe, pccard_probe),
1258 DEVMETHOD(device_attach, pccard_attach),
1259 DEVMETHOD(device_detach, pccard_detach),
1260 DEVMETHOD(device_shutdown, bus_generic_shutdown),
1261 DEVMETHOD(device_suspend, pccard_suspend),
1262 DEVMETHOD(device_resume, pccard_resume),
1263
1264 /* Bus interface */
1265 DEVMETHOD(bus_print_child, pccard_print_child),
1266 DEVMETHOD(bus_driver_added, pccard_driver_added),
1267 DEVMETHOD(bus_child_detached, pccard_child_detached),
1268 DEVMETHOD(bus_alloc_resource, pccard_alloc_resource),
1269 DEVMETHOD(bus_release_resource, pccard_release_resource),
1307static device_method_t pccard_methods[] = {
1308 /* Device interface */
1309 DEVMETHOD(device_probe, pccard_probe),
1310 DEVMETHOD(device_attach, pccard_attach),
1311 DEVMETHOD(device_detach, pccard_detach),
1312 DEVMETHOD(device_shutdown, bus_generic_shutdown),
1313 DEVMETHOD(device_suspend, pccard_suspend),
1314 DEVMETHOD(device_resume, pccard_resume),
1315
1316 /* Bus interface */
1317 DEVMETHOD(bus_print_child, pccard_print_child),
1318 DEVMETHOD(bus_driver_added, pccard_driver_added),
1319 DEVMETHOD(bus_child_detached, pccard_child_detached),
1320 DEVMETHOD(bus_alloc_resource, pccard_alloc_resource),
1321 DEVMETHOD(bus_release_resource, pccard_release_resource),
1270 DEVMETHOD(bus_activate_resource, bus_generic_activate_resource),
1271 DEVMETHOD(bus_deactivate_resource, bus_generic_deactivate_resource),
1322 DEVMETHOD(bus_activate_resource, pccard_activate_resource),
1323 DEVMETHOD(bus_deactivate_resource, pccard_deactivate_resource),
1272 DEVMETHOD(bus_setup_intr, pccard_setup_intr),
1273 DEVMETHOD(bus_teardown_intr, pccard_teardown_intr),
1274 DEVMETHOD(bus_set_resource, pccard_set_resource),
1275 DEVMETHOD(bus_get_resource, pccard_get_resource),
1276 DEVMETHOD(bus_delete_resource, pccard_delete_resource),
1277 DEVMETHOD(bus_probe_nomatch, pccard_probe_nomatch),
1278 DEVMETHOD(bus_read_ivar, pccard_read_ivar),
1279 DEVMETHOD(bus_child_pnpinfo_str, pccard_child_pnpinfo_str),

--- 26 unchanged lines hidden ---
1324 DEVMETHOD(bus_setup_intr, pccard_setup_intr),
1325 DEVMETHOD(bus_teardown_intr, pccard_teardown_intr),
1326 DEVMETHOD(bus_set_resource, pccard_set_resource),
1327 DEVMETHOD(bus_get_resource, pccard_get_resource),
1328 DEVMETHOD(bus_delete_resource, pccard_delete_resource),
1329 DEVMETHOD(bus_probe_nomatch, pccard_probe_nomatch),
1330 DEVMETHOD(bus_read_ivar, pccard_read_ivar),
1331 DEVMETHOD(bus_child_pnpinfo_str, pccard_child_pnpinfo_str),

--- 26 unchanged lines hidden ---