Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys Add support for multiple cfdata tables to the internals ...
details: https://anonhg.NetBSD.org/src/rev/91768b309d9b
branches: trunk
changeset: 536895:91768b309d9b
user: thorpej <thorpej%NetBSD.org@localhost>
date: Mon Sep 23 23:16:06 2002 +0000
description:
Add support for multiple cfdata tables to the internals of the
autoconfiguration machinery, derived from PR #2112.
More work is left to do, including revamping how matches against
a candidate parent are done.
diffstat:
sys/kern/subr_autoconf.c | 85 +++++++++++++++++++++++++++++++----------------
sys/sys/device.h | 15 +++++++-
2 files changed, 69 insertions(+), 31 deletions(-)
diffs (210 lines):
diff -r 2b59b34790b6 -r 91768b309d9b sys/kern/subr_autoconf.c
--- a/sys/kern/subr_autoconf.c Mon Sep 23 21:35:42 2002 +0000
+++ b/sys/kern/subr_autoconf.c Mon Sep 23 23:16:06 2002 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: subr_autoconf.c,v 1.64 2002/07/10 19:04:09 drochner Exp $ */
+/* $NetBSD: subr_autoconf.c,v 1.65 2002/09/23 23:16:06 thorpej Exp $ */
/*
* Copyright (c) 1996, 2000 Christopher G. Demetriou
@@ -81,7 +81,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: subr_autoconf.c,v 1.64 2002/07/10 19:04:09 drochner Exp $");
+__KERNEL_RCSID(0, "$NetBSD: subr_autoconf.c,v 1.65 2002/09/23 23:16:06 thorpej Exp $");
#include "opt_ddb.h"
@@ -111,6 +111,13 @@
extern struct cfdata cfdata[];
extern short cfroots[];
+/*
+ * List of cfdata tables. We always have one such list -- the one
+ * built statically when the kernel was configured.
+ */
+struct cftablelist allcftables;
+static struct cftable initcftable;
+
#define ROOT ((struct device *)NULL)
struct matchinfo {
@@ -153,6 +160,11 @@
configure(void)
{
+ TAILQ_INIT(&allcftables);
+
+ initcftable.ct_cfdata = cfdata;
+ TAILQ_INSERT_TAIL(&allcftables, &initcftable, ct_list);
+
TAILQ_INIT(&deferred_config_queue);
TAILQ_INIT(&interrupt_config_queue);
TAILQ_INIT(&alldevs);
@@ -223,6 +235,7 @@
struct cfdata *
config_search(cfmatch_t fn, struct device *parent, void *aux)
{
+ struct cftable *ct;
struct cfdata *cf;
short *p;
struct matchinfo m;
@@ -232,19 +245,23 @@
m.aux = aux;
m.match = NULL;
m.pri = 0;
- for (cf = cfdata; cf->cf_driver; cf++) {
- /*
- * Skip cf if no longer eligible, otherwise scan through
- * parents for one matching `parent', and try match function.
- */
- if (cf->cf_fstate == FSTATE_FOUND)
- continue;
- if (cf->cf_fstate == FSTATE_DNOTFOUND ||
- cf->cf_fstate == FSTATE_DSTAR)
- continue;
- for (p = cf->cf_parents; *p >= 0; p++)
- if (parent->dv_cfdata == &cfdata[*p])
- mapply(&m, cf);
+
+ TAILQ_FOREACH(ct, &allcftables, ct_list) {
+ for (cf = ct->ct_cfdata; cf->cf_driver; cf++) {
+ /*
+ * Skip cf if no longer eligible, otherwise scan
+ * through parents for one matching `parent', and
+ * try match function.
+ */
+ if (cf->cf_fstate == FSTATE_FOUND)
+ continue;
+ if (cf->cf_fstate == FSTATE_DNOTFOUND ||
+ cf->cf_fstate == FSTATE_DSTAR)
+ continue;
+ for (p = cf->cf_parents; *p >= 0; p++)
+ if (parent->dv_cfdata == &(ct->ct_cfdata)[*p])
+ mapply(&m, cf);
+ }
}
return (m.match);
}
@@ -252,6 +269,8 @@
/*
* Find the given root device.
* This is much like config_search, but there is no parent.
+ * Don't bother with multiple cfdata tables; the root node
+ * must always be in the initial table.
*/
struct cfdata *
config_rootsearch(cfmatch_t fn, const char *rootname, void *aux)
@@ -373,6 +392,7 @@
cfprint_t print)
{
struct device *dev;
+ struct cftable *ct;
struct cfdriver *cd;
struct cfattach *ca;
size_t lname, lunit;
@@ -448,15 +468,19 @@
#ifdef __BROKEN_CONFIG_UNIT_USAGE
/* bump the unit number on all starred cfdata for this device. */
#endif /* __BROKEN_CONFIG_UNIT_USAGE */
- for (cf = cfdata; cf->cf_driver; cf++)
- if (cf->cf_driver == cd && cf->cf_unit == dev->dv_unit) {
- if (cf->cf_fstate == FSTATE_NOTFOUND)
- cf->cf_fstate = FSTATE_FOUND;
+ TAILQ_FOREACH(ct, &allcftables, ct_list) {
+ for (cf = ct->ct_cfdata; cf->cf_driver; cf++) {
+ if (cf->cf_driver == cd &&
+ cf->cf_unit == dev->dv_unit) {
+ if (cf->cf_fstate == FSTATE_NOTFOUND)
+ cf->cf_fstate = FSTATE_FOUND;
#ifdef __BROKEN_CONFIG_UNIT_USAGE
- if (cf->cf_fstate == FSTATE_STAR)
- cf->cf_unit++;
+ if (cf->cf_fstate == FSTATE_STAR)
+ cf->cf_unit++;
#endif /* __BROKEN_CONFIG_UNIT_USAGE */
+ }
}
+ }
#ifdef __HAVE_DEVICE_REGISTER
device_register(dev, aux);
#endif
@@ -477,6 +501,7 @@
int
config_detach(struct device *dev, int flags)
{
+ struct cftable *ct;
struct cfdata *cf;
struct cfattach *ca;
struct cfdriver *cd;
@@ -551,16 +576,18 @@
* being detached had the last assigned unit number.
*/
#endif /* __BROKEN_CONFIG_UNIT_USAGE */
- for (cf = cfdata; cf->cf_driver; cf++) {
- if (cf->cf_driver == cd) {
- if (cf->cf_fstate == FSTATE_FOUND &&
- cf->cf_unit == dev->dv_unit)
- cf->cf_fstate = FSTATE_NOTFOUND;
+ TAILQ_FOREACH(ct, &allcftables, ct_list) {
+ for (cf = ct->ct_cfdata; cf->cf_driver; cf++) {
+ if (cf->cf_driver == cd) {
+ if (cf->cf_fstate == FSTATE_FOUND &&
+ cf->cf_unit == dev->dv_unit)
+ cf->cf_fstate = FSTATE_NOTFOUND;
#ifdef __BROKEN_CONFIG_UNIT_USAGE
- if (cf->cf_fstate == FSTATE_STAR &&
- cf->cf_unit == dev->dv_unit + 1)
- cf->cf_unit--;
+ if (cf->cf_fstate == FSTATE_STAR &&
+ cf->cf_unit == dev->dv_unit + 1)
+ cf->cf_unit--;
#endif /* __BROKEN_CONFIG_UNIT_USAGE */
+ }
}
}
diff -r 2b59b34790b6 -r 91768b309d9b sys/sys/device.h
--- a/sys/sys/device.h Mon Sep 23 21:35:42 2002 +0000
+++ b/sys/sys/device.h Mon Sep 23 23:16:06 2002 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: device.h,v 1.49 2002/02/15 11:18:26 simonb Exp $ */
+/* $NetBSD: device.h,v 1.50 2002/09/23 23:16:07 thorpej Exp $ */
/*
* Copyright (c) 1996, 2000 Christopher G. Demetriou
@@ -180,6 +180,16 @@
#define FSTATE_DSTAR 3 /* has not been found, and disabled */
#define FSTATE_DNOTFOUND 4 /* duplicate, and disabled */
+/*
+ * Multiple configuration data tables may be maintained. This structure
+ * provides the linkage.
+ */
+struct cftable {
+ struct cfdata *ct_cfdata; /* pointer to cfdata table */
+ TAILQ_ENTRY(cftable) ct_list; /* list linkage */
+};
+TAILQ_HEAD(cftablelist, cftable);
+
typedef int (*cfmatch_t)(struct device *, struct cfdata *, void *);
/*
@@ -211,7 +221,7 @@
struct cfdriver {
void **cd_devs; /* devices found */
- char *cd_name; /* device name */
+ const char *cd_name; /* device name */
enum devclass cd_class; /* device classification */
int cd_ndevs; /* size of cd_devs array */
};
@@ -239,6 +249,7 @@
extern struct devicelist alldevs; /* list of all devices */
extern struct evcntlist allevents; /* list of all event counters */
+extern struct cftablelist allcftables; /* list of all cfdata tables */
extern struct device *booted_device; /* the device we booted from */
extern __volatile int config_pending; /* semaphore for mountroot */
Home |
Main Index |
Thread Index |
Old Index