1 /* $NetBSD: usb.c,v 1.112 2008/04/24 15:35:28 ad Exp $ */ 2 3 /* 4 * Copyright (c) 1998, 2002, 2008 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Lennart Augustsson (lennart@augustsson.net) at 9 * Carlstedt Research & Technology. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 3. All advertising materials mentioning features or use of this software 20 * must display the following acknowledgement: 21 * This product includes software developed by the NetBSD 22 * Foundation, Inc. and its contributors. 23 * 4. Neither the name of The NetBSD Foundation nor the names of its 24 * contributors may be used to endorse or promote products derived 25 * from this software without specific prior written permission. 26 * 27 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 28 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 29 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 30 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 31 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 32 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 33 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 34 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 35 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 36 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 37 * POSSIBILITY OF SUCH DAMAGE. 38 */ 39 40 /* 41 * USB specifications and other documentation can be found at 42 * http://www.usb.org/developers/docs/ and 43 * http://www.usb.org/developers/devclass_docs/ 44 */ 45 46 #include <sys/cdefs.h> 47 __KERNEL_RCSID(0, "$NetBSD: usb.c,v 1.112 2008/04/24 15:35:28 ad Exp $"); 48 49 #include "opt_compat_netbsd.h" 50 51 #include "ohci.h" 52 #include "uhci.h" 53 54 #include <sys/param.h> 55 #include <sys/systm.h> 56 #include <sys/kernel.h> 57 #include <sys/malloc.h> 58 #include <sys/device.h> 59 #include <sys/kthread.h> 60 #include <sys/proc.h> 61 #include <sys/conf.h> 62 #include <sys/fcntl.h> 63 #include <sys/poll.h> 64 #include <sys/select.h> 65 #include <sys/vnode.h> 66 #include <sys/signalvar.h> 67 #include <sys/intr.h> 68 69 #include <dev/usb/usb.h> 70 #include <dev/usb/usbdi.h> 71 #include <dev/usb/usbdi_util.h> 72 73 #define USB_DEV_MINOR 255 74 75 #include <sys/bus.h> 76 77 #include <dev/usb/usbdivar.h> 78 #include <dev/usb/usb_quirks.h> 79 80 #ifdef USB_DEBUG 81 #define DPRINTF(x) if (usbdebug) logprintf x 82 #define DPRINTFN(n,x) if (usbdebug>(n)) logprintf x 83 int usbdebug = 0; 84 #if defined(UHCI_DEBUG) && NUHCI > 0 85 extern int uhcidebug; 86 #endif 87 #if defined(OHCI_DEBUG) && NOHCI > 0 88 extern int ohcidebug; 89 #endif 90 /* 91 * 0 - do usual exploration 92 * 1 - do not use timeout exploration 93 * >1 - do no exploration 94 */ 95 int usb_noexplore = 0; 96 #else 97 #define DPRINTF(x) 98 #define DPRINTFN(n,x) 99 #endif 100 101 struct usb_softc { 102 #if 0 103 USBBASEDEVICE sc_dev; /* base device */ 104 #endif 105 usbd_bus_handle sc_bus; /* USB controller */ 106 struct usbd_port sc_port; /* dummy port for root hub */ 107 108 struct lwp *sc_event_thread; 109 110 char sc_dying; 111 }; 112 113 struct usb_taskq { 114 TAILQ_HEAD(, usb_task) tasks; 115 struct lwp *task_thread_lwp; 116 const char *name; 117 int taskcreated; /* task thread exists. */ 118 }; 119 120 static struct usb_taskq usb_taskq[USB_NUM_TASKQS]; 121 122 dev_type_open(usbopen); 123 dev_type_close(usbclose); 124 dev_type_read(usbread); 125 dev_type_ioctl(usbioctl); 126 dev_type_poll(usbpoll); 127 dev_type_kqfilter(usbkqfilter); 128 129 const struct cdevsw usb_cdevsw = { 130 usbopen, usbclose, usbread, nowrite, usbioctl, 131 nostop, notty, usbpoll, nommap, usbkqfilter, D_OTHER, 132 }; 133 134 Static void usb_discover(struct usb_softc *); 135 Static void usb_create_event_thread(device_t); 136 Static void usb_event_thread(void *); 137 Static void usb_task_thread(void *); 138 139 #define USB_MAX_EVENTS 100 140 struct usb_event_q { 141 struct usb_event ue; 142 SIMPLEQ_ENTRY(usb_event_q) next; 143 }; 144 Static SIMPLEQ_HEAD(, usb_event_q) usb_events = 145 SIMPLEQ_HEAD_INITIALIZER(usb_events); 146 Static int usb_nevents = 0; 147 Static struct selinfo usb_selevent; 148 Static usb_proc_ptr usb_async_proc; /* process that wants USB SIGIO */ 149 Static void *usb_async_sih; 150 Static int usb_dev_open = 0; 151 Static struct usb_event *usb_alloc_event(void); 152 Static void usb_free_event(struct usb_event *); 153 Static void usb_add_event(int, struct usb_event *); 154 Static int usb_get_next_event(struct usb_event *); 155 Static void usb_async_intr(void *); 156 157 #ifdef COMPAT_30 158 Static void usb_copy_old_devinfo(struct usb_device_info_old *, const struct usb_device_info *); 159 #endif 160 161 Static const char *usbrev_str[] = USBREV_STR; 162 163 static int usb_match(device_t, struct cfdata *, void *); 164 static void usb_attach(device_t, device_t, void *); 165 static int usb_detach(device_t, int); 166 static int usb_activate(device_t, enum devact); 167 static void usb_childdet(device_t, device_t); 168 static void usb_doattach(device_t); 169 170 extern struct cfdriver usb_cd; 171 172 CFATTACH_DECL2_NEW(usb, sizeof(struct usb_softc), 173 usb_match, usb_attach, usb_detach, usb_activate, NULL, usb_childdet); 174 175 USB_MATCH(usb) 176 { 177 DPRINTF(("usbd_match\n")); 178 return (UMATCH_GENERIC); 179 } 180 181 USB_ATTACH(usb) 182 { 183 struct usb_softc *sc = device_private(self); 184 int usbrev; 185 186 sc->sc_bus = aux; 187 usbrev = sc->sc_bus->usbrev; 188 189 aprint_naive("\n"); 190 aprint_normal(": USB revision %s", usbrev_str[usbrev]); 191 switch (usbrev) { 192 case USBREV_1_0: 193 case USBREV_1_1: 194 case USBREV_2_0: 195 break; 196 default: 197 aprint_error(", not supported\n"); 198 sc->sc_dying = 1; 199 USB_ATTACH_ERROR_RETURN; 200 } 201 aprint_normal("\n"); 202 203 config_interrupts(self, usb_doattach); 204 } 205 206 static void 207 usb_doattach(device_t self) 208 { 209 static bool usb_selevent_init; /* XXX */ 210 struct usb_softc *sc = device_private(self); 211 usbd_device_handle dev; 212 usbd_status err; 213 int speed; 214 struct usb_event *ue; 215 216 if (!usb_selevent_init) { 217 selinit(&usb_selevent); 218 usb_selevent_init = true; 219 } 220 DPRINTF(("usbd_doattach\n")); 221 222 sc->sc_bus->usbctl = self; 223 sc->sc_port.power = USB_MAX_POWER; 224 225 switch (sc->sc_bus->usbrev) { 226 case USBREV_1_0: 227 case USBREV_1_1: 228 speed = USB_SPEED_FULL; 229 break; 230 case USBREV_2_0: 231 speed = USB_SPEED_HIGH; 232 break; 233 default: 234 panic("usb_doattach"); 235 } 236 237 ue = usb_alloc_event(); 238 ue->u.ue_ctrlr.ue_bus = device_unit(self); 239 usb_add_event(USB_EVENT_CTRLR_ATTACH, ue); 240 241 #ifdef USB_USE_SOFTINTR 242 /* XXX we should have our own level */ 243 sc->sc_bus->soft = softint_establish(SOFTINT_NET, 244 sc->sc_bus->methods->soft_intr, sc->sc_bus); 245 if (sc->sc_bus->soft == NULL) { 246 aprint_error("%s: can't register softintr\n", 247 device_xname(self)); 248 sc->sc_dying = 1; 249 USB_ATTACH_ERROR_RETURN; 250 } 251 #endif 252 253 err = usbd_new_device(self, sc->sc_bus, 0, speed, 0, 254 &sc->sc_port); 255 if (!err) { 256 dev = sc->sc_port.device; 257 if (dev->hub == NULL) { 258 sc->sc_dying = 1; 259 aprint_error("%s: root device is not a hub\n", 260 device_xname(self)); 261 USB_ATTACH_ERROR_RETURN; 262 } 263 sc->sc_bus->root_hub = dev; 264 #if 1 265 /* 266 * Turning this code off will delay attachment of USB devices 267 * until the USB event thread is running, which means that 268 * the keyboard will not work until after cold boot. 269 */ 270 if (cold && (device_cfdata(self)->cf_flags & 1)) 271 dev->hub->explore(sc->sc_bus->root_hub); 272 #endif 273 } else { 274 aprint_error("%s: root hub problem, error=%d\n", 275 device_xname(self), err); 276 sc->sc_dying = 1; 277 } 278 279 config_pending_incr(); 280 usb_create_event_thread(self); 281 282 if (!pmf_device_register(self, NULL, NULL)) 283 aprint_error_dev(self, "couldn't establish power handler\n"); 284 285 usb_async_sih = softint_establish(SOFTINT_CLOCK | SOFTINT_MPSAFE, 286 usb_async_intr, NULL); 287 288 USB_ATTACH_SUCCESS_RETURN; 289 } 290 291 static const char *taskq_names[] = USB_TASKQ_NAMES; 292 293 #if defined(__NetBSD__) || defined(__OpenBSD__) 294 void 295 usb_create_event_thread(device_t self) 296 { 297 struct usb_softc *sc = device_private(self); 298 struct usb_taskq *taskq; 299 int i; 300 301 if (usb_kthread_create1(PRI_NONE, 0, NULL, usb_event_thread, sc, 302 &sc->sc_event_thread, "%s", device_xname(self))) { 303 printf("%s: unable to create event thread for\n", 304 device_xname(self)); 305 panic("usb_create_event_thread"); 306 } 307 for (i = 0; i < USB_NUM_TASKQS; i++) { 308 taskq = &usb_taskq[i]; 309 310 if (taskq->taskcreated) 311 continue; 312 313 TAILQ_INIT(&taskq->tasks); 314 taskq->taskcreated = 1; 315 taskq->name = taskq_names[i]; 316 if (usb_kthread_create1(PRI_NONE, 0, NULL, usb_task_thread, 317 taskq, &taskq->task_thread_lwp, taskq->name)) { 318 printf("unable to create task thread: %s\n", taskq->name); 319 panic("usb_create_event_thread task"); 320 } 321 } 322 } 323 324 /* 325 * Add a task to be performed by the task thread. This function can be 326 * called from any context and the task will be executed in a process 327 * context ASAP. 328 */ 329 void 330 usb_add_task(usbd_device_handle dev, struct usb_task *task, int queue) 331 { 332 struct usb_taskq *taskq; 333 int s; 334 335 taskq = &usb_taskq[queue]; 336 s = splusb(); 337 if (task->queue == -1) { 338 DPRINTFN(2,("usb_add_task: task=%p\n", task)); 339 TAILQ_INSERT_TAIL(&taskq->tasks, task, next); 340 task->queue = queue; 341 } else { 342 DPRINTFN(3,("usb_add_task: task=%p on q\n", task)); 343 } 344 wakeup(&taskq->tasks); 345 splx(s); 346 } 347 348 void 349 usb_rem_task(usbd_device_handle dev, struct usb_task *task) 350 { 351 struct usb_taskq *taskq; 352 int s; 353 354 taskq = &usb_taskq[task->queue]; 355 s = splusb(); 356 if (task->queue != -1) { 357 TAILQ_REMOVE(&taskq->tasks, task, next); 358 task->queue = -1; 359 } 360 splx(s); 361 } 362 363 void 364 usb_event_thread(void *arg) 365 { 366 struct usb_softc *sc = arg; 367 368 DPRINTF(("usb_event_thread: start\n")); 369 370 /* 371 * In case this controller is a companion controller to an 372 * EHCI controller we need to wait until the EHCI controller 373 * has grabbed the port. 374 * XXX It would be nicer to do this with a tsleep(), but I don't 375 * know how to synchronize the creation of the threads so it 376 * will work. 377 */ 378 usb_delay_ms(sc->sc_bus, 500); 379 380 /* Make sure first discover does something. */ 381 sc->sc_bus->needs_explore = 1; 382 usb_discover(sc); 383 config_pending_decr(); 384 385 while (!sc->sc_dying) { 386 #ifdef USB_DEBUG 387 if (usb_noexplore < 2) 388 #endif 389 usb_discover(sc); 390 #ifdef USB_DEBUG 391 (void)tsleep(&sc->sc_bus->needs_explore, PWAIT, "usbevt", 392 usb_noexplore ? 0 : hz * 60); 393 #else 394 (void)tsleep(&sc->sc_bus->needs_explore, PWAIT, "usbevt", 395 hz * 60); 396 #endif 397 DPRINTFN(2,("usb_event_thread: woke up\n")); 398 } 399 sc->sc_event_thread = NULL; 400 401 /* In case parent is waiting for us to exit. */ 402 wakeup(sc); 403 404 DPRINTF(("usb_event_thread: exit\n")); 405 kthread_exit(0); 406 } 407 408 void 409 usb_task_thread(void *arg) 410 { 411 struct usb_task *task; 412 struct usb_taskq *taskq; 413 int s; 414 415 taskq = arg; 416 DPRINTF(("usb_task_thread: start taskq %s\n", taskq->name)); 417 418 s = splusb(); 419 for (;;) { 420 task = TAILQ_FIRST(&taskq->tasks); 421 if (task == NULL) { 422 tsleep(&taskq->tasks, PWAIT, "usbtsk", 0); 423 task = TAILQ_FIRST(&taskq->tasks); 424 } 425 DPRINTFN(2,("usb_task_thread: woke up task=%p\n", task)); 426 if (task != NULL) { 427 TAILQ_REMOVE(&taskq->tasks, task, next); 428 task->queue = -1; 429 splx(s); 430 task->fun(task->arg); 431 s = splusb(); 432 } 433 } 434 } 435 436 int 437 usbctlprint(void *aux, const char *pnp) 438 { 439 /* only "usb"es can attach to host controllers */ 440 if (pnp) 441 aprint_normal("usb at %s", pnp); 442 443 return (UNCONF); 444 } 445 #endif /* defined(__NetBSD__) || defined(__OpenBSD__) */ 446 447 int 448 usbopen(dev_t dev, int flag, int mode, struct lwp *l) 449 { 450 int unit = minor(dev); 451 struct usb_softc *sc; 452 453 if (unit == USB_DEV_MINOR) { 454 if (usb_dev_open) 455 return (EBUSY); 456 usb_dev_open = 1; 457 mutex_enter(proc_lock); 458 usb_async_proc = 0; 459 mutex_exit(proc_lock); 460 return (0); 461 } 462 463 sc = device_lookup_private(&usb_cd, unit); 464 if (!sc) 465 return (ENXIO); 466 467 if (sc->sc_dying) 468 return (EIO); 469 470 return (0); 471 } 472 473 int 474 usbread(dev_t dev, struct uio *uio, int flag) 475 { 476 struct usb_event *ue; 477 #ifdef COMPAT_30 478 struct usb_event_old *ueo = NULL; /* XXXGCC */ 479 #endif 480 int s, error, n, useold; 481 482 if (minor(dev) != USB_DEV_MINOR) 483 return (ENXIO); 484 485 useold = 0; 486 switch (uio->uio_resid) { 487 #ifdef COMPAT_30 488 case sizeof(struct usb_event_old): 489 ueo = malloc(sizeof(struct usb_event_old), M_USBDEV, 490 M_WAITOK|M_ZERO); 491 useold = 1; 492 /* FALLTHRU */ 493 #endif 494 case sizeof(struct usb_event): 495 ue = usb_alloc_event(); 496 break; 497 default: 498 return (EINVAL); 499 } 500 501 error = 0; 502 s = splusb(); 503 for (;;) { 504 n = usb_get_next_event(ue); 505 if (n != 0) 506 break; 507 if (flag & IO_NDELAY) { 508 error = EWOULDBLOCK; 509 break; 510 } 511 error = tsleep(&usb_events, PZERO | PCATCH, "usbrea", 0); 512 if (error) 513 break; 514 } 515 splx(s); 516 if (!error) { 517 #ifdef COMPAT_30 518 if (useold) { /* copy fields to old struct */ 519 ueo->ue_type = ue->ue_type; 520 memcpy(&ueo->ue_time, &ue->ue_time, 521 sizeof(struct timespec)); 522 switch (ue->ue_type) { 523 case USB_EVENT_DEVICE_ATTACH: 524 case USB_EVENT_DEVICE_DETACH: 525 usb_copy_old_devinfo(&ueo->u.ue_device, &ue->u.ue_device); 526 break; 527 528 case USB_EVENT_CTRLR_ATTACH: 529 case USB_EVENT_CTRLR_DETACH: 530 ueo->u.ue_ctrlr.ue_bus=ue->u.ue_ctrlr.ue_bus; 531 break; 532 533 case USB_EVENT_DRIVER_ATTACH: 534 case USB_EVENT_DRIVER_DETACH: 535 ueo->u.ue_driver.ue_cookie=ue->u.ue_driver.ue_cookie; 536 memcpy(ueo->u.ue_driver.ue_devname, 537 ue->u.ue_driver.ue_devname, 538 sizeof(ue->u.ue_driver.ue_devname)); 539 break; 540 default: 541 ; 542 } 543 544 error = uiomove((void *)ueo, sizeof *ueo, uio); 545 } else 546 #endif 547 error = uiomove((void *)ue, sizeof *ue, uio); 548 } 549 usb_free_event(ue); 550 #ifdef COMPAT_30 551 if (useold) 552 free(ueo, M_USBDEV); 553 #endif 554 555 return (error); 556 } 557 558 int 559 usbclose(dev_t dev, int flag, int mode, 560 struct lwp *l) 561 { 562 int unit = minor(dev); 563 564 if (unit == USB_DEV_MINOR) { 565 mutex_enter(proc_lock); 566 usb_async_proc = 0; 567 mutex_exit(proc_lock); 568 usb_dev_open = 0; 569 } 570 571 return (0); 572 } 573 574 int 575 usbioctl(dev_t devt, u_long cmd, void *data, int flag, struct lwp *l) 576 { 577 struct usb_softc *sc; 578 int unit = minor(devt); 579 580 if (unit == USB_DEV_MINOR) { 581 switch (cmd) { 582 case FIONBIO: 583 /* All handled in the upper FS layer. */ 584 return (0); 585 586 case FIOASYNC: 587 mutex_enter(proc_lock); 588 if (*(int *)data) 589 usb_async_proc = l->l_proc; 590 else 591 usb_async_proc = 0; 592 mutex_exit(proc_lock); 593 return (0); 594 595 default: 596 return (EINVAL); 597 } 598 } 599 600 sc = device_lookup_private(&usb_cd, unit); 601 602 if (sc->sc_dying) 603 return (EIO); 604 605 switch (cmd) { 606 #ifdef USB_DEBUG 607 case USB_SETDEBUG: 608 if (!(flag & FWRITE)) 609 return (EBADF); 610 usbdebug = ((*(int *)data) & 0x000000ff); 611 #if defined(UHCI_DEBUG) && NUHCI > 0 612 uhcidebug = ((*(int *)data) & 0x0000ff00) >> 8; 613 #endif 614 #if defined(OHCI_DEBUG) && NOHCI > 0 615 ohcidebug = ((*(int *)data) & 0x00ff0000) >> 16; 616 #endif 617 break; 618 #endif /* USB_DEBUG */ 619 case USB_REQUEST: 620 { 621 struct usb_ctl_request *ur = (void *)data; 622 int len = UGETW(ur->ucr_request.wLength); 623 struct iovec iov; 624 struct uio uio; 625 void *ptr = 0; 626 int addr = ur->ucr_addr; 627 usbd_status err; 628 int error = 0; 629 630 if (!(flag & FWRITE)) 631 return (EBADF); 632 633 DPRINTF(("usbioctl: USB_REQUEST addr=%d len=%d\n", addr, len)); 634 if (len < 0 || len > 32768) 635 return (EINVAL); 636 if (addr < 0 || addr >= USB_MAX_DEVICES || 637 sc->sc_bus->devices[addr] == 0) 638 return (EINVAL); 639 if (len != 0) { 640 iov.iov_base = (void *)ur->ucr_data; 641 iov.iov_len = len; 642 uio.uio_iov = &iov; 643 uio.uio_iovcnt = 1; 644 uio.uio_resid = len; 645 uio.uio_offset = 0; 646 uio.uio_rw = 647 ur->ucr_request.bmRequestType & UT_READ ? 648 UIO_READ : UIO_WRITE; 649 uio.uio_vmspace = l->l_proc->p_vmspace; 650 ptr = malloc(len, M_TEMP, M_WAITOK); 651 if (uio.uio_rw == UIO_WRITE) { 652 error = uiomove(ptr, len, &uio); 653 if (error) 654 goto ret; 655 } 656 } 657 err = usbd_do_request_flags(sc->sc_bus->devices[addr], 658 &ur->ucr_request, ptr, ur->ucr_flags, &ur->ucr_actlen, 659 USBD_DEFAULT_TIMEOUT); 660 if (err) { 661 error = EIO; 662 goto ret; 663 } 664 if (len > ur->ucr_actlen) 665 len = ur->ucr_actlen; 666 if (len != 0) { 667 if (uio.uio_rw == UIO_READ) { 668 error = uiomove(ptr, len, &uio); 669 if (error) 670 goto ret; 671 } 672 } 673 ret: 674 if (ptr) 675 free(ptr, M_TEMP); 676 return (error); 677 } 678 679 case USB_DEVICEINFO: 680 { 681 usbd_device_handle dev; 682 struct usb_device_info *di = (void *)data; 683 int addr = di->udi_addr; 684 685 if (addr < 1 || addr >= USB_MAX_DEVICES) 686 return EINVAL; 687 if ((dev = sc->sc_bus->devices[addr]) == NULL) 688 return ENXIO; 689 usbd_fill_deviceinfo(dev, di, 1); 690 break; 691 } 692 693 #ifdef COMPAT_30 694 case USB_DEVICEINFO_OLD: 695 { 696 usbd_device_handle dev; 697 struct usb_device_info_old *di = (void *)data; 698 int addr = di->udi_addr; 699 700 if (addr < 1 || addr >= USB_MAX_DEVICES) 701 return EINVAL; 702 if ((dev = sc->sc_bus->devices[addr]) == NULL) 703 return ENXIO; 704 usbd_fill_deviceinfo_old(dev, di, 1); 705 break; 706 } 707 #endif 708 709 case USB_DEVICESTATS: 710 *(struct usb_device_stats *)data = sc->sc_bus->stats; 711 break; 712 713 default: 714 return (EINVAL); 715 } 716 return (0); 717 } 718 719 int 720 usbpoll(dev_t dev, int events, struct lwp *l) 721 { 722 int revents, mask, s; 723 724 if (minor(dev) == USB_DEV_MINOR) { 725 revents = 0; 726 mask = POLLIN | POLLRDNORM; 727 728 s = splusb(); 729 if (events & mask && usb_nevents > 0) 730 revents |= events & mask; 731 if (revents == 0 && events & mask) 732 selrecord(l, &usb_selevent); 733 splx(s); 734 735 return (revents); 736 } else { 737 return (0); 738 } 739 } 740 741 static void 742 filt_usbrdetach(struct knote *kn) 743 { 744 int s; 745 746 s = splusb(); 747 SLIST_REMOVE(&usb_selevent.sel_klist, kn, knote, kn_selnext); 748 splx(s); 749 } 750 751 static int 752 filt_usbread(struct knote *kn, long hint) 753 { 754 755 if (usb_nevents == 0) 756 return (0); 757 758 kn->kn_data = sizeof(struct usb_event); 759 return (1); 760 } 761 762 static const struct filterops usbread_filtops = 763 { 1, NULL, filt_usbrdetach, filt_usbread }; 764 765 int 766 usbkqfilter(dev_t dev, struct knote *kn) 767 { 768 struct klist *klist; 769 int s; 770 771 switch (kn->kn_filter) { 772 case EVFILT_READ: 773 if (minor(dev) != USB_DEV_MINOR) 774 return (1); 775 klist = &usb_selevent.sel_klist; 776 kn->kn_fop = &usbread_filtops; 777 break; 778 779 default: 780 return (EINVAL); 781 } 782 783 kn->kn_hook = NULL; 784 785 s = splusb(); 786 SLIST_INSERT_HEAD(klist, kn, kn_selnext); 787 splx(s); 788 789 return (0); 790 } 791 792 /* Explore device tree from the root. */ 793 Static void 794 usb_discover(struct usb_softc *sc) 795 { 796 797 DPRINTFN(2,("usb_discover\n")); 798 #ifdef USB_DEBUG 799 if (usb_noexplore > 1) 800 return; 801 #endif 802 /* 803 * We need mutual exclusion while traversing the device tree, 804 * but this is guaranteed since this function is only called 805 * from the event thread for the controller. 806 */ 807 while (sc->sc_bus->needs_explore && !sc->sc_dying) { 808 sc->sc_bus->needs_explore = 0; 809 sc->sc_bus->root_hub->hub->explore(sc->sc_bus->root_hub); 810 } 811 } 812 813 void 814 usb_needs_explore(usbd_device_handle dev) 815 { 816 DPRINTFN(2,("usb_needs_explore\n")); 817 dev->bus->needs_explore = 1; 818 wakeup(&dev->bus->needs_explore); 819 } 820 821 void 822 usb_needs_reattach(usbd_device_handle dev) 823 { 824 DPRINTFN(2,("usb_needs_reattach\n")); 825 dev->powersrc->reattach = 1; 826 dev->bus->needs_explore = 1; 827 wakeup(&dev->bus->needs_explore); 828 } 829 830 /* Called at splusb() */ 831 int 832 usb_get_next_event(struct usb_event *ue) 833 { 834 struct usb_event_q *ueq; 835 836 if (usb_nevents <= 0) 837 return (0); 838 ueq = SIMPLEQ_FIRST(&usb_events); 839 #ifdef DIAGNOSTIC 840 if (ueq == NULL) { 841 printf("usb: usb_nevents got out of sync! %d\n", usb_nevents); 842 usb_nevents = 0; 843 return (0); 844 } 845 #endif 846 if (ue) 847 *ue = ueq->ue; 848 SIMPLEQ_REMOVE_HEAD(&usb_events, next); 849 usb_free_event((struct usb_event *)(void *)ueq); 850 usb_nevents--; 851 return (1); 852 } 853 854 void 855 usbd_add_dev_event(int type, usbd_device_handle udev) 856 { 857 struct usb_event *ue = usb_alloc_event(); 858 859 usbd_fill_deviceinfo(udev, &ue->u.ue_device, USB_EVENT_IS_ATTACH(type)); 860 usb_add_event(type, ue); 861 } 862 863 void 864 usbd_add_drv_event(int type, usbd_device_handle udev, device_ptr_t dev) 865 { 866 struct usb_event *ue = usb_alloc_event(); 867 868 ue->u.ue_driver.ue_cookie = udev->cookie; 869 strncpy(ue->u.ue_driver.ue_devname, USBDEVPTRNAME(dev), 870 sizeof ue->u.ue_driver.ue_devname); 871 usb_add_event(type, ue); 872 } 873 874 Static struct usb_event * 875 usb_alloc_event(void) 876 { 877 /* Yes, this is right; we allocate enough so that we can use it later */ 878 return malloc(sizeof(struct usb_event_q), M_USBDEV, M_WAITOK|M_ZERO); 879 } 880 881 Static void 882 usb_free_event(struct usb_event *uep) 883 { 884 free(uep, M_USBDEV); 885 } 886 887 Static void 888 usb_add_event(int type, struct usb_event *uep) 889 { 890 struct usb_event_q *ueq; 891 struct timeval thetime; 892 int s; 893 894 microtime(&thetime); 895 /* Don't want to wait here inside splusb() */ 896 ueq = (struct usb_event_q *)(void *)uep; 897 ueq->ue = *uep; 898 ueq->ue.ue_type = type; 899 TIMEVAL_TO_TIMESPEC(&thetime, &ueq->ue.ue_time); 900 901 s = splusb(); 902 if (++usb_nevents >= USB_MAX_EVENTS) { 903 /* Too many queued events, drop an old one. */ 904 DPRINTFN(-1,("usb: event dropped\n")); 905 (void)usb_get_next_event(0); 906 } 907 SIMPLEQ_INSERT_TAIL(&usb_events, ueq, next); 908 wakeup(&usb_events); 909 selnotify(&usb_selevent, 0, 0); 910 if (usb_async_proc != NULL) { 911 softint_schedule(usb_async_sih); 912 } 913 splx(s); 914 } 915 916 Static void 917 usb_async_intr(void *cookie) 918 { 919 proc_t *proc; 920 921 mutex_enter(proc_lock); 922 if ((proc = usb_async_proc) != NULL) 923 psignal(proc, SIGIO); 924 mutex_exit(proc_lock); 925 } 926 927 void 928 usb_schedsoftintr(usbd_bus_handle bus) 929 { 930 DPRINTFN(10,("usb_schedsoftintr: polling=%d\n", bus->use_polling)); 931 #ifdef USB_USE_SOFTINTR 932 if (bus->use_polling) { 933 bus->methods->soft_intr(bus); 934 } else { 935 softint_schedule(bus->soft); 936 } 937 #else 938 bus->methods->soft_intr(bus); 939 #endif /* USB_USE_SOFTINTR */ 940 } 941 942 int 943 usb_activate(device_t self, enum devact act) 944 { 945 struct usb_softc *sc = device_private(self); 946 usbd_device_handle dev = sc->sc_port.device; 947 int i, rv = 0; 948 949 switch (act) { 950 case DVACT_ACTIVATE: 951 return (EOPNOTSUPP); 952 953 case DVACT_DEACTIVATE: 954 sc->sc_dying = 1; 955 if (dev != NULL && dev->cdesc != NULL && dev->subdevs != NULL) { 956 for (i = 0; dev->subdevs[i]; i++) 957 rv |= config_deactivate(dev->subdevs[i]); 958 } 959 break; 960 } 961 return (rv); 962 } 963 964 void 965 usb_childdet(device_t self, device_t child) 966 { 967 int i, last = -1; 968 struct usb_softc *sc = device_private(self); 969 struct usbd_device *dev; 970 971 if ((dev = sc->sc_port.device) == NULL || dev->subdevs == NULL) 972 return; 973 974 for (i = 0; dev->subdevs[i] != NULL; i++) 975 last = i; 976 977 for (i = 0; dev->subdevs[i] != NULL; i++) { 978 if (dev->subdevs[i] == child) { 979 dev->subdevs[i] = dev->subdevs[last]; 980 dev->subdevs[last] = NULL; 981 } 982 } 983 } 984 985 int 986 usb_detach(device_t self, int flags) 987 { 988 struct usb_softc *sc = device_private(self); 989 struct usb_event *ue; 990 991 DPRINTF(("usb_detach: start\n")); 992 993 pmf_device_deregister(self); 994 /* Kill off event thread. */ 995 while (sc->sc_event_thread != NULL) { 996 wakeup(&sc->sc_bus->needs_explore); 997 tsleep(sc, PWAIT, "usbdet", hz * 60); 998 } 999 DPRINTF(("usb_detach: event thread dead\n")); 1000 1001 /* Make all devices disconnect. */ 1002 if (sc->sc_port.device != NULL) 1003 usb_disconnect_port(&sc->sc_port, self); 1004 1005 #ifdef USB_USE_SOFTINTR 1006 if (sc->sc_bus->soft != NULL) { 1007 softint_disestablish(sc->sc_bus->soft); 1008 sc->sc_bus->soft = NULL; 1009 } 1010 #endif 1011 1012 ue = usb_alloc_event(); 1013 ue->u.ue_ctrlr.ue_bus = device_unit(self); 1014 usb_add_event(USB_EVENT_CTRLR_DETACH, ue); 1015 1016 return (0); 1017 } 1018 1019 #ifdef COMPAT_30 1020 Static void 1021 usb_copy_old_devinfo(struct usb_device_info_old *uo, 1022 const struct usb_device_info *ue) 1023 { 1024 const unsigned char *p; 1025 unsigned char *q; 1026 int i, n; 1027 1028 uo->udi_bus = ue->udi_bus; 1029 uo->udi_addr = ue->udi_addr; 1030 uo->udi_cookie = ue->udi_cookie; 1031 for (i = 0, p = (const unsigned char *)ue->udi_product, 1032 q = (unsigned char *)uo->udi_product; 1033 *p && i < USB_MAX_STRING_LEN - 1; p++) { 1034 if (*p < 0x80) 1035 q[i++] = *p; 1036 else { 1037 q[i++] = '?'; 1038 if ((*p & 0xe0) == 0xe0) 1039 p++; 1040 p++; 1041 } 1042 } 1043 q[i] = 0; 1044 1045 for (i = 0, p = ue->udi_vendor, q = uo->udi_vendor; 1046 *p && i < USB_MAX_STRING_LEN - 1; p++) { 1047 if (* p < 0x80) 1048 q[i++] = *p; 1049 else { 1050 q[i++] = '?'; 1051 p++; 1052 if ((*p & 0xe0) == 0xe0) 1053 p++; 1054 } 1055 } 1056 q[i] = 0; 1057 1058 memcpy(uo->udi_release, ue->udi_release, sizeof(uo->udi_release)); 1059 1060 uo->udi_productNo = ue->udi_productNo; 1061 uo->udi_vendorNo = ue->udi_vendorNo; 1062 uo->udi_releaseNo = ue->udi_releaseNo; 1063 uo->udi_class = ue->udi_class; 1064 uo->udi_subclass = ue->udi_subclass; 1065 uo->udi_protocol = ue->udi_protocol; 1066 uo->udi_config = ue->udi_config; 1067 uo->udi_speed = ue->udi_speed; 1068 uo->udi_power = ue->udi_power; 1069 uo->udi_nports = ue->udi_nports; 1070 1071 for (n=0; n<USB_MAX_DEVNAMES; n++) 1072 memcpy(uo->udi_devnames[n], 1073 ue->udi_devnames[n], USB_MAX_DEVNAMELEN); 1074 memcpy(uo->udi_ports, ue->udi_ports, sizeof(uo->udi_ports)); 1075 } 1076 #endif 1077