kern_conf.c revision 46775
1/*- 2 * Parts Copyright (c) 1995 Terrence R. Lambert 3 * Copyright (c) 1995 Julian R. Elischer 4 * 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: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 3. All advertising materials mentioning features or use of this software 15 * must display the following acknowledgement: 16 * This product includes software developed by Terrence R. Lambert. 17 * 4. The name Terrence R. Lambert may not be used to endorse or promote 18 * products derived from this software without specific prior written 19 * permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY Julian R. Elischer ``AS IS'' AND ANY 22 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 24 * ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE 25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 31 * SUCH DAMAGE. 32 * 33 * $Id: kern_conf.c,v 1.34 1999/05/09 08:10:17 peter Exp $ 34 */ 35 36#include <sys/param.h> 37#include <sys/systm.h> 38#include <sys/module.h> 39#include <sys/conf.h> 40#include <sys/vnode.h> 41 42#define NUMCDEV 256 43#define cdevsw_ALLOCSTART (NUMCDEV/2) 44 45struct cdevsw *cdevsw[NUMCDEV]; 46int nchrdev = NUMCDEV; 47 48int bmaj2cmaj[NUMCDEV]; 49int nblkdev = NUMCDEV; 50 51/* 52 * Routine to convert from character to block device number. 53 * 54 * A minimal stub routine can always return NODEV. 55 */ 56dev_t 57chrtoblk(dev_t dev) 58{ 59 struct cdevsw *cd; 60 61 if((cd = devsw(dev)) != NULL) { 62 if (cd->d_bmaj != -1) 63 return(makedev(cd->d_bmaj,minor(dev))); 64 } 65 return(NODEV); 66} 67 68int 69cdevsw_add(dev_t *descrip, 70 struct cdevsw *newentry, 71 struct cdevsw **oldentry) 72{ 73 int i ; 74 75 if ( *descrip == NODEV) { /* auto (0 is valid) */ 76 /* 77 * Search the table looking for a slot... 78 */ 79 for (i = cdevsw_ALLOCSTART; i < nchrdev; i++) 80 if (cdevsw[i] == NULL) 81 break; /* found one! */ 82 /* out of allocable slots? */ 83 if (i >= nchrdev) { 84 return ENFILE; 85 } 86 } else { /* assign */ 87 i = major(*descrip); 88 if (i < 0 || i >= nchrdev) { 89 return EINVAL; 90 } 91 } 92 93 /* maybe save old */ 94 if (oldentry) { 95 *oldentry = cdevsw[i]; 96 } 97 if (newentry) { 98 newentry->d_bmaj = -1; 99 newentry->d_maj = i; 100 } 101 /* replace with new */ 102 cdevsw[i] = newentry; 103 104 /* done! let them know where we put it */ 105 *descrip = makedev(i,0); 106 return 0; 107} 108 109void 110cdevsw_add_generic(int bmaj, int cmaj, struct cdevsw *devsw) 111{ 112 dev_t dev; 113 114 dev = makedev(cmaj, 0); 115 cdevsw_add(&dev, devsw, NULL); 116 cdevsw[cmaj]->d_bmaj = bmaj; 117 bmaj2cmaj[bmaj] = cmaj; 118} 119 120int 121devsw_module_handler(module_t mod, int what, void* arg) 122{ 123 struct devsw_module_data* data = (struct devsw_module_data*) arg; 124 int error; 125 126 switch (what) { 127 case MOD_LOAD: 128 error = cdevsw_add(&data->cdev, data->cdevsw, NULL); 129 if (!error && data->cdevsw->d_strategy != nostrategy) { 130 if (data->bdev == NODEV) 131 data->bdev = data->cdev; 132 bmaj2cmaj[major(data->bdev)] = major(data->cdev); 133 } 134 if (!error && data->chainevh) 135 error = data->chainevh(mod, what, data->chainarg); 136 return error; 137 138 case MOD_UNLOAD: 139 if (data->chainevh) { 140 error = data->chainevh(mod, what, data->chainarg); 141 if (error) 142 return error; 143 } 144 if (data->cdevsw->d_strategy != nostrategy) 145 bmaj2cmaj[major(data->bdev)] = 0; 146 error = cdevsw_add(&data->cdev, NULL, NULL); 147 return error; 148 } 149 150 if (data->chainevh) 151 return data->chainevh(mod, what, data->chainarg); 152 else 153 return 0; 154} 155