Index: pccbb.c =================================================================== RCS file: /home/ncvs/src/sys/dev/pccbb/pccbb.c,v retrieving revision 1.59 diff -u -r1.59 pccbb.c --- pccbb.c 11 Oct 2002 04:30:59 -0000 1.59 +++ pccbb.c 28 Oct 2002 15:45:07 -0000 @@ -86,6 +86,8 @@ #include #include #include +#include +#include #include #include #include @@ -210,6 +212,13 @@ SYSCTL_ULONG(_hw_cbb, OID_AUTO, debug, CTLFLAG_RW, &cbb_debug, 0, "Verbose cardbus bridge debugging"); +int cbb_boot_deactivated = 0; +TUNABLE_INT("hw.cbb.boot_deactivated", &cbb_boot_deactivated); +SYSCTL_INT(_hw_cbb, OID_AUTO, boot_deactivated, CTLFLAG_RD, + &cbb_boot_deactivated, 0, + "Override the automatic powering up of pccards at boot."); + + static int cbb_chipset(uint32_t pci_id, const char **namep); static int cbb_probe(device_t brdev); static void cbb_chipinit(struct cbb_softc *sc); @@ -264,6 +273,84 @@ static void cbb_write_config(device_t brdev, int b, int s, int f, int reg, uint32_t val, int width); +static d_open_t crdopen; +static d_close_t crdclose; +static d_ioctl_t crdioctl; + +#define CDEV_MAJOR 50 +static struct cdevsw crd_cdevsw = { + /* open */ crdopen, + /* close */ crdclose, + /* read */ noread, + /* write */ nowrite, + /* ioctl */ crdioctl, + /* poll */ nopoll, + /* mmap */ nommap, + /* strategy */ nostrategy, + /* name */ "crd", + /* maj */ CDEV_MAJOR, + /* dump */ nodump, + /* psize */ nopsize, + /* flags */ 0, +}; + +#define PIOCSVIR _IOW('P', 10, int) /* Virtual insert/remove */ + +static int +crdopen(dev_t dev, int oflags, int devtype, d_thread_t *td) +{ + return (0); +} + +static int +crdclose(dev_t dev, int fflag, int devtype, d_thread_t *td) +{ + return (0); +} + +static int +crdioctl(dev_t dev, u_long cmd, caddr_t data, int fflag, d_thread_t *td) +{ + struct cbb_softc *sc; + int error; + int pwval; + + sc = dev->si_drv1; + + switch(cmd) { + /* + * Set power values. + */ + case PIOCSVIR: + error = EINVAL; + pwval = *(int *)data; + + switch (pwval) { + case 0: + if (sc->flags & CBB_CARD_OK) { + cbb_removal(sc); + error = 0; + sc->flags |= CBB_INACTIVATE; + } + break; + + case 1: + if (!(sc->flags & CBB_CARD_OK)) { + cbb_insert(sc); + error = 0; + } + break; + } + + break; + + default: + error = ENOTTY; + } + + return (error); +} + /* */ static __inline void @@ -560,6 +647,8 @@ { struct cbb_softc *sc = (struct cbb_softc *)device_get_softc(brdev); int rid; + int unit; + dev_t cbb_dev_t; mtx_init(&sc->mtx, device_get_nameunit(brdev), "cbb", MTX_DEF); cv_init(&sc->cv, "cbb cv"); @@ -680,6 +769,10 @@ /* reset interrupt */ cbb_set(sc, CBB_SOCKET_EVENT, cbb_get(sc, CBB_SOCKET_EVENT)); + if (cbb_boot_deactivated) { + sc->flags |= CBB_INACTIVATE; + } + /* Start the thread */ if (kthread_create(cbb_event_thread, sc, &sc->event_thread, 0, 0, "%s%d", device_get_name(sc->dev), device_get_unit(sc->dev))) { @@ -687,6 +780,10 @@ panic ("cbb_create_event_thread"); } + unit = device_get_unit(sc->dev); + cbb_dev_t = make_dev(&crd_cdevsw, unit, 0, 0, 0664, "card%d", unit); + cbb_dev_t->si_drv1 = sc; + return (0); err: if (sc->irq_res) @@ -913,10 +1010,13 @@ status = cbb_get(sc, CBB_SOCKET_STATE); mtx_lock(&Giant); - if ((status & CBB_SOCKET_STAT_CD) == 0) - cbb_insert(sc); - else + if ((status & CBB_SOCKET_STAT_CD) == 0) { + if (!(sc->flags & CBB_INACTIVATE)) { + cbb_insert(sc); + } + } else { cbb_removal(sc); + } mtx_unlock(&Giant); /* @@ -956,6 +1056,7 @@ if (sc->pccarddev != NULL) { sc->flags |= CBB_16BIT_CARD; sc->flags |= CBB_CARD_OK; + sc->flags &= ~CBB_INACTIVATE; if (CARD_ATTACH_CARD(sc->pccarddev) != 0) { device_printf(sc->dev, "PC Card card activation failed\n"); @@ -969,6 +1070,7 @@ if (sc->cbdev != NULL) { sc->flags &= ~CBB_16BIT_CARD; sc->flags |= CBB_CARD_OK; + sc->flags &= ~CBB_INACTIVATE; if (CARD_ATTACH_CARD(sc->cbdev) != 0) { device_printf(sc->dev, "CardBus card activation failed\n"); @@ -995,6 +1097,8 @@ else if ((!(sc->flags & CBB_16BIT_CARD)) && sc->cbdev != NULL) CARD_DETACH_CARD(sc->cbdev, DETACH_FORCE); cbb_destroy_res(sc); + sc->flags &= ~CBB_CARD_OK; + sc->flags &= ~CBB_INACTIVATE; } /************************************************************************/ @@ -1918,7 +2022,12 @@ cbb_setb(sc, CBB_SOCKET_MASK, CBB_SOCKET_MASK_CD); /* Force us to go query the socket state */ - cbb_setb(sc, CBB_SOCKET_FORCE, CBB_SOCKET_EVENT_CD); + if (!(sc->flags & CBB_INACTIVATE)) { + mtx_lock(&sc->mtx); + sc->flags &= ~CBB_CARD_OK; + cv_signal(&sc->cv); + mtx_unlock(&sc->mtx); + } error = bus_generic_resume(self); Index: pccbbvar.h =================================================================== RCS file: /home/ncvs/src/sys/dev/pccbb/pccbbvar.h,v retrieving revision 1.15 diff -u -r1.15 pccbbvar.h --- pccbbvar.h 7 Oct 2002 23:11:29 -0000 1.15 +++ pccbbvar.h 28 Oct 2002 15:31:17 -0000 @@ -65,6 +65,7 @@ struct mtx mtx; struct cv cv; u_int32_t flags; +#define CBB_INACTIVATE 0x04000000 #define CBB_CARD_OK 0x08000000 #define CBB_KLUDGE_ALLOC 0x10000000 #define CBB_16BIT_CARD 0x20000000