Module Name: src Committed By: christos Date: Tue Dec 30 20:29:43 UTC 2014
Modified Files: src/sys/dev: ccd.c Log Message: - only create ccd's when we ask them to be created. - keep track of the number of active ccd's so that we don't modunload and crash - fix formatting. - don't attach 4, the argument is not used. To generate a diff of this commit: cvs rdiff -u -r1.157 -r1.158 src/sys/dev/ccd.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/dev/ccd.c diff -u src/sys/dev/ccd.c:1.157 src/sys/dev/ccd.c:1.158 --- src/sys/dev/ccd.c:1.157 Tue Dec 30 14:11:05 2014 +++ src/sys/dev/ccd.c Tue Dec 30 15:29:42 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: ccd.c,v 1.157 2014/12/30 19:11:05 mlelstv Exp $ */ +/* $NetBSD: ccd.c,v 1.158 2014/12/30 20:29:42 christos Exp $ */ /*- * Copyright (c) 1996, 1997, 1998, 1999, 2007, 2009 The NetBSD Foundation, Inc. @@ -88,7 +88,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: ccd.c,v 1.157 2014/12/30 19:11:05 mlelstv Exp $"); +__KERNEL_RCSID(0, "$NetBSD: ccd.c,v 1.158 2014/12/30 20:29:42 christos Exp $"); #if defined(_KERNEL_OPT) #include "opt_compat_netbsd.h" @@ -216,6 +216,7 @@ static void printiinfo(struct ccdiinfo * static LIST_HEAD(, ccd_softc) ccds = LIST_HEAD_INITIALIZER(ccds); static kmutex_t ccd_lock; +static size_t ccd_nactive = 0; static struct ccd_softc * ccdcreate(int unit) { @@ -248,7 +249,7 @@ ccddestroy(struct ccd_softc *sc) { } static struct ccd_softc * -ccdget(int unit) { +ccdget(int unit, int make) { struct ccd_softc *sc; if (unit < 0) { #ifdef DIAGNOSTIC @@ -264,10 +265,13 @@ ccdget(int unit) { } } mutex_exit(&ccd_lock); + if (!make) + return NULL; if ((sc = ccdcreate(unit)) == NULL) return NULL; mutex_enter(&ccd_lock); LIST_INSERT_HEAD(&ccds, sc, sc_link); + ccd_nactive++; mutex_exit(&ccd_lock); return sc; } @@ -276,6 +280,7 @@ static void ccdput(struct ccd_softc *sc) { mutex_enter(&ccd_lock); LIST_REMOVE(sc, sc_link); + ccd_nactive--; mutex_exit(&ccd_lock); ccddestroy(sc); } @@ -434,11 +439,11 @@ ccdinit(struct ccd_softc *cs, char **cpa dg = &cs->sc_dkdev.dk_geom; memset(dg, 0, sizeof(*dg)); - dg->dg_secperunit = cs->sc_size; - dg->dg_secsize = ccg->ccg_secsize; - dg->dg_nsectors = ccg->ccg_nsectors; - dg->dg_ntracks = ccg->ccg_ntracks; - dg->dg_ncylinders = ccg->ccg_ncylinders; + dg->dg_secperunit = cs->sc_size; + dg->dg_secsize = ccg->ccg_secsize; + dg->dg_nsectors = ccg->ccg_nsectors; + dg->dg_ntracks = ccg->ccg_ntracks; + dg->dg_ncylinders = ccg->ccg_ncylinders; if (cs->sc_ileave > 0) aprint_normal("%s: Interleaving %d component%s " @@ -601,7 +606,7 @@ ccdopen(dev_t dev, int flags, int fmt, s if (ccddebug & CCDB_FOLLOW) printf("ccdopen(0x%"PRIx64", 0x%x)\n", dev, flags); #endif - if ((cs = ccdget(unit)) == NULL) + if ((cs = ccdget(unit, 1)) == NULL) return ENXIO; mutex_enter(&cs->sc_dvlock); @@ -662,7 +667,7 @@ ccdclose(dev_t dev, int flags, int fmt, printf("ccdclose(0x%"PRIx64", 0x%x)\n", dev, flags); #endif - if ((cs = ccdget(unit)) == NULL) + if ((cs = ccdget(unit, 0)) == NULL) return ENXIO; mutex_enter(&cs->sc_dvlock); @@ -745,7 +750,7 @@ ccdstrategy(struct buf *bp) { int unit = ccdunit(bp->b_dev); struct ccd_softc *cs; - if ((cs = ccdget(unit)) == NULL) + if ((cs = ccdget(unit, 0)) == NULL) return; /* Must be open or reading label. */ @@ -1031,7 +1036,7 @@ ccdread(dev_t dev, struct uio *uio, int if (ccddebug & CCDB_FOLLOW) printf("ccdread(0x%"PRIx64", %p)\n", dev, uio); #endif - if ((cs = ccdget(unit)) == NULL) + if ((cs = ccdget(unit, 0)) == NULL) return 0; /* Unlocked advisory check, ccdstrategy check is synchronous. */ @@ -1052,7 +1057,7 @@ ccdwrite(dev_t dev, struct uio *uio, int if (ccddebug & CCDB_FOLLOW) printf("ccdwrite(0x%"PRIx64", %p)\n", dev, uio); #endif - if ((cs = ccdget(unit)) == NULL) + if ((cs = ccdget(unit, 0)) == NULL) return ENOENT; /* Unlocked advisory check, ccdstrategy check is synchronous. */ @@ -1067,7 +1072,7 @@ ccdioctl(dev_t dev, u_long cmd, void *da { int unit = ccdunit(dev); int i, j, lookedup = 0, error = 0; - int part, pmask; + int part, pmask, make; struct ccd_softc *cs; struct ccd_ioctl *ccio = (struct ccd_ioctl *)data; kauth_cred_t uc; @@ -1078,7 +1083,19 @@ ccdioctl(dev_t dev, u_long cmd, void *da struct disklabel newlabel; #endif - if ((cs = ccdget(unit)) == NULL) + switch (cmd) { +#if defined(COMPAT_60) && !defined(_LP64) + case CCDIOCSET_60: +#endif + case CCDIOCSET: + make = 1; + break; + default: + make = 0; + break; + } + + if ((cs = ccdget(unit, make)) == NULL) return ENOENT; uc = kauth_cred_get(); @@ -1506,7 +1523,7 @@ ccdsize(dev_t dev) int part, unit, omask, size; unit = ccdunit(dev); - if ((cs = ccdget(unit)) == NULL) + if ((cs = ccdget(unit, 0)) == NULL) return -1; if ((cs->sc_flags & CCDF_INITED) == 0) @@ -1578,7 +1595,7 @@ ccdgetdisklabel(dev_t dev) struct disklabel *lp; struct cpu_disklabel *clp; - if ((cs = ccdget(unit)) == NULL) + if ((cs = ccdget(unit, 0)) == NULL) return; lp = cs->sc_dkdev.dk_label; clp = cs->sc_dkdev.dk_cpulabel; @@ -1689,16 +1706,21 @@ ccd_modcmd(modcmd_t cmd, void *arg) switch (cmd) { case MODULE_CMD_INIT: #ifdef _MODULE - ccdattach(4); + ccdattach(0); - return devsw_attach("ccd", &ccd_bdevsw, &bmajor, + error = devsw_attach("ccd", &ccd_bdevsw, &bmajor, &ccd_cdevsw, &cmajor); #endif break; case MODULE_CMD_FINI: #ifdef _MODULE - return devsw_detach(&ccd_bdevsw, &ccd_cdevsw); + mutex_enter(&ccd_lock); + if (ccd_nactive) + error = EBUSY; + else + error = devsw_detach(&ccd_bdevsw, &ccd_cdevsw); + mutex_exit(&ccd_lock); #endif break;