1 /* $NetBSD: subr_autoconf.c,v 1.291 2021/12/31 14:19:57 riastradh Exp $ */ 2 3 /* 4 * Copyright (c) 1996, 2000 Christopher G. Demetriou 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. All advertising materials mentioning features or use of this software 16 * must display the following acknowledgement: 17 * This product includes software developed for the 18 * NetBSD Project. See http://www.NetBSD.org/ for 19 * information about NetBSD. 20 * 4. The name of the author may not be used to endorse or promote products 21 * derived from this software without specific prior written permission. 22 * 23 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 24 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 25 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 26 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 27 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 28 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 29 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 30 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 31 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 32 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 33 * 34 * --(license Id: LICENSE.proto,v 1.1 2000/06/13 21:40:26 cgd Exp )-- 35 */ 36 37 /* 38 * Copyright (c) 1992, 1993 39 * The Regents of the University of California. All rights reserved. 40 * 41 * This software was developed by the Computer Systems Engineering group 42 * at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and 43 * contributed to Berkeley. 44 * 45 * All advertising materials mentioning features or use of this software 46 * must display the following acknowledgement: 47 * This product includes software developed by the University of 48 * California, Lawrence Berkeley Laboratories. 49 * 50 * Redistribution and use in source and binary forms, with or without 51 * modification, are permitted provided that the following conditions 52 * are met: 53 * 1. Redistributions of source code must retain the above copyright 54 * notice, this list of conditions and the following disclaimer. 55 * 2. Redistributions in binary form must reproduce the above copyright 56 * notice, this list of conditions and the following disclaimer in the 57 * documentation and/or other materials provided with the distribution. 58 * 3. Neither the name of the University nor the names of its contributors 59 * may be used to endorse or promote products derived from this software 60 * without specific prior written permission. 61 * 62 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 63 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 64 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 65 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 66 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 67 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 68 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 69 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 70 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 71 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 72 * SUCH DAMAGE. 73 * 74 * from: Header: subr_autoconf.c,v 1.12 93/02/01 19:31:48 torek Exp (LBL) 75 * 76 * @(#)subr_autoconf.c 8.3 (Berkeley) 5/17/94 77 */ 78 79 #include <sys/cdefs.h> 80 __KERNEL_RCSID(0, "$NetBSD: subr_autoconf.c,v 1.291 2021/12/31 14:19:57 riastradh Exp $"); 81 82 #ifdef _KERNEL_OPT 83 #include "opt_ddb.h" 84 #include "drvctl.h" 85 #endif 86 87 #include <sys/param.h> 88 #include <sys/device.h> 89 #include <sys/disklabel.h> 90 #include <sys/conf.h> 91 #include <sys/kauth.h> 92 #include <sys/kmem.h> 93 #include <sys/systm.h> 94 #include <sys/kernel.h> 95 #include <sys/errno.h> 96 #include <sys/proc.h> 97 #include <sys/reboot.h> 98 #include <sys/kthread.h> 99 #include <sys/buf.h> 100 #include <sys/dirent.h> 101 #include <sys/mount.h> 102 #include <sys/namei.h> 103 #include <sys/unistd.h> 104 #include <sys/fcntl.h> 105 #include <sys/lockf.h> 106 #include <sys/callout.h> 107 #include <sys/devmon.h> 108 #include <sys/cpu.h> 109 #include <sys/sysctl.h> 110 #include <sys/stdarg.h> 111 112 #include <sys/disk.h> 113 114 #include <sys/rndsource.h> 115 116 #include <machine/limits.h> 117 118 /* 119 * Autoconfiguration subroutines. 120 */ 121 122 /* 123 * Device autoconfiguration timings are mixed into the entropy pool. 124 */ 125 static krndsource_t rnd_autoconf_source; 126 127 /* 128 * ioconf.c exports exactly two names: cfdata and cfroots. All system 129 * devices and drivers are found via these tables. 130 */ 131 extern struct cfdata cfdata[]; 132 extern const short cfroots[]; 133 134 /* 135 * List of all cfdriver structures. We use this to detect duplicates 136 * when other cfdrivers are loaded. 137 */ 138 struct cfdriverlist allcfdrivers = LIST_HEAD_INITIALIZER(&allcfdrivers); 139 extern struct cfdriver * const cfdriver_list_initial[]; 140 141 /* 142 * Initial list of cfattach's. 143 */ 144 extern const struct cfattachinit cfattachinit[]; 145 146 /* 147 * List of cfdata tables. We always have one such list -- the one 148 * built statically when the kernel was configured. 149 */ 150 struct cftablelist allcftables = TAILQ_HEAD_INITIALIZER(allcftables); 151 static struct cftable initcftable; 152 153 #define ROOT ((device_t)NULL) 154 155 struct matchinfo { 156 cfsubmatch_t fn; 157 device_t parent; 158 const int *locs; 159 void *aux; 160 struct cfdata *match; 161 int pri; 162 }; 163 164 struct alldevs_foray { 165 int af_s; 166 struct devicelist af_garbage; 167 }; 168 169 /* 170 * Internal version of the cfargs structure; all versions are 171 * canonicalized to this. 172 */ 173 struct cfargs_internal { 174 union { 175 cfsubmatch_t submatch;/* submatch function (direct config) */ 176 cfsearch_t search; /* search function (indirect config) */ 177 }; 178 const char * iattr; /* interface attribute */ 179 const int * locators; /* locators array */ 180 devhandle_t devhandle; /* devhandle_t (by value) */ 181 }; 182 183 static char *number(char *, int); 184 static void mapply(struct matchinfo *, cfdata_t); 185 static void config_devdelete(device_t); 186 static void config_devunlink(device_t, struct devicelist *); 187 static void config_makeroom(int, struct cfdriver *); 188 static void config_devlink(device_t); 189 static void config_alldevs_enter(struct alldevs_foray *); 190 static void config_alldevs_exit(struct alldevs_foray *); 191 static void config_add_attrib_dict(device_t); 192 static device_t config_attach_internal(device_t, cfdata_t, void *, 193 cfprint_t, const struct cfargs_internal *); 194 195 static void config_collect_garbage(struct devicelist *); 196 static void config_dump_garbage(struct devicelist *); 197 198 static void pmflock_debug(device_t, const char *, int); 199 200 static device_t deviter_next1(deviter_t *); 201 static void deviter_reinit(deviter_t *); 202 203 struct deferred_config { 204 TAILQ_ENTRY(deferred_config) dc_queue; 205 device_t dc_dev; 206 void (*dc_func)(device_t); 207 }; 208 209 TAILQ_HEAD(deferred_config_head, deferred_config); 210 211 static struct deferred_config_head deferred_config_queue = 212 TAILQ_HEAD_INITIALIZER(deferred_config_queue); 213 static struct deferred_config_head interrupt_config_queue = 214 TAILQ_HEAD_INITIALIZER(interrupt_config_queue); 215 static int interrupt_config_threads = 8; 216 static struct deferred_config_head mountroot_config_queue = 217 TAILQ_HEAD_INITIALIZER(mountroot_config_queue); 218 static int mountroot_config_threads = 2; 219 static lwp_t **mountroot_config_lwpids; 220 static size_t mountroot_config_lwpids_size; 221 bool root_is_mounted = false; 222 223 static void config_process_deferred(struct deferred_config_head *, device_t); 224 225 /* Hooks to finalize configuration once all real devices have been found. */ 226 struct finalize_hook { 227 TAILQ_ENTRY(finalize_hook) f_list; 228 int (*f_func)(device_t); 229 device_t f_dev; 230 }; 231 static TAILQ_HEAD(, finalize_hook) config_finalize_list = 232 TAILQ_HEAD_INITIALIZER(config_finalize_list); 233 static int config_finalize_done; 234 235 /* list of all devices */ 236 static struct devicelist alldevs = TAILQ_HEAD_INITIALIZER(alldevs); 237 static kmutex_t alldevs_lock __cacheline_aligned; 238 static devgen_t alldevs_gen = 1; 239 static int alldevs_nread = 0; 240 static int alldevs_nwrite = 0; 241 static bool alldevs_garbage = false; 242 243 static struct devicelist config_pending = 244 TAILQ_HEAD_INITIALIZER(config_pending); 245 static kmutex_t config_misc_lock; 246 static kcondvar_t config_misc_cv; 247 248 static bool detachall = false; 249 250 #define STREQ(s1, s2) \ 251 (*(s1) == *(s2) && strcmp((s1), (s2)) == 0) 252 253 static bool config_initialized = false; /* config_init() has been called. */ 254 255 static int config_do_twiddle; 256 static callout_t config_twiddle_ch; 257 258 static void sysctl_detach_setup(struct sysctllog **); 259 260 int no_devmon_insert(const char *, prop_dictionary_t); 261 int (*devmon_insert_vec)(const char *, prop_dictionary_t) = no_devmon_insert; 262 263 typedef int (*cfdriver_fn)(struct cfdriver *); 264 static int 265 frob_cfdrivervec(struct cfdriver * const *cfdriverv, 266 cfdriver_fn drv_do, cfdriver_fn drv_undo, 267 const char *style, bool dopanic) 268 { 269 void (*pr)(const char *, ...) __printflike(1, 2) = 270 dopanic ? panic : printf; 271 int i, error = 0, e2 __diagused; 272 273 for (i = 0; cfdriverv[i] != NULL; i++) { 274 if ((error = drv_do(cfdriverv[i])) != 0) { 275 pr("configure: `%s' driver %s failed: %d", 276 cfdriverv[i]->cd_name, style, error); 277 goto bad; 278 } 279 } 280 281 KASSERT(error == 0); 282 return 0; 283 284 bad: 285 printf("\n"); 286 for (i--; i >= 0; i--) { 287 e2 = drv_undo(cfdriverv[i]); 288 KASSERT(e2 == 0); 289 } 290 291 return error; 292 } 293 294 typedef int (*cfattach_fn)(const char *, struct cfattach *); 295 static int 296 frob_cfattachvec(const struct cfattachinit *cfattachv, 297 cfattach_fn att_do, cfattach_fn att_undo, 298 const char *style, bool dopanic) 299 { 300 const struct cfattachinit *cfai = NULL; 301 void (*pr)(const char *, ...) __printflike(1, 2) = 302 dopanic ? panic : printf; 303 int j = 0, error = 0, e2 __diagused; 304 305 for (cfai = &cfattachv[0]; cfai->cfai_name != NULL; cfai++) { 306 for (j = 0; cfai->cfai_list[j] != NULL; j++) { 307 if ((error = att_do(cfai->cfai_name, 308 cfai->cfai_list[j])) != 0) { 309 pr("configure: attachment `%s' " 310 "of `%s' driver %s failed: %d", 311 cfai->cfai_list[j]->ca_name, 312 cfai->cfai_name, style, error); 313 goto bad; 314 } 315 } 316 } 317 318 KASSERT(error == 0); 319 return 0; 320 321 bad: 322 /* 323 * Rollback in reverse order. dunno if super-important, but 324 * do that anyway. Although the code looks a little like 325 * someone did a little integration (in the math sense). 326 */ 327 printf("\n"); 328 if (cfai) { 329 bool last; 330 331 for (last = false; last == false; ) { 332 if (cfai == &cfattachv[0]) 333 last = true; 334 for (j--; j >= 0; j--) { 335 e2 = att_undo(cfai->cfai_name, 336 cfai->cfai_list[j]); 337 KASSERT(e2 == 0); 338 } 339 if (!last) { 340 cfai--; 341 for (j = 0; cfai->cfai_list[j] != NULL; j++) 342 ; 343 } 344 } 345 } 346 347 return error; 348 } 349 350 /* 351 * Initialize the autoconfiguration data structures. Normally this 352 * is done by configure(), but some platforms need to do this very 353 * early (to e.g. initialize the console). 354 */ 355 void 356 config_init(void) 357 { 358 359 KASSERT(config_initialized == false); 360 361 mutex_init(&alldevs_lock, MUTEX_DEFAULT, IPL_VM); 362 363 mutex_init(&config_misc_lock, MUTEX_DEFAULT, IPL_NONE); 364 cv_init(&config_misc_cv, "cfgmisc"); 365 366 callout_init(&config_twiddle_ch, CALLOUT_MPSAFE); 367 368 frob_cfdrivervec(cfdriver_list_initial, 369 config_cfdriver_attach, NULL, "bootstrap", true); 370 frob_cfattachvec(cfattachinit, 371 config_cfattach_attach, NULL, "bootstrap", true); 372 373 initcftable.ct_cfdata = cfdata; 374 TAILQ_INSERT_TAIL(&allcftables, &initcftable, ct_list); 375 376 rnd_attach_source(&rnd_autoconf_source, "autoconf", RND_TYPE_UNKNOWN, 377 RND_FLAG_COLLECT_TIME); 378 379 config_initialized = true; 380 } 381 382 /* 383 * Init or fini drivers and attachments. Either all or none 384 * are processed (via rollback). It would be nice if this were 385 * atomic to outside consumers, but with the current state of 386 * locking ... 387 */ 388 int 389 config_init_component(struct cfdriver * const *cfdriverv, 390 const struct cfattachinit *cfattachv, struct cfdata *cfdatav) 391 { 392 int error; 393 394 KERNEL_LOCK(1, NULL); 395 396 if ((error = frob_cfdrivervec(cfdriverv, 397 config_cfdriver_attach, config_cfdriver_detach, "init", false))!= 0) 398 goto out; 399 if ((error = frob_cfattachvec(cfattachv, 400 config_cfattach_attach, config_cfattach_detach, 401 "init", false)) != 0) { 402 frob_cfdrivervec(cfdriverv, 403 config_cfdriver_detach, NULL, "init rollback", true); 404 goto out; 405 } 406 if ((error = config_cfdata_attach(cfdatav, 1)) != 0) { 407 frob_cfattachvec(cfattachv, 408 config_cfattach_detach, NULL, "init rollback", true); 409 frob_cfdrivervec(cfdriverv, 410 config_cfdriver_detach, NULL, "init rollback", true); 411 goto out; 412 } 413 414 /* Success! */ 415 error = 0; 416 417 out: KERNEL_UNLOCK_ONE(NULL); 418 return error; 419 } 420 421 int 422 config_fini_component(struct cfdriver * const *cfdriverv, 423 const struct cfattachinit *cfattachv, struct cfdata *cfdatav) 424 { 425 int error; 426 427 KERNEL_LOCK(1, NULL); 428 429 if ((error = config_cfdata_detach(cfdatav)) != 0) 430 goto out; 431 if ((error = frob_cfattachvec(cfattachv, 432 config_cfattach_detach, config_cfattach_attach, 433 "fini", false)) != 0) { 434 if (config_cfdata_attach(cfdatav, 0) != 0) 435 panic("config_cfdata fini rollback failed"); 436 goto out; 437 } 438 if ((error = frob_cfdrivervec(cfdriverv, 439 config_cfdriver_detach, config_cfdriver_attach, 440 "fini", false)) != 0) { 441 frob_cfattachvec(cfattachv, 442 config_cfattach_attach, NULL, "fini rollback", true); 443 if (config_cfdata_attach(cfdatav, 0) != 0) 444 panic("config_cfdata fini rollback failed"); 445 goto out; 446 } 447 448 /* Success! */ 449 error = 0; 450 451 out: KERNEL_UNLOCK_ONE(NULL); 452 return error; 453 } 454 455 void 456 config_init_mi(void) 457 { 458 459 if (!config_initialized) 460 config_init(); 461 462 sysctl_detach_setup(NULL); 463 } 464 465 void 466 config_deferred(device_t dev) 467 { 468 469 KASSERT(KERNEL_LOCKED_P()); 470 471 config_process_deferred(&deferred_config_queue, dev); 472 config_process_deferred(&interrupt_config_queue, dev); 473 config_process_deferred(&mountroot_config_queue, dev); 474 } 475 476 static void 477 config_interrupts_thread(void *cookie) 478 { 479 struct deferred_config *dc; 480 device_t dev; 481 482 mutex_enter(&config_misc_lock); 483 while ((dc = TAILQ_FIRST(&interrupt_config_queue)) != NULL) { 484 TAILQ_REMOVE(&interrupt_config_queue, dc, dc_queue); 485 mutex_exit(&config_misc_lock); 486 487 dev = dc->dc_dev; 488 (*dc->dc_func)(dev); 489 if (!device_pmf_is_registered(dev)) 490 aprint_debug_dev(dev, 491 "WARNING: power management not supported\n"); 492 config_pending_decr(dev); 493 kmem_free(dc, sizeof(*dc)); 494 495 mutex_enter(&config_misc_lock); 496 } 497 mutex_exit(&config_misc_lock); 498 499 kthread_exit(0); 500 } 501 502 void 503 config_create_interruptthreads(void) 504 { 505 int i; 506 507 for (i = 0; i < interrupt_config_threads; i++) { 508 (void)kthread_create(PRI_NONE, 0/*XXXSMP */, NULL, 509 config_interrupts_thread, NULL, NULL, "configintr"); 510 } 511 } 512 513 static void 514 config_mountroot_thread(void *cookie) 515 { 516 struct deferred_config *dc; 517 518 mutex_enter(&config_misc_lock); 519 while ((dc = TAILQ_FIRST(&mountroot_config_queue)) != NULL) { 520 TAILQ_REMOVE(&mountroot_config_queue, dc, dc_queue); 521 mutex_exit(&config_misc_lock); 522 523 (*dc->dc_func)(dc->dc_dev); 524 kmem_free(dc, sizeof(*dc)); 525 526 mutex_enter(&config_misc_lock); 527 } 528 mutex_exit(&config_misc_lock); 529 530 kthread_exit(0); 531 } 532 533 void 534 config_create_mountrootthreads(void) 535 { 536 int i; 537 538 if (!root_is_mounted) 539 root_is_mounted = true; 540 541 mountroot_config_lwpids_size = sizeof(mountroot_config_lwpids) * 542 mountroot_config_threads; 543 mountroot_config_lwpids = kmem_alloc(mountroot_config_lwpids_size, 544 KM_NOSLEEP); 545 KASSERT(mountroot_config_lwpids); 546 for (i = 0; i < mountroot_config_threads; i++) { 547 mountroot_config_lwpids[i] = 0; 548 (void)kthread_create(PRI_NONE, KTHREAD_MUSTJOIN/* XXXSMP */, 549 NULL, config_mountroot_thread, NULL, 550 &mountroot_config_lwpids[i], 551 "configroot"); 552 } 553 } 554 555 void 556 config_finalize_mountroot(void) 557 { 558 int i, error; 559 560 for (i = 0; i < mountroot_config_threads; i++) { 561 if (mountroot_config_lwpids[i] == 0) 562 continue; 563 564 error = kthread_join(mountroot_config_lwpids[i]); 565 if (error) 566 printf("%s: thread %x joined with error %d\n", 567 __func__, i, error); 568 } 569 kmem_free(mountroot_config_lwpids, mountroot_config_lwpids_size); 570 } 571 572 /* 573 * Announce device attach/detach to userland listeners. 574 */ 575 576 int 577 no_devmon_insert(const char *name, prop_dictionary_t p) 578 { 579 580 return ENODEV; 581 } 582 583 static void 584 devmon_report_device(device_t dev, bool isattach) 585 { 586 prop_dictionary_t ev, dict = device_properties(dev); 587 const char *parent; 588 const char *what; 589 const char *where; 590 device_t pdev = device_parent(dev); 591 592 /* If currently no drvctl device, just return */ 593 if (devmon_insert_vec == no_devmon_insert) 594 return; 595 596 ev = prop_dictionary_create(); 597 if (ev == NULL) 598 return; 599 600 what = (isattach ? "device-attach" : "device-detach"); 601 parent = (pdev == NULL ? "root" : device_xname(pdev)); 602 if (prop_dictionary_get_string(dict, "location", &where)) { 603 prop_dictionary_set_string(ev, "location", where); 604 aprint_debug("ev: %s %s at %s in [%s]\n", 605 what, device_xname(dev), parent, where); 606 } 607 if (!prop_dictionary_set_string(ev, "device", device_xname(dev)) || 608 !prop_dictionary_set_string(ev, "parent", parent)) { 609 prop_object_release(ev); 610 return; 611 } 612 613 if ((*devmon_insert_vec)(what, ev) != 0) 614 prop_object_release(ev); 615 } 616 617 /* 618 * Add a cfdriver to the system. 619 */ 620 int 621 config_cfdriver_attach(struct cfdriver *cd) 622 { 623 struct cfdriver *lcd; 624 625 /* Make sure this driver isn't already in the system. */ 626 LIST_FOREACH(lcd, &allcfdrivers, cd_list) { 627 if (STREQ(lcd->cd_name, cd->cd_name)) 628 return EEXIST; 629 } 630 631 LIST_INIT(&cd->cd_attach); 632 LIST_INSERT_HEAD(&allcfdrivers, cd, cd_list); 633 634 return 0; 635 } 636 637 /* 638 * Remove a cfdriver from the system. 639 */ 640 int 641 config_cfdriver_detach(struct cfdriver *cd) 642 { 643 struct alldevs_foray af; 644 int i, rc = 0; 645 646 config_alldevs_enter(&af); 647 /* Make sure there are no active instances. */ 648 for (i = 0; i < cd->cd_ndevs; i++) { 649 if (cd->cd_devs[i] != NULL) { 650 rc = EBUSY; 651 break; 652 } 653 } 654 config_alldevs_exit(&af); 655 656 if (rc != 0) 657 return rc; 658 659 /* ...and no attachments loaded. */ 660 if (LIST_EMPTY(&cd->cd_attach) == 0) 661 return EBUSY; 662 663 LIST_REMOVE(cd, cd_list); 664 665 KASSERT(cd->cd_devs == NULL); 666 667 return 0; 668 } 669 670 /* 671 * Look up a cfdriver by name. 672 */ 673 struct cfdriver * 674 config_cfdriver_lookup(const char *name) 675 { 676 struct cfdriver *cd; 677 678 LIST_FOREACH(cd, &allcfdrivers, cd_list) { 679 if (STREQ(cd->cd_name, name)) 680 return cd; 681 } 682 683 return NULL; 684 } 685 686 /* 687 * Add a cfattach to the specified driver. 688 */ 689 int 690 config_cfattach_attach(const char *driver, struct cfattach *ca) 691 { 692 struct cfattach *lca; 693 struct cfdriver *cd; 694 695 cd = config_cfdriver_lookup(driver); 696 if (cd == NULL) 697 return ESRCH; 698 699 /* Make sure this attachment isn't already on this driver. */ 700 LIST_FOREACH(lca, &cd->cd_attach, ca_list) { 701 if (STREQ(lca->ca_name, ca->ca_name)) 702 return EEXIST; 703 } 704 705 LIST_INSERT_HEAD(&cd->cd_attach, ca, ca_list); 706 707 return 0; 708 } 709 710 /* 711 * Remove a cfattach from the specified driver. 712 */ 713 int 714 config_cfattach_detach(const char *driver, struct cfattach *ca) 715 { 716 struct alldevs_foray af; 717 struct cfdriver *cd; 718 device_t dev; 719 int i, rc = 0; 720 721 cd = config_cfdriver_lookup(driver); 722 if (cd == NULL) 723 return ESRCH; 724 725 config_alldevs_enter(&af); 726 /* Make sure there are no active instances. */ 727 for (i = 0; i < cd->cd_ndevs; i++) { 728 if ((dev = cd->cd_devs[i]) == NULL) 729 continue; 730 if (dev->dv_cfattach == ca) { 731 rc = EBUSY; 732 break; 733 } 734 } 735 config_alldevs_exit(&af); 736 737 if (rc != 0) 738 return rc; 739 740 LIST_REMOVE(ca, ca_list); 741 742 return 0; 743 } 744 745 /* 746 * Look up a cfattach by name. 747 */ 748 static struct cfattach * 749 config_cfattach_lookup_cd(struct cfdriver *cd, const char *atname) 750 { 751 struct cfattach *ca; 752 753 LIST_FOREACH(ca, &cd->cd_attach, ca_list) { 754 if (STREQ(ca->ca_name, atname)) 755 return ca; 756 } 757 758 return NULL; 759 } 760 761 /* 762 * Look up a cfattach by driver/attachment name. 763 */ 764 struct cfattach * 765 config_cfattach_lookup(const char *name, const char *atname) 766 { 767 struct cfdriver *cd; 768 769 cd = config_cfdriver_lookup(name); 770 if (cd == NULL) 771 return NULL; 772 773 return config_cfattach_lookup_cd(cd, atname); 774 } 775 776 /* 777 * Apply the matching function and choose the best. This is used 778 * a few times and we want to keep the code small. 779 */ 780 static void 781 mapply(struct matchinfo *m, cfdata_t cf) 782 { 783 int pri; 784 785 if (m->fn != NULL) { 786 pri = (*m->fn)(m->parent, cf, m->locs, m->aux); 787 } else { 788 pri = config_match(m->parent, cf, m->aux); 789 } 790 if (pri > m->pri) { 791 m->match = cf; 792 m->pri = pri; 793 } 794 } 795 796 int 797 config_stdsubmatch(device_t parent, cfdata_t cf, const int *locs, void *aux) 798 { 799 const struct cfiattrdata *ci; 800 const struct cflocdesc *cl; 801 int nlocs, i; 802 803 ci = cfiattr_lookup(cfdata_ifattr(cf), parent->dv_cfdriver); 804 KASSERT(ci); 805 nlocs = ci->ci_loclen; 806 KASSERT(!nlocs || locs); 807 for (i = 0; i < nlocs; i++) { 808 cl = &ci->ci_locdesc[i]; 809 if (cl->cld_defaultstr != NULL && 810 cf->cf_loc[i] == cl->cld_default) 811 continue; 812 if (cf->cf_loc[i] == locs[i]) 813 continue; 814 return 0; 815 } 816 817 return config_match(parent, cf, aux); 818 } 819 820 /* 821 * Helper function: check whether the driver supports the interface attribute 822 * and return its descriptor structure. 823 */ 824 static const struct cfiattrdata * 825 cfdriver_get_iattr(const struct cfdriver *cd, const char *ia) 826 { 827 const struct cfiattrdata * const *cpp; 828 829 if (cd->cd_attrs == NULL) 830 return 0; 831 832 for (cpp = cd->cd_attrs; *cpp; cpp++) { 833 if (STREQ((*cpp)->ci_name, ia)) { 834 /* Match. */ 835 return *cpp; 836 } 837 } 838 return 0; 839 } 840 841 static int 842 cfdriver_iattr_count(const struct cfdriver *cd) 843 { 844 const struct cfiattrdata * const *cpp; 845 int i; 846 847 if (cd->cd_attrs == NULL) 848 return 0; 849 850 for (i = 0, cpp = cd->cd_attrs; *cpp; cpp++) { 851 i++; 852 } 853 return i; 854 } 855 856 /* 857 * Lookup an interface attribute description by name. 858 * If the driver is given, consider only its supported attributes. 859 */ 860 const struct cfiattrdata * 861 cfiattr_lookup(const char *name, const struct cfdriver *cd) 862 { 863 const struct cfdriver *d; 864 const struct cfiattrdata *ia; 865 866 if (cd) 867 return cfdriver_get_iattr(cd, name); 868 869 LIST_FOREACH(d, &allcfdrivers, cd_list) { 870 ia = cfdriver_get_iattr(d, name); 871 if (ia) 872 return ia; 873 } 874 return 0; 875 } 876 877 /* 878 * Determine if `parent' is a potential parent for a device spec based 879 * on `cfp'. 880 */ 881 static int 882 cfparent_match(const device_t parent, const struct cfparent *cfp) 883 { 884 struct cfdriver *pcd; 885 886 /* We don't match root nodes here. */ 887 if (cfp == NULL) 888 return 0; 889 890 pcd = parent->dv_cfdriver; 891 KASSERT(pcd != NULL); 892 893 /* 894 * First, ensure this parent has the correct interface 895 * attribute. 896 */ 897 if (!cfdriver_get_iattr(pcd, cfp->cfp_iattr)) 898 return 0; 899 900 /* 901 * If no specific parent device instance was specified (i.e. 902 * we're attaching to the attribute only), we're done! 903 */ 904 if (cfp->cfp_parent == NULL) 905 return 1; 906 907 /* 908 * Check the parent device's name. 909 */ 910 if (STREQ(pcd->cd_name, cfp->cfp_parent) == 0) 911 return 0; /* not the same parent */ 912 913 /* 914 * Make sure the unit number matches. 915 */ 916 if (cfp->cfp_unit == DVUNIT_ANY || /* wildcard */ 917 cfp->cfp_unit == parent->dv_unit) 918 return 1; 919 920 /* Unit numbers don't match. */ 921 return 0; 922 } 923 924 /* 925 * Helper for config_cfdata_attach(): check all devices whether it could be 926 * parent any attachment in the config data table passed, and rescan. 927 */ 928 static void 929 rescan_with_cfdata(const struct cfdata *cf) 930 { 931 device_t d; 932 const struct cfdata *cf1; 933 deviter_t di; 934 935 KASSERT(KERNEL_LOCKED_P()); 936 937 /* 938 * "alldevs" is likely longer than a modules's cfdata, so make it 939 * the outer loop. 940 */ 941 for (d = deviter_first(&di, 0); d != NULL; d = deviter_next(&di)) { 942 943 if (!(d->dv_cfattach->ca_rescan)) 944 continue; 945 946 for (cf1 = cf; cf1->cf_name; cf1++) { 947 948 if (!cfparent_match(d, cf1->cf_pspec)) 949 continue; 950 951 (*d->dv_cfattach->ca_rescan)(d, 952 cfdata_ifattr(cf1), cf1->cf_loc); 953 954 config_deferred(d); 955 } 956 } 957 deviter_release(&di); 958 } 959 960 /* 961 * Attach a supplemental config data table and rescan potential 962 * parent devices if required. 963 */ 964 int 965 config_cfdata_attach(cfdata_t cf, int scannow) 966 { 967 struct cftable *ct; 968 969 KERNEL_LOCK(1, NULL); 970 971 ct = kmem_alloc(sizeof(*ct), KM_SLEEP); 972 ct->ct_cfdata = cf; 973 TAILQ_INSERT_TAIL(&allcftables, ct, ct_list); 974 975 if (scannow) 976 rescan_with_cfdata(cf); 977 978 KERNEL_UNLOCK_ONE(NULL); 979 980 return 0; 981 } 982 983 /* 984 * Helper for config_cfdata_detach: check whether a device is 985 * found through any attachment in the config data table. 986 */ 987 static int 988 dev_in_cfdata(device_t d, cfdata_t cf) 989 { 990 const struct cfdata *cf1; 991 992 for (cf1 = cf; cf1->cf_name; cf1++) 993 if (d->dv_cfdata == cf1) 994 return 1; 995 996 return 0; 997 } 998 999 /* 1000 * Detach a supplemental config data table. Detach all devices found 1001 * through that table (and thus keeping references to it) before. 1002 */ 1003 int 1004 config_cfdata_detach(cfdata_t cf) 1005 { 1006 device_t d; 1007 int error = 0; 1008 struct cftable *ct; 1009 deviter_t di; 1010 1011 KERNEL_LOCK(1, NULL); 1012 1013 for (d = deviter_first(&di, DEVITER_F_RW); d != NULL; 1014 d = deviter_next(&di)) { 1015 if (!dev_in_cfdata(d, cf)) 1016 continue; 1017 if ((error = config_detach(d, 0)) != 0) 1018 break; 1019 } 1020 deviter_release(&di); 1021 if (error) { 1022 aprint_error_dev(d, "unable to detach instance\n"); 1023 goto out; 1024 } 1025 1026 TAILQ_FOREACH(ct, &allcftables, ct_list) { 1027 if (ct->ct_cfdata == cf) { 1028 TAILQ_REMOVE(&allcftables, ct, ct_list); 1029 kmem_free(ct, sizeof(*ct)); 1030 error = 0; 1031 goto out; 1032 } 1033 } 1034 1035 /* not found -- shouldn't happen */ 1036 error = EINVAL; 1037 1038 out: KERNEL_UNLOCK_ONE(NULL); 1039 return error; 1040 } 1041 1042 /* 1043 * Invoke the "match" routine for a cfdata entry on behalf of 1044 * an external caller, usually a direct config "submatch" routine. 1045 */ 1046 int 1047 config_match(device_t parent, cfdata_t cf, void *aux) 1048 { 1049 struct cfattach *ca; 1050 1051 KASSERT(KERNEL_LOCKED_P()); 1052 1053 ca = config_cfattach_lookup(cf->cf_name, cf->cf_atname); 1054 if (ca == NULL) { 1055 /* No attachment for this entry, oh well. */ 1056 return 0; 1057 } 1058 1059 return (*ca->ca_match)(parent, cf, aux); 1060 } 1061 1062 /* 1063 * Invoke the "probe" routine for a cfdata entry on behalf of 1064 * an external caller, usually an indirect config "search" routine. 1065 */ 1066 int 1067 config_probe(device_t parent, cfdata_t cf, void *aux) 1068 { 1069 /* 1070 * This is currently a synonym for config_match(), but this 1071 * is an implementation detail; "match" and "probe" routines 1072 * have different behaviors. 1073 * 1074 * XXX config_probe() should return a bool, because there is 1075 * XXX no match score for probe -- it's either there or it's 1076 * XXX not, but some ports abuse the return value as a way 1077 * XXX to attach "critical" devices before "non-critical" 1078 * XXX devices. 1079 */ 1080 return config_match(parent, cf, aux); 1081 } 1082 1083 static struct cfargs_internal * 1084 cfargs_canonicalize(const struct cfargs * const cfargs, 1085 struct cfargs_internal * const store) 1086 { 1087 struct cfargs_internal *args = store; 1088 1089 memset(args, 0, sizeof(*args)); 1090 1091 /* If none specified, are all-NULL pointers are good. */ 1092 if (cfargs == NULL) { 1093 return args; 1094 } 1095 1096 /* 1097 * Only one arguments version is recognized at this time. 1098 */ 1099 if (cfargs->cfargs_version != CFARGS_VERSION) { 1100 panic("cfargs_canonicalize: unknown version %lu\n", 1101 (unsigned long)cfargs->cfargs_version); 1102 } 1103 1104 /* 1105 * submatch and search are mutually-exclusive. 1106 */ 1107 if (cfargs->submatch != NULL && cfargs->search != NULL) { 1108 panic("cfargs_canonicalize: submatch and search are " 1109 "mutually-exclusive"); 1110 } 1111 if (cfargs->submatch != NULL) { 1112 args->submatch = cfargs->submatch; 1113 } else if (cfargs->search != NULL) { 1114 args->search = cfargs->search; 1115 } 1116 1117 args->iattr = cfargs->iattr; 1118 args->locators = cfargs->locators; 1119 args->devhandle = cfargs->devhandle; 1120 1121 return args; 1122 } 1123 1124 /* 1125 * Iterate over all potential children of some device, calling the given 1126 * function (default being the child's match function) for each one. 1127 * Nonzero returns are matches; the highest value returned is considered 1128 * the best match. Return the `found child' if we got a match, or NULL 1129 * otherwise. The `aux' pointer is simply passed on through. 1130 * 1131 * Note that this function is designed so that it can be used to apply 1132 * an arbitrary function to all potential children (its return value 1133 * can be ignored). 1134 */ 1135 static cfdata_t 1136 config_search_internal(device_t parent, void *aux, 1137 const struct cfargs_internal * const args) 1138 { 1139 struct cftable *ct; 1140 cfdata_t cf; 1141 struct matchinfo m; 1142 1143 KASSERT(config_initialized); 1144 KASSERT(!args->iattr || 1145 cfdriver_get_iattr(parent->dv_cfdriver, args->iattr)); 1146 KASSERT(args->iattr || 1147 cfdriver_iattr_count(parent->dv_cfdriver) < 2); 1148 1149 m.fn = args->submatch; /* N.B. union */ 1150 m.parent = parent; 1151 m.locs = args->locators; 1152 m.aux = aux; 1153 m.match = NULL; 1154 m.pri = 0; 1155 1156 TAILQ_FOREACH(ct, &allcftables, ct_list) { 1157 for (cf = ct->ct_cfdata; cf->cf_name; cf++) { 1158 1159 /* We don't match root nodes here. */ 1160 if (!cf->cf_pspec) 1161 continue; 1162 1163 /* 1164 * Skip cf if no longer eligible, otherwise scan 1165 * through parents for one matching `parent', and 1166 * try match function. 1167 */ 1168 if (cf->cf_fstate == FSTATE_FOUND) 1169 continue; 1170 if (cf->cf_fstate == FSTATE_DNOTFOUND || 1171 cf->cf_fstate == FSTATE_DSTAR) 1172 continue; 1173 1174 /* 1175 * If an interface attribute was specified, 1176 * consider only children which attach to 1177 * that attribute. 1178 */ 1179 if (args->iattr != NULL && 1180 !STREQ(args->iattr, cfdata_ifattr(cf))) 1181 continue; 1182 1183 if (cfparent_match(parent, cf->cf_pspec)) 1184 mapply(&m, cf); 1185 } 1186 } 1187 return m.match; 1188 } 1189 1190 cfdata_t 1191 config_search(device_t parent, void *aux, const struct cfargs *cfargs) 1192 { 1193 cfdata_t cf; 1194 struct cfargs_internal store; 1195 1196 cf = config_search_internal(parent, aux, 1197 cfargs_canonicalize(cfargs, &store)); 1198 1199 return cf; 1200 } 1201 1202 /* 1203 * Find the given root device. 1204 * This is much like config_search, but there is no parent. 1205 * Don't bother with multiple cfdata tables; the root node 1206 * must always be in the initial table. 1207 */ 1208 cfdata_t 1209 config_rootsearch(cfsubmatch_t fn, const char *rootname, void *aux) 1210 { 1211 cfdata_t cf; 1212 const short *p; 1213 struct matchinfo m; 1214 1215 m.fn = fn; 1216 m.parent = ROOT; 1217 m.aux = aux; 1218 m.match = NULL; 1219 m.pri = 0; 1220 m.locs = 0; 1221 /* 1222 * Look at root entries for matching name. We do not bother 1223 * with found-state here since only one root should ever be 1224 * searched (and it must be done first). 1225 */ 1226 for (p = cfroots; *p >= 0; p++) { 1227 cf = &cfdata[*p]; 1228 if (strcmp(cf->cf_name, rootname) == 0) 1229 mapply(&m, cf); 1230 } 1231 return m.match; 1232 } 1233 1234 static const char * const msgs[] = { 1235 [QUIET] = "", 1236 [UNCONF] = " not configured\n", 1237 [UNSUPP] = " unsupported\n", 1238 }; 1239 1240 /* 1241 * The given `aux' argument describes a device that has been found 1242 * on the given parent, but not necessarily configured. Locate the 1243 * configuration data for that device (using the submatch function 1244 * provided, or using candidates' cd_match configuration driver 1245 * functions) and attach it, and return its device_t. If the device was 1246 * not configured, call the given `print' function and return NULL. 1247 */ 1248 device_t 1249 config_found(device_t parent, void *aux, cfprint_t print, 1250 const struct cfargs * const cfargs) 1251 { 1252 cfdata_t cf; 1253 struct cfargs_internal store; 1254 const struct cfargs_internal * const args = 1255 cfargs_canonicalize(cfargs, &store); 1256 1257 cf = config_search_internal(parent, aux, args); 1258 if (cf != NULL) { 1259 return config_attach_internal(parent, cf, aux, print, args); 1260 } 1261 1262 if (print) { 1263 if (config_do_twiddle && cold) 1264 twiddle(); 1265 1266 const int pret = (*print)(aux, device_xname(parent)); 1267 KASSERT(pret >= 0); 1268 KASSERT(pret < __arraycount(msgs)); 1269 KASSERT(msgs[pret] != NULL); 1270 aprint_normal("%s", msgs[pret]); 1271 } 1272 1273 /* 1274 * This has the effect of mixing in a single timestamp to the 1275 * entropy pool. Experiments indicate the estimator will almost 1276 * always attribute one bit of entropy to this sample; analysis 1277 * of device attach/detach timestamps on FreeBSD indicates 4 1278 * bits of entropy/sample so this seems appropriately conservative. 1279 */ 1280 rnd_add_uint32(&rnd_autoconf_source, 0); 1281 return NULL; 1282 } 1283 1284 /* 1285 * As above, but for root devices. 1286 */ 1287 device_t 1288 config_rootfound(const char *rootname, void *aux) 1289 { 1290 cfdata_t cf; 1291 device_t dev = NULL; 1292 1293 KERNEL_LOCK(1, NULL); 1294 if ((cf = config_rootsearch(NULL, rootname, aux)) != NULL) 1295 dev = config_attach(ROOT, cf, aux, NULL, CFARGS_NONE); 1296 else 1297 aprint_error("root device %s not configured\n", rootname); 1298 KERNEL_UNLOCK_ONE(NULL); 1299 return dev; 1300 } 1301 1302 /* just like sprintf(buf, "%d") except that it works from the end */ 1303 static char * 1304 number(char *ep, int n) 1305 { 1306 1307 *--ep = 0; 1308 while (n >= 10) { 1309 *--ep = (n % 10) + '0'; 1310 n /= 10; 1311 } 1312 *--ep = n + '0'; 1313 return ep; 1314 } 1315 1316 /* 1317 * Expand the size of the cd_devs array if necessary. 1318 * 1319 * The caller must hold alldevs_lock. config_makeroom() may release and 1320 * re-acquire alldevs_lock, so callers should re-check conditions such 1321 * as alldevs_nwrite == 0 and alldevs_nread == 0 when config_makeroom() 1322 * returns. 1323 */ 1324 static void 1325 config_makeroom(int n, struct cfdriver *cd) 1326 { 1327 int ondevs, nndevs; 1328 device_t *osp, *nsp; 1329 1330 KASSERT(mutex_owned(&alldevs_lock)); 1331 alldevs_nwrite++; 1332 1333 for (nndevs = MAX(4, cd->cd_ndevs); nndevs <= n; nndevs += nndevs) 1334 ; 1335 1336 while (n >= cd->cd_ndevs) { 1337 /* 1338 * Need to expand the array. 1339 */ 1340 ondevs = cd->cd_ndevs; 1341 osp = cd->cd_devs; 1342 1343 /* 1344 * Release alldevs_lock around allocation, which may 1345 * sleep. 1346 */ 1347 mutex_exit(&alldevs_lock); 1348 nsp = kmem_alloc(sizeof(device_t) * nndevs, KM_SLEEP); 1349 mutex_enter(&alldevs_lock); 1350 1351 /* 1352 * If another thread moved the array while we did 1353 * not hold alldevs_lock, try again. 1354 */ 1355 if (cd->cd_devs != osp) { 1356 mutex_exit(&alldevs_lock); 1357 kmem_free(nsp, sizeof(device_t) * nndevs); 1358 mutex_enter(&alldevs_lock); 1359 continue; 1360 } 1361 1362 memset(nsp + ondevs, 0, sizeof(device_t) * (nndevs - ondevs)); 1363 if (ondevs != 0) 1364 memcpy(nsp, cd->cd_devs, sizeof(device_t) * ondevs); 1365 1366 cd->cd_ndevs = nndevs; 1367 cd->cd_devs = nsp; 1368 if (ondevs != 0) { 1369 mutex_exit(&alldevs_lock); 1370 kmem_free(osp, sizeof(device_t) * ondevs); 1371 mutex_enter(&alldevs_lock); 1372 } 1373 } 1374 KASSERT(mutex_owned(&alldevs_lock)); 1375 alldevs_nwrite--; 1376 } 1377 1378 /* 1379 * Put dev into the devices list. 1380 */ 1381 static void 1382 config_devlink(device_t dev) 1383 { 1384 1385 mutex_enter(&alldevs_lock); 1386 1387 KASSERT(device_cfdriver(dev)->cd_devs[dev->dv_unit] == dev); 1388 1389 dev->dv_add_gen = alldevs_gen; 1390 /* It is safe to add a device to the tail of the list while 1391 * readers and writers are in the list. 1392 */ 1393 TAILQ_INSERT_TAIL(&alldevs, dev, dv_list); 1394 mutex_exit(&alldevs_lock); 1395 } 1396 1397 static void 1398 config_devfree(device_t dev) 1399 { 1400 1401 KASSERT(dev->dv_flags & DVF_PRIV_ALLOC); 1402 KASSERTMSG(dev->dv_pending == 0, "%d", dev->dv_pending); 1403 1404 if (dev->dv_cfattach->ca_devsize > 0) 1405 kmem_free(dev->dv_private, dev->dv_cfattach->ca_devsize); 1406 kmem_free(dev, sizeof(*dev)); 1407 } 1408 1409 /* 1410 * Caller must hold alldevs_lock. 1411 */ 1412 static void 1413 config_devunlink(device_t dev, struct devicelist *garbage) 1414 { 1415 struct device_garbage *dg = &dev->dv_garbage; 1416 cfdriver_t cd = device_cfdriver(dev); 1417 int i; 1418 1419 KASSERT(mutex_owned(&alldevs_lock)); 1420 KASSERTMSG(dev->dv_pending == 0, "%d", dev->dv_pending); 1421 1422 /* Unlink from device list. Link to garbage list. */ 1423 TAILQ_REMOVE(&alldevs, dev, dv_list); 1424 TAILQ_INSERT_TAIL(garbage, dev, dv_list); 1425 1426 /* Remove from cfdriver's array. */ 1427 cd->cd_devs[dev->dv_unit] = NULL; 1428 1429 /* 1430 * If the device now has no units in use, unlink its softc array. 1431 */ 1432 for (i = 0; i < cd->cd_ndevs; i++) { 1433 if (cd->cd_devs[i] != NULL) 1434 break; 1435 } 1436 /* Nothing found. Unlink, now. Deallocate, later. */ 1437 if (i == cd->cd_ndevs) { 1438 dg->dg_ndevs = cd->cd_ndevs; 1439 dg->dg_devs = cd->cd_devs; 1440 cd->cd_devs = NULL; 1441 cd->cd_ndevs = 0; 1442 } 1443 } 1444 1445 static void 1446 config_devdelete(device_t dev) 1447 { 1448 struct device_garbage *dg = &dev->dv_garbage; 1449 device_lock_t dvl = device_getlock(dev); 1450 1451 KASSERTMSG(dev->dv_pending == 0, "%d", dev->dv_pending); 1452 1453 if (dg->dg_devs != NULL) 1454 kmem_free(dg->dg_devs, sizeof(device_t) * dg->dg_ndevs); 1455 1456 cv_destroy(&dvl->dvl_cv); 1457 mutex_destroy(&dvl->dvl_mtx); 1458 1459 KASSERT(dev->dv_properties != NULL); 1460 prop_object_release(dev->dv_properties); 1461 1462 if (dev->dv_activity_handlers) 1463 panic("%s with registered handlers", __func__); 1464 1465 if (dev->dv_locators) { 1466 size_t amount = *--dev->dv_locators; 1467 kmem_free(dev->dv_locators, amount); 1468 } 1469 1470 config_devfree(dev); 1471 } 1472 1473 static int 1474 config_unit_nextfree(cfdriver_t cd, cfdata_t cf) 1475 { 1476 int unit; 1477 1478 if (cf->cf_fstate == FSTATE_STAR) { 1479 for (unit = cf->cf_unit; unit < cd->cd_ndevs; unit++) 1480 if (cd->cd_devs[unit] == NULL) 1481 break; 1482 /* 1483 * unit is now the unit of the first NULL device pointer, 1484 * or max(cd->cd_ndevs,cf->cf_unit). 1485 */ 1486 } else { 1487 unit = cf->cf_unit; 1488 if (unit < cd->cd_ndevs && cd->cd_devs[unit] != NULL) 1489 unit = -1; 1490 } 1491 return unit; 1492 } 1493 1494 static int 1495 config_unit_alloc(device_t dev, cfdriver_t cd, cfdata_t cf) 1496 { 1497 struct alldevs_foray af; 1498 int unit; 1499 1500 config_alldevs_enter(&af); 1501 for (;;) { 1502 unit = config_unit_nextfree(cd, cf); 1503 if (unit == -1) 1504 break; 1505 if (unit < cd->cd_ndevs) { 1506 cd->cd_devs[unit] = dev; 1507 dev->dv_unit = unit; 1508 break; 1509 } 1510 config_makeroom(unit, cd); 1511 } 1512 config_alldevs_exit(&af); 1513 1514 return unit; 1515 } 1516 1517 static device_t 1518 config_devalloc(const device_t parent, const cfdata_t cf, 1519 const struct cfargs_internal * const args) 1520 { 1521 cfdriver_t cd; 1522 cfattach_t ca; 1523 size_t lname, lunit; 1524 const char *xunit; 1525 int myunit; 1526 char num[10]; 1527 device_t dev; 1528 void *dev_private; 1529 const struct cfiattrdata *ia; 1530 device_lock_t dvl; 1531 1532 cd = config_cfdriver_lookup(cf->cf_name); 1533 if (cd == NULL) 1534 return NULL; 1535 1536 ca = config_cfattach_lookup_cd(cd, cf->cf_atname); 1537 if (ca == NULL) 1538 return NULL; 1539 1540 /* get memory for all device vars */ 1541 KASSERT(ca->ca_flags & DVF_PRIV_ALLOC); 1542 if (ca->ca_devsize > 0) { 1543 dev_private = kmem_zalloc(ca->ca_devsize, KM_SLEEP); 1544 } else { 1545 dev_private = NULL; 1546 } 1547 dev = kmem_zalloc(sizeof(*dev), KM_SLEEP); 1548 1549 dev->dv_handle = args->devhandle; 1550 1551 dev->dv_class = cd->cd_class; 1552 dev->dv_cfdata = cf; 1553 dev->dv_cfdriver = cd; 1554 dev->dv_cfattach = ca; 1555 dev->dv_activity_count = 0; 1556 dev->dv_activity_handlers = NULL; 1557 dev->dv_private = dev_private; 1558 dev->dv_flags = ca->ca_flags; /* inherit flags from class */ 1559 1560 myunit = config_unit_alloc(dev, cd, cf); 1561 if (myunit == -1) { 1562 config_devfree(dev); 1563 return NULL; 1564 } 1565 1566 /* compute length of name and decimal expansion of unit number */ 1567 lname = strlen(cd->cd_name); 1568 xunit = number(&num[sizeof(num)], myunit); 1569 lunit = &num[sizeof(num)] - xunit; 1570 if (lname + lunit > sizeof(dev->dv_xname)) 1571 panic("config_devalloc: device name too long"); 1572 1573 dvl = device_getlock(dev); 1574 1575 mutex_init(&dvl->dvl_mtx, MUTEX_DEFAULT, IPL_NONE); 1576 cv_init(&dvl->dvl_cv, "pmfsusp"); 1577 1578 memcpy(dev->dv_xname, cd->cd_name, lname); 1579 memcpy(dev->dv_xname + lname, xunit, lunit); 1580 dev->dv_parent = parent; 1581 if (parent != NULL) 1582 dev->dv_depth = parent->dv_depth + 1; 1583 else 1584 dev->dv_depth = 0; 1585 dev->dv_flags |= DVF_ACTIVE; /* always initially active */ 1586 if (args->locators) { 1587 KASSERT(parent); /* no locators at root */ 1588 ia = cfiattr_lookup(cfdata_ifattr(cf), parent->dv_cfdriver); 1589 dev->dv_locators = 1590 kmem_alloc(sizeof(int) * (ia->ci_loclen + 1), KM_SLEEP); 1591 *dev->dv_locators++ = sizeof(int) * (ia->ci_loclen + 1); 1592 memcpy(dev->dv_locators, args->locators, 1593 sizeof(int) * ia->ci_loclen); 1594 } 1595 dev->dv_properties = prop_dictionary_create(); 1596 KASSERT(dev->dv_properties != NULL); 1597 1598 prop_dictionary_set_string_nocopy(dev->dv_properties, 1599 "device-driver", dev->dv_cfdriver->cd_name); 1600 prop_dictionary_set_uint16(dev->dv_properties, 1601 "device-unit", dev->dv_unit); 1602 if (parent != NULL) { 1603 prop_dictionary_set_string(dev->dv_properties, 1604 "device-parent", device_xname(parent)); 1605 } 1606 1607 if (dev->dv_cfdriver->cd_attrs != NULL) 1608 config_add_attrib_dict(dev); 1609 1610 return dev; 1611 } 1612 1613 /* 1614 * Create an array of device attach attributes and add it 1615 * to the device's dv_properties dictionary. 1616 * 1617 * <key>interface-attributes</key> 1618 * <array> 1619 * <dict> 1620 * <key>attribute-name</key> 1621 * <string>foo</string> 1622 * <key>locators</key> 1623 * <array> 1624 * <dict> 1625 * <key>loc-name</key> 1626 * <string>foo-loc1</string> 1627 * </dict> 1628 * <dict> 1629 * <key>loc-name</key> 1630 * <string>foo-loc2</string> 1631 * <key>default</key> 1632 * <string>foo-loc2-default</string> 1633 * </dict> 1634 * ... 1635 * </array> 1636 * </dict> 1637 * ... 1638 * </array> 1639 */ 1640 1641 static void 1642 config_add_attrib_dict(device_t dev) 1643 { 1644 int i, j; 1645 const struct cfiattrdata *ci; 1646 prop_dictionary_t attr_dict, loc_dict; 1647 prop_array_t attr_array, loc_array; 1648 1649 if ((attr_array = prop_array_create()) == NULL) 1650 return; 1651 1652 for (i = 0; ; i++) { 1653 if ((ci = dev->dv_cfdriver->cd_attrs[i]) == NULL) 1654 break; 1655 if ((attr_dict = prop_dictionary_create()) == NULL) 1656 break; 1657 prop_dictionary_set_string_nocopy(attr_dict, "attribute-name", 1658 ci->ci_name); 1659 1660 /* Create an array of the locator names and defaults */ 1661 1662 if (ci->ci_loclen != 0 && 1663 (loc_array = prop_array_create()) != NULL) { 1664 for (j = 0; j < ci->ci_loclen; j++) { 1665 loc_dict = prop_dictionary_create(); 1666 if (loc_dict == NULL) 1667 continue; 1668 prop_dictionary_set_string_nocopy(loc_dict, 1669 "loc-name", ci->ci_locdesc[j].cld_name); 1670 if (ci->ci_locdesc[j].cld_defaultstr != NULL) 1671 prop_dictionary_set_string_nocopy( 1672 loc_dict, "default", 1673 ci->ci_locdesc[j].cld_defaultstr); 1674 prop_array_set(loc_array, j, loc_dict); 1675 prop_object_release(loc_dict); 1676 } 1677 prop_dictionary_set_and_rel(attr_dict, "locators", 1678 loc_array); 1679 } 1680 prop_array_add(attr_array, attr_dict); 1681 prop_object_release(attr_dict); 1682 } 1683 if (i == 0) 1684 prop_object_release(attr_array); 1685 else 1686 prop_dictionary_set_and_rel(dev->dv_properties, 1687 "interface-attributes", attr_array); 1688 1689 return; 1690 } 1691 1692 /* 1693 * Attach a found device. 1694 */ 1695 static device_t 1696 config_attach_internal(device_t parent, cfdata_t cf, void *aux, cfprint_t print, 1697 const struct cfargs_internal * const args) 1698 { 1699 device_t dev; 1700 struct cftable *ct; 1701 const char *drvname; 1702 bool deferred; 1703 1704 KASSERT(KERNEL_LOCKED_P()); 1705 1706 dev = config_devalloc(parent, cf, args); 1707 if (!dev) 1708 panic("config_attach: allocation of device softc failed"); 1709 1710 /* XXX redundant - see below? */ 1711 if (cf->cf_fstate != FSTATE_STAR) { 1712 KASSERT(cf->cf_fstate == FSTATE_NOTFOUND); 1713 cf->cf_fstate = FSTATE_FOUND; 1714 } 1715 1716 config_devlink(dev); 1717 1718 if (config_do_twiddle && cold) 1719 twiddle(); 1720 else 1721 aprint_naive("Found "); 1722 /* 1723 * We want the next two printfs for normal, verbose, and quiet, 1724 * but not silent (in which case, we're twiddling, instead). 1725 */ 1726 if (parent == ROOT) { 1727 aprint_naive("%s (root)", device_xname(dev)); 1728 aprint_normal("%s (root)", device_xname(dev)); 1729 } else { 1730 aprint_naive("%s at %s", device_xname(dev), 1731 device_xname(parent)); 1732 aprint_normal("%s at %s", device_xname(dev), 1733 device_xname(parent)); 1734 if (print) 1735 (void) (*print)(aux, NULL); 1736 } 1737 1738 /* 1739 * Before attaching, clobber any unfound devices that are 1740 * otherwise identical. 1741 * XXX code above is redundant? 1742 */ 1743 drvname = dev->dv_cfdriver->cd_name; 1744 TAILQ_FOREACH(ct, &allcftables, ct_list) { 1745 for (cf = ct->ct_cfdata; cf->cf_name; cf++) { 1746 if (STREQ(cf->cf_name, drvname) && 1747 cf->cf_unit == dev->dv_unit) { 1748 if (cf->cf_fstate == FSTATE_NOTFOUND) 1749 cf->cf_fstate = FSTATE_FOUND; 1750 } 1751 } 1752 } 1753 device_register(dev, aux); 1754 1755 /* Let userland know */ 1756 devmon_report_device(dev, true); 1757 1758 config_pending_incr(dev); 1759 (*dev->dv_cfattach->ca_attach)(parent, dev, aux); 1760 config_pending_decr(dev); 1761 1762 mutex_enter(&config_misc_lock); 1763 deferred = (dev->dv_pending != 0); 1764 mutex_exit(&config_misc_lock); 1765 1766 if (!deferred && !device_pmf_is_registered(dev)) 1767 aprint_debug_dev(dev, 1768 "WARNING: power management not supported\n"); 1769 1770 config_process_deferred(&deferred_config_queue, dev); 1771 1772 device_register_post_config(dev, aux); 1773 return dev; 1774 } 1775 1776 device_t 1777 config_attach(device_t parent, cfdata_t cf, void *aux, cfprint_t print, 1778 const struct cfargs *cfargs) 1779 { 1780 struct cfargs_internal store; 1781 1782 KASSERT(KERNEL_LOCKED_P()); 1783 1784 return config_attach_internal(parent, cf, aux, print, 1785 cfargs_canonicalize(cfargs, &store)); 1786 } 1787 1788 /* 1789 * As above, but for pseudo-devices. Pseudo-devices attached in this 1790 * way are silently inserted into the device tree, and their children 1791 * attached. 1792 * 1793 * Note that because pseudo-devices are attached silently, any information 1794 * the attach routine wishes to print should be prefixed with the device 1795 * name by the attach routine. 1796 */ 1797 device_t 1798 config_attach_pseudo(cfdata_t cf) 1799 { 1800 device_t dev; 1801 1802 KERNEL_LOCK(1, NULL); 1803 1804 struct cfargs_internal args = { }; 1805 dev = config_devalloc(ROOT, cf, &args); 1806 if (!dev) 1807 goto out; 1808 1809 /* XXX mark busy in cfdata */ 1810 1811 if (cf->cf_fstate != FSTATE_STAR) { 1812 KASSERT(cf->cf_fstate == FSTATE_NOTFOUND); 1813 cf->cf_fstate = FSTATE_FOUND; 1814 } 1815 1816 config_devlink(dev); 1817 1818 #if 0 /* XXXJRT not yet */ 1819 device_register(dev, NULL); /* like a root node */ 1820 #endif 1821 1822 /* Let userland know */ 1823 devmon_report_device(dev, true); 1824 1825 config_pending_incr(dev); 1826 (*dev->dv_cfattach->ca_attach)(ROOT, dev, NULL); 1827 config_pending_decr(dev); 1828 1829 config_process_deferred(&deferred_config_queue, dev); 1830 1831 out: KERNEL_UNLOCK_ONE(NULL); 1832 return dev; 1833 } 1834 1835 /* 1836 * Caller must hold alldevs_lock. 1837 */ 1838 static void 1839 config_collect_garbage(struct devicelist *garbage) 1840 { 1841 device_t dv; 1842 1843 KASSERT(!cpu_intr_p()); 1844 KASSERT(!cpu_softintr_p()); 1845 KASSERT(mutex_owned(&alldevs_lock)); 1846 1847 while (alldevs_nwrite == 0 && alldevs_nread == 0 && alldevs_garbage) { 1848 TAILQ_FOREACH(dv, &alldevs, dv_list) { 1849 if (dv->dv_del_gen != 0) 1850 break; 1851 } 1852 if (dv == NULL) { 1853 alldevs_garbage = false; 1854 break; 1855 } 1856 config_devunlink(dv, garbage); 1857 } 1858 KASSERT(mutex_owned(&alldevs_lock)); 1859 } 1860 1861 static void 1862 config_dump_garbage(struct devicelist *garbage) 1863 { 1864 device_t dv; 1865 1866 while ((dv = TAILQ_FIRST(garbage)) != NULL) { 1867 TAILQ_REMOVE(garbage, dv, dv_list); 1868 config_devdelete(dv); 1869 } 1870 } 1871 1872 static int 1873 config_detach_enter(device_t dev) 1874 { 1875 int error; 1876 1877 mutex_enter(&config_misc_lock); 1878 for (;;) { 1879 if (dev->dv_pending == 0 && dev->dv_detaching == NULL) { 1880 dev->dv_detaching = curlwp; 1881 error = 0; 1882 break; 1883 } 1884 KASSERTMSG(dev->dv_detaching != curlwp, 1885 "recursively detaching %s", device_xname(dev)); 1886 error = cv_wait_sig(&config_misc_cv, &config_misc_lock); 1887 if (error) 1888 break; 1889 } 1890 KASSERT(error || dev->dv_detaching == curlwp); 1891 mutex_exit(&config_misc_lock); 1892 1893 return error; 1894 } 1895 1896 static void 1897 config_detach_exit(device_t dev) 1898 { 1899 1900 mutex_enter(&config_misc_lock); 1901 KASSERT(dev->dv_detaching == curlwp); 1902 dev->dv_detaching = NULL; 1903 cv_broadcast(&config_misc_cv); 1904 mutex_exit(&config_misc_lock); 1905 } 1906 1907 /* 1908 * Detach a device. Optionally forced (e.g. because of hardware 1909 * removal) and quiet. Returns zero if successful, non-zero 1910 * (an error code) otherwise. 1911 * 1912 * Note that this code wants to be run from a process context, so 1913 * that the detach can sleep to allow processes which have a device 1914 * open to run and unwind their stacks. 1915 */ 1916 int 1917 config_detach(device_t dev, int flags) 1918 { 1919 struct alldevs_foray af; 1920 struct cftable *ct; 1921 cfdata_t cf; 1922 const struct cfattach *ca; 1923 struct cfdriver *cd; 1924 device_t d __diagused; 1925 int rv = 0; 1926 1927 KERNEL_LOCK(1, NULL); 1928 1929 cf = dev->dv_cfdata; 1930 KASSERTMSG((cf == NULL || cf->cf_fstate == FSTATE_FOUND || 1931 cf->cf_fstate == FSTATE_STAR), 1932 "config_detach: %s: bad device fstate: %d", 1933 device_xname(dev), cf ? cf->cf_fstate : -1); 1934 1935 cd = dev->dv_cfdriver; 1936 KASSERT(cd != NULL); 1937 1938 ca = dev->dv_cfattach; 1939 KASSERT(ca != NULL); 1940 1941 /* 1942 * Only one detach at a time, please -- and not until fully 1943 * attached. 1944 */ 1945 rv = config_detach_enter(dev); 1946 if (rv) { 1947 KERNEL_UNLOCK_ONE(NULL); 1948 return rv; 1949 } 1950 1951 mutex_enter(&alldevs_lock); 1952 if (dev->dv_del_gen != 0) { 1953 mutex_exit(&alldevs_lock); 1954 #ifdef DIAGNOSTIC 1955 printf("%s: %s is already detached\n", __func__, 1956 device_xname(dev)); 1957 #endif /* DIAGNOSTIC */ 1958 config_detach_exit(dev); 1959 KERNEL_UNLOCK_ONE(NULL); 1960 return ENOENT; 1961 } 1962 alldevs_nwrite++; 1963 mutex_exit(&alldevs_lock); 1964 1965 if (!detachall && 1966 (flags & (DETACH_SHUTDOWN|DETACH_FORCE)) == DETACH_SHUTDOWN && 1967 (dev->dv_flags & DVF_DETACH_SHUTDOWN) == 0) { 1968 rv = EOPNOTSUPP; 1969 } else if (ca->ca_detach != NULL) { 1970 rv = (*ca->ca_detach)(dev, flags); 1971 } else 1972 rv = EOPNOTSUPP; 1973 1974 /* 1975 * If it was not possible to detach the device, then we either 1976 * panic() (for the forced but failed case), or return an error. 1977 * 1978 * If it was possible to detach the device, ensure that the 1979 * device is deactivated. 1980 */ 1981 if (rv == 0) 1982 dev->dv_flags &= ~DVF_ACTIVE; 1983 else if ((flags & DETACH_FORCE) == 0) 1984 goto out; 1985 else { 1986 panic("config_detach: forced detach of %s failed (%d)", 1987 device_xname(dev), rv); 1988 } 1989 1990 /* 1991 * The device has now been successfully detached. 1992 */ 1993 1994 /* Let userland know */ 1995 devmon_report_device(dev, false); 1996 1997 #ifdef DIAGNOSTIC 1998 /* 1999 * Sanity: If you're successfully detached, you should have no 2000 * children. (Note that because children must be attached 2001 * after parents, we only need to search the latter part of 2002 * the list.) 2003 */ 2004 mutex_enter(&alldevs_lock); 2005 for (d = TAILQ_NEXT(dev, dv_list); d != NULL; 2006 d = TAILQ_NEXT(d, dv_list)) { 2007 if (d->dv_parent == dev && d->dv_del_gen == 0) { 2008 printf("config_detach: detached device %s" 2009 " has children %s\n", device_xname(dev), 2010 device_xname(d)); 2011 panic("config_detach"); 2012 } 2013 } 2014 mutex_exit(&alldevs_lock); 2015 #endif 2016 2017 /* notify the parent that the child is gone */ 2018 if (dev->dv_parent) { 2019 device_t p = dev->dv_parent; 2020 if (p->dv_cfattach->ca_childdetached) 2021 (*p->dv_cfattach->ca_childdetached)(p, dev); 2022 } 2023 2024 /* 2025 * Mark cfdata to show that the unit can be reused, if possible. 2026 */ 2027 TAILQ_FOREACH(ct, &allcftables, ct_list) { 2028 for (cf = ct->ct_cfdata; cf->cf_name; cf++) { 2029 if (STREQ(cf->cf_name, cd->cd_name)) { 2030 if (cf->cf_fstate == FSTATE_FOUND && 2031 cf->cf_unit == dev->dv_unit) 2032 cf->cf_fstate = FSTATE_NOTFOUND; 2033 } 2034 } 2035 } 2036 2037 if (dev->dv_cfdata != NULL && (flags & DETACH_QUIET) == 0) 2038 aprint_normal_dev(dev, "detached\n"); 2039 2040 out: 2041 config_detach_exit(dev); 2042 2043 config_alldevs_enter(&af); 2044 KASSERT(alldevs_nwrite != 0); 2045 --alldevs_nwrite; 2046 if (rv == 0 && dev->dv_del_gen == 0) { 2047 if (alldevs_nwrite == 0 && alldevs_nread == 0) 2048 config_devunlink(dev, &af.af_garbage); 2049 else { 2050 dev->dv_del_gen = alldevs_gen; 2051 alldevs_garbage = true; 2052 } 2053 } 2054 config_alldevs_exit(&af); 2055 2056 KERNEL_UNLOCK_ONE(NULL); 2057 2058 return rv; 2059 } 2060 2061 int 2062 config_detach_children(device_t parent, int flags) 2063 { 2064 device_t dv; 2065 deviter_t di; 2066 int error = 0; 2067 2068 KASSERT(KERNEL_LOCKED_P()); 2069 2070 for (dv = deviter_first(&di, DEVITER_F_RW); dv != NULL; 2071 dv = deviter_next(&di)) { 2072 if (device_parent(dv) != parent) 2073 continue; 2074 if ((error = config_detach(dv, flags)) != 0) 2075 break; 2076 } 2077 deviter_release(&di); 2078 return error; 2079 } 2080 2081 device_t 2082 shutdown_first(struct shutdown_state *s) 2083 { 2084 if (!s->initialized) { 2085 deviter_init(&s->di, DEVITER_F_SHUTDOWN|DEVITER_F_LEAVES_FIRST); 2086 s->initialized = true; 2087 } 2088 return shutdown_next(s); 2089 } 2090 2091 device_t 2092 shutdown_next(struct shutdown_state *s) 2093 { 2094 device_t dv; 2095 2096 while ((dv = deviter_next(&s->di)) != NULL && !device_is_active(dv)) 2097 ; 2098 2099 if (dv == NULL) 2100 s->initialized = false; 2101 2102 return dv; 2103 } 2104 2105 bool 2106 config_detach_all(int how) 2107 { 2108 static struct shutdown_state s; 2109 device_t curdev; 2110 bool progress = false; 2111 int flags; 2112 2113 KERNEL_LOCK(1, NULL); 2114 2115 if ((how & (RB_NOSYNC|RB_DUMP)) != 0) 2116 goto out; 2117 2118 if ((how & RB_POWERDOWN) == RB_POWERDOWN) 2119 flags = DETACH_SHUTDOWN | DETACH_POWEROFF; 2120 else 2121 flags = DETACH_SHUTDOWN; 2122 2123 for (curdev = shutdown_first(&s); curdev != NULL; 2124 curdev = shutdown_next(&s)) { 2125 aprint_debug(" detaching %s, ", device_xname(curdev)); 2126 if (config_detach(curdev, flags) == 0) { 2127 progress = true; 2128 aprint_debug("success."); 2129 } else 2130 aprint_debug("failed."); 2131 } 2132 2133 out: KERNEL_UNLOCK_ONE(NULL); 2134 return progress; 2135 } 2136 2137 static bool 2138 device_is_ancestor_of(device_t ancestor, device_t descendant) 2139 { 2140 device_t dv; 2141 2142 for (dv = descendant; dv != NULL; dv = device_parent(dv)) { 2143 if (device_parent(dv) == ancestor) 2144 return true; 2145 } 2146 return false; 2147 } 2148 2149 int 2150 config_deactivate(device_t dev) 2151 { 2152 deviter_t di; 2153 const struct cfattach *ca; 2154 device_t descendant; 2155 int s, rv = 0, oflags; 2156 2157 for (descendant = deviter_first(&di, DEVITER_F_ROOT_FIRST); 2158 descendant != NULL; 2159 descendant = deviter_next(&di)) { 2160 if (dev != descendant && 2161 !device_is_ancestor_of(dev, descendant)) 2162 continue; 2163 2164 if ((descendant->dv_flags & DVF_ACTIVE) == 0) 2165 continue; 2166 2167 ca = descendant->dv_cfattach; 2168 oflags = descendant->dv_flags; 2169 2170 descendant->dv_flags &= ~DVF_ACTIVE; 2171 if (ca->ca_activate == NULL) 2172 continue; 2173 s = splhigh(); 2174 rv = (*ca->ca_activate)(descendant, DVACT_DEACTIVATE); 2175 splx(s); 2176 if (rv != 0) 2177 descendant->dv_flags = oflags; 2178 } 2179 deviter_release(&di); 2180 return rv; 2181 } 2182 2183 /* 2184 * Defer the configuration of the specified device until all 2185 * of its parent's devices have been attached. 2186 */ 2187 void 2188 config_defer(device_t dev, void (*func)(device_t)) 2189 { 2190 struct deferred_config *dc; 2191 2192 if (dev->dv_parent == NULL) 2193 panic("config_defer: can't defer config of a root device"); 2194 2195 dc = kmem_alloc(sizeof(*dc), KM_SLEEP); 2196 2197 config_pending_incr(dev); 2198 2199 mutex_enter(&config_misc_lock); 2200 #ifdef DIAGNOSTIC 2201 struct deferred_config *odc; 2202 TAILQ_FOREACH(odc, &deferred_config_queue, dc_queue) { 2203 if (odc->dc_dev == dev) 2204 panic("config_defer: deferred twice"); 2205 } 2206 #endif 2207 dc->dc_dev = dev; 2208 dc->dc_func = func; 2209 TAILQ_INSERT_TAIL(&deferred_config_queue, dc, dc_queue); 2210 mutex_exit(&config_misc_lock); 2211 } 2212 2213 /* 2214 * Defer some autoconfiguration for a device until after interrupts 2215 * are enabled. 2216 */ 2217 void 2218 config_interrupts(device_t dev, void (*func)(device_t)) 2219 { 2220 struct deferred_config *dc; 2221 2222 /* 2223 * If interrupts are enabled, callback now. 2224 */ 2225 if (cold == 0) { 2226 (*func)(dev); 2227 return; 2228 } 2229 2230 dc = kmem_alloc(sizeof(*dc), KM_SLEEP); 2231 2232 config_pending_incr(dev); 2233 2234 mutex_enter(&config_misc_lock); 2235 #ifdef DIAGNOSTIC 2236 struct deferred_config *odc; 2237 TAILQ_FOREACH(odc, &interrupt_config_queue, dc_queue) { 2238 if (odc->dc_dev == dev) 2239 panic("config_interrupts: deferred twice"); 2240 } 2241 #endif 2242 dc->dc_dev = dev; 2243 dc->dc_func = func; 2244 TAILQ_INSERT_TAIL(&interrupt_config_queue, dc, dc_queue); 2245 mutex_exit(&config_misc_lock); 2246 } 2247 2248 /* 2249 * Defer some autoconfiguration for a device until after root file system 2250 * is mounted (to load firmware etc). 2251 */ 2252 void 2253 config_mountroot(device_t dev, void (*func)(device_t)) 2254 { 2255 struct deferred_config *dc; 2256 2257 /* 2258 * If root file system is mounted, callback now. 2259 */ 2260 if (root_is_mounted) { 2261 (*func)(dev); 2262 return; 2263 } 2264 2265 dc = kmem_alloc(sizeof(*dc), KM_SLEEP); 2266 2267 mutex_enter(&config_misc_lock); 2268 #ifdef DIAGNOSTIC 2269 struct deferred_config *odc; 2270 TAILQ_FOREACH(odc, &mountroot_config_queue, dc_queue) { 2271 if (odc->dc_dev == dev) 2272 panic("%s: deferred twice", __func__); 2273 } 2274 #endif 2275 2276 dc->dc_dev = dev; 2277 dc->dc_func = func; 2278 TAILQ_INSERT_TAIL(&mountroot_config_queue, dc, dc_queue); 2279 mutex_exit(&config_misc_lock); 2280 } 2281 2282 /* 2283 * Process a deferred configuration queue. 2284 */ 2285 static void 2286 config_process_deferred(struct deferred_config_head *queue, device_t parent) 2287 { 2288 struct deferred_config *dc; 2289 2290 KASSERT(KERNEL_LOCKED_P()); 2291 2292 mutex_enter(&config_misc_lock); 2293 dc = TAILQ_FIRST(queue); 2294 while (dc) { 2295 if (parent == NULL || dc->dc_dev->dv_parent == parent) { 2296 TAILQ_REMOVE(queue, dc, dc_queue); 2297 mutex_exit(&config_misc_lock); 2298 2299 (*dc->dc_func)(dc->dc_dev); 2300 config_pending_decr(dc->dc_dev); 2301 kmem_free(dc, sizeof(*dc)); 2302 2303 mutex_enter(&config_misc_lock); 2304 /* Restart, queue might have changed */ 2305 dc = TAILQ_FIRST(queue); 2306 } else { 2307 dc = TAILQ_NEXT(dc, dc_queue); 2308 } 2309 } 2310 mutex_exit(&config_misc_lock); 2311 } 2312 2313 /* 2314 * Manipulate the config_pending semaphore. 2315 */ 2316 void 2317 config_pending_incr(device_t dev) 2318 { 2319 2320 mutex_enter(&config_misc_lock); 2321 KASSERTMSG(dev->dv_pending < INT_MAX, 2322 "%s: excess config_pending_incr", device_xname(dev)); 2323 if (dev->dv_pending++ == 0) 2324 TAILQ_INSERT_TAIL(&config_pending, dev, dv_pending_list); 2325 #ifdef DEBUG_AUTOCONF 2326 printf("%s: %s %d\n", __func__, device_xname(dev), dev->dv_pending); 2327 #endif 2328 mutex_exit(&config_misc_lock); 2329 } 2330 2331 void 2332 config_pending_decr(device_t dev) 2333 { 2334 2335 mutex_enter(&config_misc_lock); 2336 KASSERTMSG(dev->dv_pending > 0, 2337 "%s: excess config_pending_decr", device_xname(dev)); 2338 if (--dev->dv_pending == 0) { 2339 TAILQ_REMOVE(&config_pending, dev, dv_pending_list); 2340 cv_broadcast(&config_misc_cv); 2341 } 2342 #ifdef DEBUG_AUTOCONF 2343 printf("%s: %s %d\n", __func__, device_xname(dev), dev->dv_pending); 2344 #endif 2345 mutex_exit(&config_misc_lock); 2346 } 2347 2348 /* 2349 * Register a "finalization" routine. Finalization routines are 2350 * called iteratively once all real devices have been found during 2351 * autoconfiguration, for as long as any one finalizer has done 2352 * any work. 2353 */ 2354 int 2355 config_finalize_register(device_t dev, int (*fn)(device_t)) 2356 { 2357 struct finalize_hook *f; 2358 int error = 0; 2359 2360 KERNEL_LOCK(1, NULL); 2361 2362 /* 2363 * If finalization has already been done, invoke the 2364 * callback function now. 2365 */ 2366 if (config_finalize_done) { 2367 while ((*fn)(dev) != 0) 2368 /* loop */ ; 2369 goto out; 2370 } 2371 2372 /* Ensure this isn't already on the list. */ 2373 TAILQ_FOREACH(f, &config_finalize_list, f_list) { 2374 if (f->f_func == fn && f->f_dev == dev) { 2375 error = EEXIST; 2376 goto out; 2377 } 2378 } 2379 2380 f = kmem_alloc(sizeof(*f), KM_SLEEP); 2381 f->f_func = fn; 2382 f->f_dev = dev; 2383 TAILQ_INSERT_TAIL(&config_finalize_list, f, f_list); 2384 2385 /* Success! */ 2386 error = 0; 2387 2388 out: KERNEL_UNLOCK_ONE(NULL); 2389 return error; 2390 } 2391 2392 void 2393 config_finalize(void) 2394 { 2395 struct finalize_hook *f; 2396 struct pdevinit *pdev; 2397 extern struct pdevinit pdevinit[]; 2398 int errcnt, rv; 2399 2400 /* 2401 * Now that device driver threads have been created, wait for 2402 * them to finish any deferred autoconfiguration. 2403 */ 2404 mutex_enter(&config_misc_lock); 2405 while (!TAILQ_EMPTY(&config_pending)) { 2406 device_t dev; 2407 int error; 2408 2409 error = cv_timedwait(&config_misc_cv, &config_misc_lock, 2410 mstohz(1000)); 2411 if (error == EWOULDBLOCK) { 2412 aprint_debug("waiting for devices:"); 2413 TAILQ_FOREACH(dev, &config_pending, dv_pending_list) 2414 aprint_debug(" %s", device_xname(dev)); 2415 aprint_debug("\n"); 2416 } 2417 } 2418 mutex_exit(&config_misc_lock); 2419 2420 KERNEL_LOCK(1, NULL); 2421 2422 /* Attach pseudo-devices. */ 2423 for (pdev = pdevinit; pdev->pdev_attach != NULL; pdev++) 2424 (*pdev->pdev_attach)(pdev->pdev_count); 2425 2426 /* Run the hooks until none of them does any work. */ 2427 do { 2428 rv = 0; 2429 TAILQ_FOREACH(f, &config_finalize_list, f_list) 2430 rv |= (*f->f_func)(f->f_dev); 2431 } while (rv != 0); 2432 2433 config_finalize_done = 1; 2434 2435 /* Now free all the hooks. */ 2436 while ((f = TAILQ_FIRST(&config_finalize_list)) != NULL) { 2437 TAILQ_REMOVE(&config_finalize_list, f, f_list); 2438 kmem_free(f, sizeof(*f)); 2439 } 2440 2441 KERNEL_UNLOCK_ONE(NULL); 2442 2443 errcnt = aprint_get_error_count(); 2444 if ((boothowto & (AB_QUIET|AB_SILENT)) != 0 && 2445 (boothowto & AB_VERBOSE) == 0) { 2446 mutex_enter(&config_misc_lock); 2447 if (config_do_twiddle) { 2448 config_do_twiddle = 0; 2449 printf_nolog(" done.\n"); 2450 } 2451 mutex_exit(&config_misc_lock); 2452 } 2453 if (errcnt != 0) { 2454 printf("WARNING: %d error%s while detecting hardware; " 2455 "check system log.\n", errcnt, 2456 errcnt == 1 ? "" : "s"); 2457 } 2458 } 2459 2460 void 2461 config_twiddle_init(void) 2462 { 2463 2464 if ((boothowto & (AB_SILENT|AB_VERBOSE)) == AB_SILENT) { 2465 config_do_twiddle = 1; 2466 } 2467 callout_setfunc(&config_twiddle_ch, config_twiddle_fn, NULL); 2468 } 2469 2470 void 2471 config_twiddle_fn(void *cookie) 2472 { 2473 2474 mutex_enter(&config_misc_lock); 2475 if (config_do_twiddle) { 2476 twiddle(); 2477 callout_schedule(&config_twiddle_ch, mstohz(100)); 2478 } 2479 mutex_exit(&config_misc_lock); 2480 } 2481 2482 static void 2483 config_alldevs_enter(struct alldevs_foray *af) 2484 { 2485 TAILQ_INIT(&af->af_garbage); 2486 mutex_enter(&alldevs_lock); 2487 config_collect_garbage(&af->af_garbage); 2488 } 2489 2490 static void 2491 config_alldevs_exit(struct alldevs_foray *af) 2492 { 2493 mutex_exit(&alldevs_lock); 2494 config_dump_garbage(&af->af_garbage); 2495 } 2496 2497 /* 2498 * device_lookup: 2499 * 2500 * Look up a device instance for a given driver. 2501 */ 2502 device_t 2503 device_lookup(cfdriver_t cd, int unit) 2504 { 2505 device_t dv; 2506 2507 mutex_enter(&alldevs_lock); 2508 if (unit < 0 || unit >= cd->cd_ndevs) 2509 dv = NULL; 2510 else if ((dv = cd->cd_devs[unit]) != NULL && dv->dv_del_gen != 0) 2511 dv = NULL; 2512 mutex_exit(&alldevs_lock); 2513 2514 return dv; 2515 } 2516 2517 /* 2518 * device_lookup_private: 2519 * 2520 * Look up a softc instance for a given driver. 2521 */ 2522 void * 2523 device_lookup_private(cfdriver_t cd, int unit) 2524 { 2525 2526 return device_private(device_lookup(cd, unit)); 2527 } 2528 2529 /* 2530 * device_find_by_xname: 2531 * 2532 * Returns the device of the given name or NULL if it doesn't exist. 2533 */ 2534 device_t 2535 device_find_by_xname(const char *name) 2536 { 2537 device_t dv; 2538 deviter_t di; 2539 2540 for (dv = deviter_first(&di, 0); dv != NULL; dv = deviter_next(&di)) { 2541 if (strcmp(device_xname(dv), name) == 0) 2542 break; 2543 } 2544 deviter_release(&di); 2545 2546 return dv; 2547 } 2548 2549 /* 2550 * device_find_by_driver_unit: 2551 * 2552 * Returns the device of the given driver name and unit or 2553 * NULL if it doesn't exist. 2554 */ 2555 device_t 2556 device_find_by_driver_unit(const char *name, int unit) 2557 { 2558 struct cfdriver *cd; 2559 2560 if ((cd = config_cfdriver_lookup(name)) == NULL) 2561 return NULL; 2562 return device_lookup(cd, unit); 2563 } 2564 2565 static bool 2566 match_strcmp(const char * const s1, const char * const s2) 2567 { 2568 return strcmp(s1, s2) == 0; 2569 } 2570 2571 static bool 2572 match_pmatch(const char * const s1, const char * const s2) 2573 { 2574 return pmatch(s1, s2, NULL) == 2; 2575 } 2576 2577 static bool 2578 strarray_match_internal(const char ** const strings, 2579 unsigned int const nstrings, const char * const str, 2580 unsigned int * const indexp, 2581 bool (*match_fn)(const char *, const char *)) 2582 { 2583 unsigned int i; 2584 2585 if (strings == NULL || nstrings == 0) { 2586 return false; 2587 } 2588 2589 for (i = 0; i < nstrings; i++) { 2590 if ((*match_fn)(strings[i], str)) { 2591 *indexp = i; 2592 return true; 2593 } 2594 } 2595 2596 return false; 2597 } 2598 2599 static int 2600 strarray_match(const char ** const strings, unsigned int const nstrings, 2601 const char * const str) 2602 { 2603 unsigned int idx; 2604 2605 if (strarray_match_internal(strings, nstrings, str, &idx, 2606 match_strcmp)) { 2607 return (int)(nstrings - idx); 2608 } 2609 return 0; 2610 } 2611 2612 static int 2613 strarray_pmatch(const char ** const strings, unsigned int const nstrings, 2614 const char * const pattern) 2615 { 2616 unsigned int idx; 2617 2618 if (strarray_match_internal(strings, nstrings, pattern, &idx, 2619 match_pmatch)) { 2620 return (int)(nstrings - idx); 2621 } 2622 return 0; 2623 } 2624 2625 static int 2626 device_compatible_match_strarray_internal( 2627 const char **device_compats, int ndevice_compats, 2628 const struct device_compatible_entry *driver_compats, 2629 const struct device_compatible_entry **matching_entryp, 2630 int (*match_fn)(const char **, unsigned int, const char *)) 2631 { 2632 const struct device_compatible_entry *dce = NULL; 2633 int rv; 2634 2635 if (ndevice_compats == 0 || device_compats == NULL || 2636 driver_compats == NULL) 2637 return 0; 2638 2639 for (dce = driver_compats; dce->compat != NULL; dce++) { 2640 rv = (*match_fn)(device_compats, ndevice_compats, dce->compat); 2641 if (rv != 0) { 2642 if (matching_entryp != NULL) { 2643 *matching_entryp = dce; 2644 } 2645 return rv; 2646 } 2647 } 2648 return 0; 2649 } 2650 2651 /* 2652 * device_compatible_match: 2653 * 2654 * Match a driver's "compatible" data against a device's 2655 * "compatible" strings. Returns resulted weighted by 2656 * which device "compatible" string was matched. 2657 */ 2658 int 2659 device_compatible_match(const char **device_compats, int ndevice_compats, 2660 const struct device_compatible_entry *driver_compats) 2661 { 2662 return device_compatible_match_strarray_internal(device_compats, 2663 ndevice_compats, driver_compats, NULL, strarray_match); 2664 } 2665 2666 /* 2667 * device_compatible_pmatch: 2668 * 2669 * Like device_compatible_match(), but uses pmatch(9) to compare 2670 * the device "compatible" strings against patterns in the 2671 * driver's "compatible" data. 2672 */ 2673 int 2674 device_compatible_pmatch(const char **device_compats, int ndevice_compats, 2675 const struct device_compatible_entry *driver_compats) 2676 { 2677 return device_compatible_match_strarray_internal(device_compats, 2678 ndevice_compats, driver_compats, NULL, strarray_pmatch); 2679 } 2680 2681 static int 2682 device_compatible_match_strlist_internal( 2683 const char * const device_compats, size_t const device_compatsize, 2684 const struct device_compatible_entry *driver_compats, 2685 const struct device_compatible_entry **matching_entryp, 2686 int (*match_fn)(const char *, size_t, const char *)) 2687 { 2688 const struct device_compatible_entry *dce = NULL; 2689 int rv; 2690 2691 if (device_compats == NULL || device_compatsize == 0 || 2692 driver_compats == NULL) 2693 return 0; 2694 2695 for (dce = driver_compats; dce->compat != NULL; dce++) { 2696 rv = (*match_fn)(device_compats, device_compatsize, 2697 dce->compat); 2698 if (rv != 0) { 2699 if (matching_entryp != NULL) { 2700 *matching_entryp = dce; 2701 } 2702 return rv; 2703 } 2704 } 2705 return 0; 2706 } 2707 2708 /* 2709 * device_compatible_match_strlist: 2710 * 2711 * Like device_compatible_match(), but take the device 2712 * "compatible" strings as an OpenFirmware-style string 2713 * list. 2714 */ 2715 int 2716 device_compatible_match_strlist( 2717 const char * const device_compats, size_t const device_compatsize, 2718 const struct device_compatible_entry *driver_compats) 2719 { 2720 return device_compatible_match_strlist_internal(device_compats, 2721 device_compatsize, driver_compats, NULL, strlist_match); 2722 } 2723 2724 /* 2725 * device_compatible_pmatch_strlist: 2726 * 2727 * Like device_compatible_pmatch(), but take the device 2728 * "compatible" strings as an OpenFirmware-style string 2729 * list. 2730 */ 2731 int 2732 device_compatible_pmatch_strlist( 2733 const char * const device_compats, size_t const device_compatsize, 2734 const struct device_compatible_entry *driver_compats) 2735 { 2736 return device_compatible_match_strlist_internal(device_compats, 2737 device_compatsize, driver_compats, NULL, strlist_pmatch); 2738 } 2739 2740 static int 2741 device_compatible_match_id_internal( 2742 uintptr_t const id, uintptr_t const mask, uintptr_t const sentinel_id, 2743 const struct device_compatible_entry *driver_compats, 2744 const struct device_compatible_entry **matching_entryp) 2745 { 2746 const struct device_compatible_entry *dce = NULL; 2747 2748 if (mask == 0) 2749 return 0; 2750 2751 for (dce = driver_compats; dce->id != sentinel_id; dce++) { 2752 if ((id & mask) == dce->id) { 2753 if (matching_entryp != NULL) { 2754 *matching_entryp = dce; 2755 } 2756 return 1; 2757 } 2758 } 2759 return 0; 2760 } 2761 2762 /* 2763 * device_compatible_match_id: 2764 * 2765 * Like device_compatible_match(), but takes a single 2766 * unsigned integer device ID. 2767 */ 2768 int 2769 device_compatible_match_id( 2770 uintptr_t const id, uintptr_t const sentinel_id, 2771 const struct device_compatible_entry *driver_compats) 2772 { 2773 return device_compatible_match_id_internal(id, (uintptr_t)-1, 2774 sentinel_id, driver_compats, NULL); 2775 } 2776 2777 /* 2778 * device_compatible_lookup: 2779 * 2780 * Look up and return the device_compatible_entry, using the 2781 * same matching criteria used by device_compatible_match(). 2782 */ 2783 const struct device_compatible_entry * 2784 device_compatible_lookup(const char **device_compats, int ndevice_compats, 2785 const struct device_compatible_entry *driver_compats) 2786 { 2787 const struct device_compatible_entry *dce; 2788 2789 if (device_compatible_match_strarray_internal(device_compats, 2790 ndevice_compats, driver_compats, &dce, strarray_match)) { 2791 return dce; 2792 } 2793 return NULL; 2794 } 2795 2796 /* 2797 * device_compatible_plookup: 2798 * 2799 * Look up and return the device_compatible_entry, using the 2800 * same matching criteria used by device_compatible_pmatch(). 2801 */ 2802 const struct device_compatible_entry * 2803 device_compatible_plookup(const char **device_compats, int ndevice_compats, 2804 const struct device_compatible_entry *driver_compats) 2805 { 2806 const struct device_compatible_entry *dce; 2807 2808 if (device_compatible_match_strarray_internal(device_compats, 2809 ndevice_compats, driver_compats, &dce, strarray_pmatch)) { 2810 return dce; 2811 } 2812 return NULL; 2813 } 2814 2815 /* 2816 * device_compatible_lookup_strlist: 2817 * 2818 * Like device_compatible_lookup(), but take the device 2819 * "compatible" strings as an OpenFirmware-style string 2820 * list. 2821 */ 2822 const struct device_compatible_entry * 2823 device_compatible_lookup_strlist( 2824 const char * const device_compats, size_t const device_compatsize, 2825 const struct device_compatible_entry *driver_compats) 2826 { 2827 const struct device_compatible_entry *dce; 2828 2829 if (device_compatible_match_strlist_internal(device_compats, 2830 device_compatsize, driver_compats, &dce, strlist_match)) { 2831 return dce; 2832 } 2833 return NULL; 2834 } 2835 2836 /* 2837 * device_compatible_plookup_strlist: 2838 * 2839 * Like device_compatible_plookup(), but take the device 2840 * "compatible" strings as an OpenFirmware-style string 2841 * list. 2842 */ 2843 const struct device_compatible_entry * 2844 device_compatible_plookup_strlist( 2845 const char * const device_compats, size_t const device_compatsize, 2846 const struct device_compatible_entry *driver_compats) 2847 { 2848 const struct device_compatible_entry *dce; 2849 2850 if (device_compatible_match_strlist_internal(device_compats, 2851 device_compatsize, driver_compats, &dce, strlist_pmatch)) { 2852 return dce; 2853 } 2854 return NULL; 2855 } 2856 2857 /* 2858 * device_compatible_lookup_id: 2859 * 2860 * Like device_compatible_lookup(), but takes a single 2861 * unsigned integer device ID. 2862 */ 2863 const struct device_compatible_entry * 2864 device_compatible_lookup_id( 2865 uintptr_t const id, uintptr_t const sentinel_id, 2866 const struct device_compatible_entry *driver_compats) 2867 { 2868 const struct device_compatible_entry *dce; 2869 2870 if (device_compatible_match_id_internal(id, (uintptr_t)-1, 2871 sentinel_id, driver_compats, &dce)) { 2872 return dce; 2873 } 2874 return NULL; 2875 } 2876 2877 /* 2878 * Power management related functions. 2879 */ 2880 2881 bool 2882 device_pmf_is_registered(device_t dev) 2883 { 2884 return (dev->dv_flags & DVF_POWER_HANDLERS) != 0; 2885 } 2886 2887 bool 2888 device_pmf_driver_suspend(device_t dev, const pmf_qual_t *qual) 2889 { 2890 if ((dev->dv_flags & DVF_DRIVER_SUSPENDED) != 0) 2891 return true; 2892 if ((dev->dv_flags & DVF_CLASS_SUSPENDED) == 0) 2893 return false; 2894 if (pmf_qual_depth(qual) <= DEVACT_LEVEL_DRIVER && 2895 dev->dv_driver_suspend != NULL && 2896 !(*dev->dv_driver_suspend)(dev, qual)) 2897 return false; 2898 2899 dev->dv_flags |= DVF_DRIVER_SUSPENDED; 2900 return true; 2901 } 2902 2903 bool 2904 device_pmf_driver_resume(device_t dev, const pmf_qual_t *qual) 2905 { 2906 if ((dev->dv_flags & DVF_DRIVER_SUSPENDED) == 0) 2907 return true; 2908 if ((dev->dv_flags & DVF_BUS_SUSPENDED) != 0) 2909 return false; 2910 if (pmf_qual_depth(qual) <= DEVACT_LEVEL_DRIVER && 2911 dev->dv_driver_resume != NULL && 2912 !(*dev->dv_driver_resume)(dev, qual)) 2913 return false; 2914 2915 dev->dv_flags &= ~DVF_DRIVER_SUSPENDED; 2916 return true; 2917 } 2918 2919 bool 2920 device_pmf_driver_shutdown(device_t dev, int how) 2921 { 2922 2923 if (*dev->dv_driver_shutdown != NULL && 2924 !(*dev->dv_driver_shutdown)(dev, how)) 2925 return false; 2926 return true; 2927 } 2928 2929 bool 2930 device_pmf_driver_register(device_t dev, 2931 bool (*suspend)(device_t, const pmf_qual_t *), 2932 bool (*resume)(device_t, const pmf_qual_t *), 2933 bool (*shutdown)(device_t, int)) 2934 { 2935 dev->dv_driver_suspend = suspend; 2936 dev->dv_driver_resume = resume; 2937 dev->dv_driver_shutdown = shutdown; 2938 dev->dv_flags |= DVF_POWER_HANDLERS; 2939 return true; 2940 } 2941 2942 static const char * 2943 curlwp_name(void) 2944 { 2945 if (curlwp->l_name != NULL) 2946 return curlwp->l_name; 2947 else 2948 return curlwp->l_proc->p_comm; 2949 } 2950 2951 void 2952 device_pmf_driver_deregister(device_t dev) 2953 { 2954 device_lock_t dvl = device_getlock(dev); 2955 2956 dev->dv_driver_suspend = NULL; 2957 dev->dv_driver_resume = NULL; 2958 2959 mutex_enter(&dvl->dvl_mtx); 2960 dev->dv_flags &= ~DVF_POWER_HANDLERS; 2961 while (dvl->dvl_nlock > 0 || dvl->dvl_nwait > 0) { 2962 /* Wake a thread that waits for the lock. That 2963 * thread will fail to acquire the lock, and then 2964 * it will wake the next thread that waits for the 2965 * lock, or else it will wake us. 2966 */ 2967 cv_signal(&dvl->dvl_cv); 2968 pmflock_debug(dev, __func__, __LINE__); 2969 cv_wait(&dvl->dvl_cv, &dvl->dvl_mtx); 2970 pmflock_debug(dev, __func__, __LINE__); 2971 } 2972 mutex_exit(&dvl->dvl_mtx); 2973 } 2974 2975 bool 2976 device_pmf_driver_child_register(device_t dev) 2977 { 2978 device_t parent = device_parent(dev); 2979 2980 if (parent == NULL || parent->dv_driver_child_register == NULL) 2981 return true; 2982 return (*parent->dv_driver_child_register)(dev); 2983 } 2984 2985 void 2986 device_pmf_driver_set_child_register(device_t dev, 2987 bool (*child_register)(device_t)) 2988 { 2989 dev->dv_driver_child_register = child_register; 2990 } 2991 2992 static void 2993 pmflock_debug(device_t dev, const char *func, int line) 2994 { 2995 device_lock_t dvl = device_getlock(dev); 2996 2997 aprint_debug_dev(dev, 2998 "%s.%d, %s dvl_nlock %d dvl_nwait %d dv_flags %x\n", func, line, 2999 curlwp_name(), dvl->dvl_nlock, dvl->dvl_nwait, dev->dv_flags); 3000 } 3001 3002 static bool 3003 device_pmf_lock1(device_t dev) 3004 { 3005 device_lock_t dvl = device_getlock(dev); 3006 3007 while (device_pmf_is_registered(dev) && 3008 dvl->dvl_nlock > 0 && dvl->dvl_holder != curlwp) { 3009 dvl->dvl_nwait++; 3010 pmflock_debug(dev, __func__, __LINE__); 3011 cv_wait(&dvl->dvl_cv, &dvl->dvl_mtx); 3012 pmflock_debug(dev, __func__, __LINE__); 3013 dvl->dvl_nwait--; 3014 } 3015 if (!device_pmf_is_registered(dev)) { 3016 pmflock_debug(dev, __func__, __LINE__); 3017 /* We could not acquire the lock, but some other thread may 3018 * wait for it, also. Wake that thread. 3019 */ 3020 cv_signal(&dvl->dvl_cv); 3021 return false; 3022 } 3023 dvl->dvl_nlock++; 3024 dvl->dvl_holder = curlwp; 3025 pmflock_debug(dev, __func__, __LINE__); 3026 return true; 3027 } 3028 3029 bool 3030 device_pmf_lock(device_t dev) 3031 { 3032 bool rc; 3033 device_lock_t dvl = device_getlock(dev); 3034 3035 mutex_enter(&dvl->dvl_mtx); 3036 rc = device_pmf_lock1(dev); 3037 mutex_exit(&dvl->dvl_mtx); 3038 3039 return rc; 3040 } 3041 3042 void 3043 device_pmf_unlock(device_t dev) 3044 { 3045 device_lock_t dvl = device_getlock(dev); 3046 3047 KASSERT(dvl->dvl_nlock > 0); 3048 mutex_enter(&dvl->dvl_mtx); 3049 if (--dvl->dvl_nlock == 0) 3050 dvl->dvl_holder = NULL; 3051 cv_signal(&dvl->dvl_cv); 3052 pmflock_debug(dev, __func__, __LINE__); 3053 mutex_exit(&dvl->dvl_mtx); 3054 } 3055 3056 device_lock_t 3057 device_getlock(device_t dev) 3058 { 3059 return &dev->dv_lock; 3060 } 3061 3062 void * 3063 device_pmf_bus_private(device_t dev) 3064 { 3065 return dev->dv_bus_private; 3066 } 3067 3068 bool 3069 device_pmf_bus_suspend(device_t dev, const pmf_qual_t *qual) 3070 { 3071 if ((dev->dv_flags & DVF_BUS_SUSPENDED) != 0) 3072 return true; 3073 if ((dev->dv_flags & DVF_CLASS_SUSPENDED) == 0 || 3074 (dev->dv_flags & DVF_DRIVER_SUSPENDED) == 0) 3075 return false; 3076 if (pmf_qual_depth(qual) <= DEVACT_LEVEL_BUS && 3077 dev->dv_bus_suspend != NULL && 3078 !(*dev->dv_bus_suspend)(dev, qual)) 3079 return false; 3080 3081 dev->dv_flags |= DVF_BUS_SUSPENDED; 3082 return true; 3083 } 3084 3085 bool 3086 device_pmf_bus_resume(device_t dev, const pmf_qual_t *qual) 3087 { 3088 if ((dev->dv_flags & DVF_BUS_SUSPENDED) == 0) 3089 return true; 3090 if (pmf_qual_depth(qual) <= DEVACT_LEVEL_BUS && 3091 dev->dv_bus_resume != NULL && 3092 !(*dev->dv_bus_resume)(dev, qual)) 3093 return false; 3094 3095 dev->dv_flags &= ~DVF_BUS_SUSPENDED; 3096 return true; 3097 } 3098 3099 bool 3100 device_pmf_bus_shutdown(device_t dev, int how) 3101 { 3102 3103 if (*dev->dv_bus_shutdown != NULL && 3104 !(*dev->dv_bus_shutdown)(dev, how)) 3105 return false; 3106 return true; 3107 } 3108 3109 void 3110 device_pmf_bus_register(device_t dev, void *priv, 3111 bool (*suspend)(device_t, const pmf_qual_t *), 3112 bool (*resume)(device_t, const pmf_qual_t *), 3113 bool (*shutdown)(device_t, int), void (*deregister)(device_t)) 3114 { 3115 dev->dv_bus_private = priv; 3116 dev->dv_bus_resume = resume; 3117 dev->dv_bus_suspend = suspend; 3118 dev->dv_bus_shutdown = shutdown; 3119 dev->dv_bus_deregister = deregister; 3120 } 3121 3122 void 3123 device_pmf_bus_deregister(device_t dev) 3124 { 3125 if (dev->dv_bus_deregister == NULL) 3126 return; 3127 (*dev->dv_bus_deregister)(dev); 3128 dev->dv_bus_private = NULL; 3129 dev->dv_bus_suspend = NULL; 3130 dev->dv_bus_resume = NULL; 3131 dev->dv_bus_deregister = NULL; 3132 } 3133 3134 void * 3135 device_pmf_class_private(device_t dev) 3136 { 3137 return dev->dv_class_private; 3138 } 3139 3140 bool 3141 device_pmf_class_suspend(device_t dev, const pmf_qual_t *qual) 3142 { 3143 if ((dev->dv_flags & DVF_CLASS_SUSPENDED) != 0) 3144 return true; 3145 if (pmf_qual_depth(qual) <= DEVACT_LEVEL_CLASS && 3146 dev->dv_class_suspend != NULL && 3147 !(*dev->dv_class_suspend)(dev, qual)) 3148 return false; 3149 3150 dev->dv_flags |= DVF_CLASS_SUSPENDED; 3151 return true; 3152 } 3153 3154 bool 3155 device_pmf_class_resume(device_t dev, const pmf_qual_t *qual) 3156 { 3157 if ((dev->dv_flags & DVF_CLASS_SUSPENDED) == 0) 3158 return true; 3159 if ((dev->dv_flags & DVF_BUS_SUSPENDED) != 0 || 3160 (dev->dv_flags & DVF_DRIVER_SUSPENDED) != 0) 3161 return false; 3162 if (pmf_qual_depth(qual) <= DEVACT_LEVEL_CLASS && 3163 dev->dv_class_resume != NULL && 3164 !(*dev->dv_class_resume)(dev, qual)) 3165 return false; 3166 3167 dev->dv_flags &= ~DVF_CLASS_SUSPENDED; 3168 return true; 3169 } 3170 3171 void 3172 device_pmf_class_register(device_t dev, void *priv, 3173 bool (*suspend)(device_t, const pmf_qual_t *), 3174 bool (*resume)(device_t, const pmf_qual_t *), 3175 void (*deregister)(device_t)) 3176 { 3177 dev->dv_class_private = priv; 3178 dev->dv_class_suspend = suspend; 3179 dev->dv_class_resume = resume; 3180 dev->dv_class_deregister = deregister; 3181 } 3182 3183 void 3184 device_pmf_class_deregister(device_t dev) 3185 { 3186 if (dev->dv_class_deregister == NULL) 3187 return; 3188 (*dev->dv_class_deregister)(dev); 3189 dev->dv_class_private = NULL; 3190 dev->dv_class_suspend = NULL; 3191 dev->dv_class_resume = NULL; 3192 dev->dv_class_deregister = NULL; 3193 } 3194 3195 bool 3196 device_active(device_t dev, devactive_t type) 3197 { 3198 size_t i; 3199 3200 if (dev->dv_activity_count == 0) 3201 return false; 3202 3203 for (i = 0; i < dev->dv_activity_count; ++i) { 3204 if (dev->dv_activity_handlers[i] == NULL) 3205 break; 3206 (*dev->dv_activity_handlers[i])(dev, type); 3207 } 3208 3209 return true; 3210 } 3211 3212 bool 3213 device_active_register(device_t dev, void (*handler)(device_t, devactive_t)) 3214 { 3215 void (**new_handlers)(device_t, devactive_t); 3216 void (**old_handlers)(device_t, devactive_t); 3217 size_t i, old_size, new_size; 3218 int s; 3219 3220 old_handlers = dev->dv_activity_handlers; 3221 old_size = dev->dv_activity_count; 3222 3223 KASSERT(old_size == 0 || old_handlers != NULL); 3224 3225 for (i = 0; i < old_size; ++i) { 3226 KASSERT(old_handlers[i] != handler); 3227 if (old_handlers[i] == NULL) { 3228 old_handlers[i] = handler; 3229 return true; 3230 } 3231 } 3232 3233 new_size = old_size + 4; 3234 new_handlers = kmem_alloc(sizeof(void *) * new_size, KM_SLEEP); 3235 3236 for (i = 0; i < old_size; ++i) 3237 new_handlers[i] = old_handlers[i]; 3238 new_handlers[old_size] = handler; 3239 for (i = old_size+1; i < new_size; ++i) 3240 new_handlers[i] = NULL; 3241 3242 s = splhigh(); 3243 dev->dv_activity_count = new_size; 3244 dev->dv_activity_handlers = new_handlers; 3245 splx(s); 3246 3247 if (old_size > 0) 3248 kmem_free(old_handlers, sizeof(void *) * old_size); 3249 3250 return true; 3251 } 3252 3253 void 3254 device_active_deregister(device_t dev, void (*handler)(device_t, devactive_t)) 3255 { 3256 void (**old_handlers)(device_t, devactive_t); 3257 size_t i, old_size; 3258 int s; 3259 3260 old_handlers = dev->dv_activity_handlers; 3261 old_size = dev->dv_activity_count; 3262 3263 for (i = 0; i < old_size; ++i) { 3264 if (old_handlers[i] == handler) 3265 break; 3266 if (old_handlers[i] == NULL) 3267 return; /* XXX panic? */ 3268 } 3269 3270 if (i == old_size) 3271 return; /* XXX panic? */ 3272 3273 for (; i < old_size - 1; ++i) { 3274 if ((old_handlers[i] = old_handlers[i + 1]) != NULL) 3275 continue; 3276 3277 if (i == 0) { 3278 s = splhigh(); 3279 dev->dv_activity_count = 0; 3280 dev->dv_activity_handlers = NULL; 3281 splx(s); 3282 kmem_free(old_handlers, sizeof(void *) * old_size); 3283 } 3284 return; 3285 } 3286 old_handlers[i] = NULL; 3287 } 3288 3289 /* Return true iff the device_t `dev' exists at generation `gen'. */ 3290 static bool 3291 device_exists_at(device_t dv, devgen_t gen) 3292 { 3293 return (dv->dv_del_gen == 0 || dv->dv_del_gen > gen) && 3294 dv->dv_add_gen <= gen; 3295 } 3296 3297 static bool 3298 deviter_visits(const deviter_t *di, device_t dv) 3299 { 3300 return device_exists_at(dv, di->di_gen); 3301 } 3302 3303 /* 3304 * Device Iteration 3305 * 3306 * deviter_t: a device iterator. Holds state for a "walk" visiting 3307 * each device_t's in the device tree. 3308 * 3309 * deviter_init(di, flags): initialize the device iterator `di' 3310 * to "walk" the device tree. deviter_next(di) will return 3311 * the first device_t in the device tree, or NULL if there are 3312 * no devices. 3313 * 3314 * `flags' is one or more of DEVITER_F_RW, indicating that the 3315 * caller intends to modify the device tree by calling 3316 * config_detach(9) on devices in the order that the iterator 3317 * returns them; DEVITER_F_ROOT_FIRST, asking for the devices 3318 * nearest the "root" of the device tree to be returned, first; 3319 * DEVITER_F_LEAVES_FIRST, asking for the devices furthest from 3320 * the root of the device tree, first; and DEVITER_F_SHUTDOWN, 3321 * indicating both that deviter_init() should not respect any 3322 * locks on the device tree, and that deviter_next(di) may run 3323 * in more than one LWP before the walk has finished. 3324 * 3325 * Only one DEVITER_F_RW iterator may be in the device tree at 3326 * once. 3327 * 3328 * DEVITER_F_SHUTDOWN implies DEVITER_F_RW. 3329 * 3330 * Results are undefined if the flags DEVITER_F_ROOT_FIRST and 3331 * DEVITER_F_LEAVES_FIRST are used in combination. 3332 * 3333 * deviter_first(di, flags): initialize the device iterator `di' 3334 * and return the first device_t in the device tree, or NULL 3335 * if there are no devices. The statement 3336 * 3337 * dv = deviter_first(di); 3338 * 3339 * is shorthand for 3340 * 3341 * deviter_init(di); 3342 * dv = deviter_next(di); 3343 * 3344 * deviter_next(di): return the next device_t in the device tree, 3345 * or NULL if there are no more devices. deviter_next(di) 3346 * is undefined if `di' was not initialized with deviter_init() or 3347 * deviter_first(). 3348 * 3349 * deviter_release(di): stops iteration (subsequent calls to 3350 * deviter_next() will return NULL), releases any locks and 3351 * resources held by the device iterator. 3352 * 3353 * Device iteration does not return device_t's in any particular 3354 * order. An iterator will never return the same device_t twice. 3355 * Device iteration is guaranteed to complete---i.e., if deviter_next(di) 3356 * is called repeatedly on the same `di', it will eventually return 3357 * NULL. It is ok to attach/detach devices during device iteration. 3358 */ 3359 void 3360 deviter_init(deviter_t *di, deviter_flags_t flags) 3361 { 3362 device_t dv; 3363 3364 memset(di, 0, sizeof(*di)); 3365 3366 if ((flags & DEVITER_F_SHUTDOWN) != 0) 3367 flags |= DEVITER_F_RW; 3368 3369 mutex_enter(&alldevs_lock); 3370 if ((flags & DEVITER_F_RW) != 0) 3371 alldevs_nwrite++; 3372 else 3373 alldevs_nread++; 3374 di->di_gen = alldevs_gen++; 3375 di->di_flags = flags; 3376 3377 switch (di->di_flags & (DEVITER_F_LEAVES_FIRST|DEVITER_F_ROOT_FIRST)) { 3378 case DEVITER_F_LEAVES_FIRST: 3379 TAILQ_FOREACH(dv, &alldevs, dv_list) { 3380 if (!deviter_visits(di, dv)) 3381 continue; 3382 di->di_curdepth = MAX(di->di_curdepth, dv->dv_depth); 3383 } 3384 break; 3385 case DEVITER_F_ROOT_FIRST: 3386 TAILQ_FOREACH(dv, &alldevs, dv_list) { 3387 if (!deviter_visits(di, dv)) 3388 continue; 3389 di->di_maxdepth = MAX(di->di_maxdepth, dv->dv_depth); 3390 } 3391 break; 3392 default: 3393 break; 3394 } 3395 3396 deviter_reinit(di); 3397 mutex_exit(&alldevs_lock); 3398 } 3399 3400 static void 3401 deviter_reinit(deviter_t *di) 3402 { 3403 3404 KASSERT(mutex_owned(&alldevs_lock)); 3405 if ((di->di_flags & DEVITER_F_RW) != 0) 3406 di->di_prev = TAILQ_LAST(&alldevs, devicelist); 3407 else 3408 di->di_prev = TAILQ_FIRST(&alldevs); 3409 } 3410 3411 device_t 3412 deviter_first(deviter_t *di, deviter_flags_t flags) 3413 { 3414 3415 deviter_init(di, flags); 3416 return deviter_next(di); 3417 } 3418 3419 static device_t 3420 deviter_next2(deviter_t *di) 3421 { 3422 device_t dv; 3423 3424 KASSERT(mutex_owned(&alldevs_lock)); 3425 3426 dv = di->di_prev; 3427 3428 if (dv == NULL) 3429 return NULL; 3430 3431 if ((di->di_flags & DEVITER_F_RW) != 0) 3432 di->di_prev = TAILQ_PREV(dv, devicelist, dv_list); 3433 else 3434 di->di_prev = TAILQ_NEXT(dv, dv_list); 3435 3436 return dv; 3437 } 3438 3439 static device_t 3440 deviter_next1(deviter_t *di) 3441 { 3442 device_t dv; 3443 3444 KASSERT(mutex_owned(&alldevs_lock)); 3445 3446 do { 3447 dv = deviter_next2(di); 3448 } while (dv != NULL && !deviter_visits(di, dv)); 3449 3450 return dv; 3451 } 3452 3453 device_t 3454 deviter_next(deviter_t *di) 3455 { 3456 device_t dv = NULL; 3457 3458 mutex_enter(&alldevs_lock); 3459 switch (di->di_flags & (DEVITER_F_LEAVES_FIRST|DEVITER_F_ROOT_FIRST)) { 3460 case 0: 3461 dv = deviter_next1(di); 3462 break; 3463 case DEVITER_F_LEAVES_FIRST: 3464 while (di->di_curdepth >= 0) { 3465 if ((dv = deviter_next1(di)) == NULL) { 3466 di->di_curdepth--; 3467 deviter_reinit(di); 3468 } else if (dv->dv_depth == di->di_curdepth) 3469 break; 3470 } 3471 break; 3472 case DEVITER_F_ROOT_FIRST: 3473 while (di->di_curdepth <= di->di_maxdepth) { 3474 if ((dv = deviter_next1(di)) == NULL) { 3475 di->di_curdepth++; 3476 deviter_reinit(di); 3477 } else if (dv->dv_depth == di->di_curdepth) 3478 break; 3479 } 3480 break; 3481 default: 3482 break; 3483 } 3484 mutex_exit(&alldevs_lock); 3485 3486 return dv; 3487 } 3488 3489 void 3490 deviter_release(deviter_t *di) 3491 { 3492 bool rw = (di->di_flags & DEVITER_F_RW) != 0; 3493 3494 mutex_enter(&alldevs_lock); 3495 if (rw) 3496 --alldevs_nwrite; 3497 else 3498 --alldevs_nread; 3499 /* XXX wake a garbage-collection thread */ 3500 mutex_exit(&alldevs_lock); 3501 } 3502 3503 const char * 3504 cfdata_ifattr(const struct cfdata *cf) 3505 { 3506 return cf->cf_pspec->cfp_iattr; 3507 } 3508 3509 bool 3510 ifattr_match(const char *snull, const char *t) 3511 { 3512 return (snull == NULL) || strcmp(snull, t) == 0; 3513 } 3514 3515 void 3516 null_childdetached(device_t self, device_t child) 3517 { 3518 /* do nothing */ 3519 } 3520 3521 static void 3522 sysctl_detach_setup(struct sysctllog **clog) 3523 { 3524 3525 sysctl_createv(clog, 0, NULL, NULL, 3526 CTLFLAG_PERMANENT | CTLFLAG_READWRITE, 3527 CTLTYPE_BOOL, "detachall", 3528 SYSCTL_DESCR("Detach all devices at shutdown"), 3529 NULL, 0, &detachall, 0, 3530 CTL_KERN, CTL_CREATE, CTL_EOL); 3531 } 3532