1 /* $NetBSD: usb.c,v 1.28 1999/10/13 08:10:57 augustss Exp $ */ 2 3 /* 4 * Copyright (c) 1998 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 (augustss@carlstedt.se) 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/data/ and 43 * http://www.usb.org/developers/index.html . 44 */ 45 46 #include <sys/param.h> 47 #include <sys/systm.h> 48 #include <sys/kernel.h> 49 #include <sys/malloc.h> 50 #if defined(__NetBSD__) || defined(__OpenBSD__) 51 #include <sys/device.h> 52 #include <sys/kthread.h> 53 #elif defined(__FreeBSD__) 54 #include <sys/module.h> 55 #include <sys/bus.h> 56 #include <sys/ioccom.h> 57 #include <sys/uio.h> 58 #endif 59 #include <sys/conf.h> 60 #include <sys/poll.h> 61 #include <sys/proc.h> 62 #include <sys/select.h> 63 #include <sys/vnode.h> 64 #include <sys/signalvar.h> 65 66 #include <dev/usb/usb.h> 67 #include <dev/usb/usbdi.h> 68 #include <dev/usb/usbdi_util.h> 69 70 #define USB_DEV_MINOR 255 71 72 #if defined(__FreeBSD__) 73 MALLOC_DEFINE(M_USB, "USB", "USB"); 74 MALLOC_DEFINE(M_USBDEV, "USBdev", "USB device"); 75 MALLOC_DEFINE(M_USBHC, "USBHC", "USB host controller"); 76 77 #include "usb_if.h" 78 #endif /* defined(__FreeBSD__) */ 79 80 #include <machine/bus.h> 81 82 #include <dev/usb/usbdivar.h> 83 #include <dev/usb/usb_quirks.h> 84 85 #ifdef USB_DEBUG 86 #define DPRINTF(x) if (usbdebug) logprintf x 87 #define DPRINTFN(n,x) if (usbdebug>(n)) logprintf x 88 int usbdebug = 0; 89 int uhcidebug; 90 int ohcidebug; 91 int usb_noexplore = 0; 92 #else 93 #define DPRINTF(x) 94 #define DPRINTFN(n,x) 95 #endif 96 97 struct usb_softc { 98 USBBASEDEVICE sc_dev; /* base device */ 99 usbd_bus_handle sc_bus; /* USB controller */ 100 struct usbd_port sc_port; /* dummy port for root hub */ 101 102 struct selinfo sc_consel; /* waiting for connect change */ 103 struct proc *sc_event_thread; 104 105 char sc_dying; 106 }; 107 108 #if defined(__NetBSD__) || defined(__OpenBSD__) 109 cdev_decl(usb); 110 #elif defined(__FreeBSD__) 111 d_open_t usbopen; 112 d_close_t usbclose; 113 d_ioctl_t usbioctl; 114 int usbpoll __P((dev_t, int, struct proc *)); 115 116 struct cdevsw usb_cdevsw = { 117 /* open */ usbopen, 118 /* close */ usbclose, 119 /* read */ noread, 120 /* write */ nowrite, 121 /* ioctl */ usbioctl, 122 /* poll */ usbpoll, 123 /* mmap */ nommap, 124 /* strategy */ nostrategy, 125 /* name */ "usb", 126 /* maj */ USB_CDEV_MAJOR, 127 /* dump */ nodump, 128 /* psize */ nopsize, 129 /* flags */ 0, 130 /* bmaj */ -1 131 }; 132 #endif 133 134 usbd_status usb_discover __P((struct usb_softc *)); 135 void usb_create_event_thread __P((void *)); 136 void usb_event_thread __P((void *)); 137 138 #define USB_MAX_EVENTS 50 139 struct usb_event_q { 140 struct usb_event ue; 141 SIMPLEQ_ENTRY(usb_event_q) next; 142 }; 143 SIMPLEQ_HEAD(, usb_event_q) usb_events = SIMPLEQ_HEAD_INITIALIZER(usb_events); 144 int usb_nevents = 0; 145 struct selinfo usb_selevent; 146 struct proc *usb_async_proc; /* process who wants USB SIGIO */ 147 int usb_dev_open = 0; 148 149 int usb_get_next_event __P((struct usb_event *)); 150 151 /* Flag to see if we are in the cold boot process. */ 152 extern int cold; 153 154 USB_DECLARE_DRIVER(usb); 155 156 USB_MATCH(usb) 157 { 158 DPRINTF(("usbd_match\n")); 159 return (UMATCH_GENERIC); 160 } 161 162 USB_ATTACH(usb) 163 { 164 #if defined(__NetBSD__) || defined(__OpenBSD__) 165 struct usb_softc *sc = (struct usb_softc *)self; 166 #elif defined(__FreeBSD__) 167 struct usb_softc *sc = device_get_softc(self); 168 void *aux = device_get_ivars(self); 169 #endif 170 usbd_device_handle dev; 171 usbd_status r; 172 173 #if defined(__NetBSD__) || defined(__OpenBSD__) 174 printf("\n"); 175 #elif defined(__FreeBSD__) 176 sc->sc_dev = self; 177 #endif 178 179 DPRINTF(("usbd_attach\n")); 180 usbd_init(); 181 sc->sc_bus = aux; 182 sc->sc_bus->usbctl = sc; 183 sc->sc_port.power = USB_MAX_POWER; 184 r = usbd_new_device(USBDEV(sc->sc_dev), sc->sc_bus, 0, 0, 0, 185 &sc->sc_port); 186 187 if (r == USBD_NORMAL_COMPLETION) { 188 dev = sc->sc_port.device; 189 if (!dev->hub) { 190 sc->sc_dying = 1; 191 printf("%s: root device is not a hub\n", 192 USBDEVNAME(sc->sc_dev)); 193 USB_ATTACH_ERROR_RETURN; 194 } 195 sc->sc_bus->root_hub = dev; 196 #if 1 197 /* 198 * Turning this code off will delay attachment of USB devices 199 * until the USB event thread is running, which means that 200 * the keyboard will not work until after cold boot. 201 */ 202 if (cold) { 203 sc->sc_bus->use_polling++; 204 dev->hub->explore(sc->sc_bus->root_hub); 205 sc->sc_bus->use_polling--; 206 } 207 #endif 208 } else { 209 printf("%s: root hub problem, error=%d\n", 210 USBDEVNAME(sc->sc_dev), r); 211 sc->sc_dying = 1; 212 } 213 214 #if defined(__NetBSD__) || defined(__OpenBSD__) 215 kthread_create(usb_create_event_thread, sc); 216 #endif 217 218 #if defined(__FreeBSD__) 219 make_dev(&usb_cdevsw, device_get_unit(self), UID_ROOT, GID_OPERATOR, 220 0644, "usb%d", device_get_unit(self)); 221 #endif 222 223 USB_ATTACH_SUCCESS_RETURN; 224 } 225 226 #if defined(__NetBSD__) || defined(__OpenBSD__) 227 void 228 usb_create_event_thread(arg) 229 void *arg; 230 { 231 struct usb_softc *sc = arg; 232 233 if (kthread_create1(usb_event_thread, sc, &sc->sc_event_thread, 234 "%s", sc->sc_dev.dv_xname)) { 235 printf("%s: unable to create event thread for\n", 236 sc->sc_dev.dv_xname); 237 panic("usb_create_event_thread"); 238 } 239 } 240 241 void 242 usb_event_thread(arg) 243 void *arg; 244 { 245 struct usb_softc *sc = arg; 246 247 DPRINTF(("usb_event_thread: start\n")); 248 249 while (!sc->sc_dying) { 250 #ifdef USB_DEBUG 251 if (!usb_noexplore) 252 #endif 253 usb_discover(sc); 254 (void)tsleep(&sc->sc_bus->needs_explore, 255 PWAIT, "usbevt", hz*60); 256 DPRINTFN(2,("usb_event_thread: woke up\n")); 257 } 258 sc->sc_event_thread = 0; 259 260 /* In case parent is waiting for us to exit. */ 261 wakeup(sc); 262 263 DPRINTF(("usb_event_thread: exit\n")); 264 kthread_exit(0); 265 } 266 267 int 268 usbctlprint(aux, pnp) 269 void *aux; 270 const char *pnp; 271 { 272 /* only "usb"es can attach to host controllers */ 273 if (pnp) 274 printf("usb at %s", pnp); 275 276 return (UNCONF); 277 } 278 #endif /* defined(__NetBSD__) || defined(__OpenBSD__) */ 279 280 int 281 usbopen(dev, flag, mode, p) 282 dev_t dev; 283 int flag, mode; 284 struct proc *p; 285 { 286 int unit = minor(dev); 287 struct usb_softc *sc; 288 289 if (unit == USB_DEV_MINOR) { 290 if (usb_dev_open) 291 return (EBUSY); 292 usb_dev_open = 1; 293 usb_async_proc = 0; 294 return (0); 295 } 296 297 USB_GET_SC_OPEN(usb, unit, sc); 298 299 if (sc->sc_dying) 300 return (EIO); 301 302 return (0); 303 } 304 305 int 306 usbread(dev, uio, flag) 307 dev_t dev; 308 struct uio *uio; 309 int flag; 310 { 311 struct usb_event ue; 312 int s, error, n; 313 314 if (minor(dev) != USB_DEV_MINOR) 315 return (ENXIO); 316 317 if (uio->uio_resid != sizeof(struct usb_event)) 318 return (EINVAL); 319 320 error = 0; 321 s = splusb(); 322 for (;;) { 323 n = usb_get_next_event(&ue); 324 if (n != 0) 325 break; 326 if (flag & IO_NDELAY) { 327 error = EWOULDBLOCK; 328 break; 329 } 330 error = tsleep(&usb_events, PZERO | PCATCH, "usbrea", 0); 331 if (error) 332 break; 333 } 334 splx(s); 335 if (!error) 336 error = uiomove(&ue, uio->uio_resid, uio); 337 338 return (error); 339 } 340 341 int 342 usbclose(dev, flag, mode, p) 343 dev_t dev; 344 int flag, mode; 345 struct proc *p; 346 { 347 int unit = minor(dev); 348 349 if (unit == USB_DEV_MINOR) { 350 usb_async_proc = 0; 351 usb_dev_open = 0; 352 } 353 354 return (0); 355 } 356 357 int 358 usbioctl(devt, cmd, data, flag, p) 359 dev_t devt; 360 u_long cmd; 361 caddr_t data; 362 int flag; 363 struct proc *p; 364 { 365 struct usb_softc *sc; 366 int unit = minor(devt); 367 368 if (unit == USB_DEV_MINOR) { 369 switch (cmd) { 370 case FIONBIO: 371 /* All handled in the upper FS layer. */ 372 return (0); 373 374 case FIOASYNC: 375 if (*(int *)data) 376 usb_async_proc = p; 377 else 378 usb_async_proc = 0; 379 return (0); 380 381 default: 382 return (EINVAL); 383 } 384 } 385 386 USB_GET_SC(usb, unit, sc); 387 388 if (sc->sc_dying) 389 return (EIO); 390 391 switch (cmd) { 392 #if defined(__FreeBSD__) 393 case USB_DISCOVER: 394 usb_discover(sc); 395 break; 396 #endif 397 #ifdef USB_DEBUG 398 case USB_SETDEBUG: 399 usbdebug = uhcidebug = ohcidebug = *(int *)data; 400 break; 401 #endif 402 case USB_REQUEST: 403 { 404 struct usb_ctl_request *ur = (void *)data; 405 int len = UGETW(ur->request.wLength); 406 struct iovec iov; 407 struct uio uio; 408 void *ptr = 0; 409 int addr = ur->addr; 410 usbd_status r; 411 int error = 0; 412 413 DPRINTF(("usbioctl: USB_REQUEST addr=%d len=%d\n", addr, len)); 414 if (len < 0 || len > 32768) 415 return (EINVAL); 416 if (addr < 0 || addr >= USB_MAX_DEVICES || 417 sc->sc_bus->devices[addr] == 0) 418 return (EINVAL); 419 if (len != 0) { 420 iov.iov_base = (caddr_t)ur->data; 421 iov.iov_len = len; 422 uio.uio_iov = &iov; 423 uio.uio_iovcnt = 1; 424 uio.uio_resid = len; 425 uio.uio_offset = 0; 426 uio.uio_segflg = UIO_USERSPACE; 427 uio.uio_rw = 428 ur->request.bmRequestType & UT_READ ? 429 UIO_READ : UIO_WRITE; 430 uio.uio_procp = p; 431 ptr = malloc(len, M_TEMP, M_WAITOK); 432 if (uio.uio_rw == UIO_WRITE) { 433 error = uiomove(ptr, len, &uio); 434 if (error) 435 goto ret; 436 } 437 } 438 r = usbd_do_request_flags(sc->sc_bus->devices[addr], 439 &ur->request, ptr, 440 ur->flags, &ur->actlen); 441 if (r != USBD_NORMAL_COMPLETION) { 442 error = EIO; 443 goto ret; 444 } 445 if (len != 0) { 446 if (uio.uio_rw == UIO_READ) { 447 error = uiomove(ptr, len, &uio); 448 if (error) 449 goto ret; 450 } 451 } 452 ret: 453 if (ptr) 454 free(ptr, M_TEMP); 455 return (error); 456 } 457 458 case USB_DEVICEINFO: 459 { 460 struct usb_device_info *di = (void *)data; 461 int addr = di->addr; 462 usbd_device_handle devh; 463 464 if (addr < 1 || addr >= USB_MAX_DEVICES) 465 return (EINVAL); 466 devh = sc->sc_bus->devices[addr]; 467 if (devh == 0) 468 return (ENXIO); 469 usbd_fill_deviceinfo(devh, di); 470 break; 471 } 472 473 case USB_DEVICESTATS: 474 *(struct usb_device_stats *)data = sc->sc_bus->stats; 475 break; 476 477 default: 478 return (EINVAL); 479 } 480 return (0); 481 } 482 483 int 484 usbpoll(dev, events, p) 485 dev_t dev; 486 int events; 487 struct proc *p; 488 { 489 int revents, mask, s; 490 491 if (minor(dev) != USB_DEV_MINOR) 492 return (ENXIO); 493 494 revents = 0; 495 s = splusb(); 496 mask = POLLIN | POLLRDNORM; 497 if (events & mask) 498 if (usb_nevents > 0) 499 revents |= events & mask; 500 501 DPRINTFN(2, ("usbpoll: revents=0x%x\n", revents)); 502 if (revents == 0) { 503 if (events & mask) { 504 DPRINTFN(2, ("usbpoll: selrecord\n")); 505 selrecord(p, &usb_selevent); 506 } 507 } 508 splx(s); 509 return (revents); 510 } 511 512 /* Explore device tree from the root. */ 513 usbd_status 514 usb_discover(sc) 515 struct usb_softc *sc; 516 { 517 /* 518 * We need mutual exclusion while traversing the device tree, 519 * but this is guaranteed since this function is only called 520 * from the event thread for the controller. 521 */ 522 do { 523 sc->sc_bus->needs_explore = 0; 524 sc->sc_bus->root_hub->hub->explore(sc->sc_bus->root_hub); 525 } while (sc->sc_bus->needs_explore && !sc->sc_dying); 526 return (USBD_NORMAL_COMPLETION); 527 } 528 529 void 530 usb_needs_explore(bus) 531 usbd_bus_handle bus; 532 { 533 bus->needs_explore = 1; 534 wakeup(&bus->needs_explore); 535 } 536 537 /* Called at splusb() */ 538 int 539 usb_get_next_event(ue) 540 struct usb_event *ue; 541 { 542 struct usb_event_q *ueq; 543 544 if (usb_nevents <= 0) 545 return (0); 546 ueq = SIMPLEQ_FIRST(&usb_events); 547 *ue = ueq->ue; 548 SIMPLEQ_REMOVE_HEAD(&usb_events, ueq, next); 549 free(ueq, M_USBDEV); 550 usb_nevents--; 551 return (1); 552 } 553 554 void 555 usbd_add_event(type, devh) 556 int type; 557 usbd_device_handle devh; 558 { 559 struct usb_event_q *ueq; 560 struct usb_event ue; 561 struct timeval thetime; 562 int s; 563 564 s = splusb(); 565 if (++usb_nevents >= USB_MAX_EVENTS) { 566 /* Too many queued events, drop an old one. */ 567 DPRINTFN(-1,("usb: event dropped\n")); 568 (void)usb_get_next_event(&ue); 569 } 570 /* Don't want to wait here inside splusb() */ 571 ueq = malloc(sizeof *ueq, M_USBDEV, M_NOWAIT); 572 if (ueq == 0) { 573 printf("usb: no memory, event dropped\n"); 574 splx(s); 575 return; 576 } 577 ueq->ue.ue_type = type; 578 ueq->ue.ue_cookie = devh->cookie; 579 usbd_fill_deviceinfo(devh, &ueq->ue.ue_device); 580 microtime(&thetime); 581 TIMEVAL_TO_TIMESPEC(&thetime, &ueq->ue.ue_time); 582 SIMPLEQ_INSERT_TAIL(&usb_events, ueq, next); 583 wakeup(&usb_events); 584 selwakeup(&usb_selevent); 585 if (usb_async_proc) 586 psignal(usb_async_proc, SIGIO); 587 splx(s); 588 } 589 590 #if defined(__NetBSD__) || defined(__OpenBSD__) 591 int 592 usb_activate(self, act) 593 device_ptr_t self; 594 enum devact act; 595 { 596 struct usb_softc *sc = (struct usb_softc *)self; 597 usbd_device_handle dev = sc->sc_port.device; 598 int i, rv = 0; 599 600 switch (act) { 601 case DVACT_ACTIVATE: 602 return (EOPNOTSUPP); 603 break; 604 605 case DVACT_DEACTIVATE: 606 sc->sc_dying = 1; 607 if (dev && dev->cdesc && dev->subdevs) { 608 for (i = 0; dev->subdevs[i]; i++) 609 rv |= config_deactivate(dev->subdevs[i]); 610 } 611 break; 612 } 613 return (rv); 614 } 615 616 int 617 usb_detach(self, flags) 618 device_ptr_t self; 619 int flags; 620 { 621 struct usb_softc *sc = (struct usb_softc *)self; 622 623 DPRINTF(("usb_detach: start\n")); 624 625 sc->sc_dying = 1; 626 627 /* Make all devices disconnect. */ 628 if (sc->sc_port.device) 629 usb_disconnect_port(&sc->sc_port, self); 630 631 /* Kill off event thread. */ 632 if (sc->sc_event_thread) { 633 wakeup(&sc->sc_bus->needs_explore); 634 if (tsleep(sc, PWAIT, "usbdet", hz * 60)) 635 printf("%s: event thread didn't die\n", 636 USBDEVNAME(sc->sc_dev)); 637 DPRINTF(("usb_detach: event thread dead\n")); 638 } 639 640 usbd_finish(); 641 return (0); 642 } 643 #elif defined(__FreeBSD__) 644 int 645 usb_detach(device_t self) 646 { 647 DPRINTF(("%s: unload, prevented\n", USBDEVNAME(self))); 648 649 return (EINVAL); 650 } 651 #endif 652 653 654 #if defined(__FreeBSD__) 655 DRIVER_MODULE(usb, ohci, usb_driver, usb_devclass, 0, 0); 656 DRIVER_MODULE(usb, uhci, usb_driver, usb_devclass, 0, 0); 657 #endif 658