1 /* $OpenBSD: uhci.c,v 1.149 2020/02/22 14:01:34 jasper Exp $ */ 2 /* $NetBSD: uhci.c,v 1.172 2003/02/23 04:19:26 simonb Exp $ */ 3 /* $FreeBSD: src/sys/dev/usb/uhci.c,v 1.33 1999/11/17 22:33:41 n_hibma Exp $ */ 4 5 /* 6 * Copyright (c) 1998 The NetBSD Foundation, Inc. 7 * All rights reserved. 8 * 9 * This code is derived from software contributed to The NetBSD Foundation 10 * by Lennart Augustsson (lennart@augustsson.net) at 11 * Carlstedt Research & Technology. 12 * 13 * Redistribution and use in source and binary forms, with or without 14 * modification, are permitted provided that the following conditions 15 * are met: 16 * 1. Redistributions of source code must retain the above copyright 17 * notice, this list of conditions and the following disclaimer. 18 * 2. Redistributions in binary form must reproduce the above copyright 19 * notice, this list of conditions and the following disclaimer in the 20 * documentation and/or other materials provided with the distribution. 21 * 22 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 23 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 24 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 25 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 26 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 27 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 28 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 29 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 30 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 31 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 32 * POSSIBILITY OF SUCH DAMAGE. 33 */ 34 35 #include <sys/param.h> 36 #include <sys/systm.h> 37 #include <sys/malloc.h> 38 #include <sys/device.h> 39 #include <sys/queue.h> 40 #include <sys/timeout.h> 41 #include <sys/pool.h> 42 #include <sys/endian.h> 43 44 #include <machine/bus.h> 45 46 #include <dev/usb/usb.h> 47 #include <dev/usb/usbdi.h> 48 #include <dev/usb/usbdivar.h> 49 #include <dev/usb/usb_mem.h> 50 51 #include <dev/usb/uhcireg.h> 52 #include <dev/usb/uhcivar.h> 53 54 /* Use bandwidth reclamation for control transfers. Some devices choke on it. */ 55 /*#define UHCI_CTL_LOOP */ 56 57 struct cfdriver uhci_cd = { 58 NULL, "uhci", DV_DULL 59 }; 60 61 #ifdef UHCI_DEBUG 62 struct uhci_softc *thesc; 63 #define DPRINTF(x) if (uhcidebug) printf x 64 #define DPRINTFN(n,x) if (uhcidebug>(n)) printf x 65 int uhcidebug = 0; 66 int uhcinoloop = 0; 67 #define bitmask_snprintf(q,f,b,l) snprintf((b), (l), "%b", (q), (f)) 68 #else 69 #define DPRINTF(x) 70 #define DPRINTFN(n,x) 71 #endif 72 73 struct pool *uhcixfer; 74 75 struct uhci_pipe { 76 struct usbd_pipe pipe; 77 int nexttoggle; 78 79 union { 80 /* Control pipe */ 81 struct { 82 struct uhci_soft_qh *sqh; 83 struct usb_dma reqdma; 84 struct uhci_soft_td *setup, *stat; 85 u_int length; 86 } ctl; 87 /* Interrupt pipe */ 88 struct { 89 int npoll; 90 int isread; 91 struct uhci_soft_qh **qhs; 92 } intr; 93 /* Bulk pipe */ 94 struct { 95 struct uhci_soft_qh *sqh; 96 u_int length; 97 int isread; 98 } bulk; 99 /* Iso pipe */ 100 struct iso { 101 struct uhci_soft_td **stds; 102 int next, inuse; 103 } iso; 104 } u; 105 }; 106 107 void uhci_globalreset(struct uhci_softc *); 108 usbd_status uhci_portreset(struct uhci_softc *, int); 109 void uhci_reset(struct uhci_softc *); 110 usbd_status uhci_run(struct uhci_softc *, int run); 111 struct uhci_soft_td *uhci_alloc_std(struct uhci_softc *); 112 void uhci_free_std(struct uhci_softc *, struct uhci_soft_td *); 113 struct uhci_soft_qh *uhci_alloc_sqh(struct uhci_softc *); 114 void uhci_free_sqh(struct uhci_softc *, struct uhci_soft_qh *); 115 116 void uhci_free_std_chain(struct uhci_softc *, 117 struct uhci_soft_td *, struct uhci_soft_td *); 118 usbd_status uhci_alloc_std_chain(struct uhci_softc *, u_int, 119 struct usbd_xfer *, struct uhci_soft_td **, 120 struct uhci_soft_td **); 121 void uhci_poll_hub(void *); 122 void uhci_check_intr(struct uhci_softc *, struct usbd_xfer *); 123 void uhci_idone(struct usbd_xfer *); 124 125 void uhci_abort_xfer(struct usbd_xfer *, usbd_status status); 126 127 void uhci_timeout(void *); 128 void uhci_timeout_task(void *); 129 void uhci_add_ls_ctrl(struct uhci_softc *, struct uhci_soft_qh *); 130 void uhci_add_hs_ctrl(struct uhci_softc *, struct uhci_soft_qh *); 131 void uhci_add_bulk(struct uhci_softc *, struct uhci_soft_qh *); 132 void uhci_remove_ls_ctrl(struct uhci_softc *, struct uhci_soft_qh *); 133 void uhci_remove_hs_ctrl(struct uhci_softc *, struct uhci_soft_qh *); 134 void uhci_remove_bulk(struct uhci_softc *,struct uhci_soft_qh *); 135 void uhci_add_loop(struct uhci_softc *sc); 136 void uhci_rem_loop(struct uhci_softc *sc); 137 138 usbd_status uhci_setup_isoc(struct usbd_pipe *pipe); 139 void uhci_device_isoc_enter(struct usbd_xfer *); 140 141 struct usbd_xfer *uhci_allocx(struct usbd_bus *); 142 void uhci_freex(struct usbd_bus *, struct usbd_xfer *); 143 144 usbd_status uhci_device_ctrl_transfer(struct usbd_xfer *); 145 usbd_status uhci_device_ctrl_start(struct usbd_xfer *); 146 void uhci_device_ctrl_abort(struct usbd_xfer *); 147 void uhci_device_ctrl_close(struct usbd_pipe *); 148 void uhci_device_ctrl_done(struct usbd_xfer *); 149 150 usbd_status uhci_device_intr_transfer(struct usbd_xfer *); 151 usbd_status uhci_device_intr_start(struct usbd_xfer *); 152 void uhci_device_intr_abort(struct usbd_xfer *); 153 void uhci_device_intr_close(struct usbd_pipe *); 154 void uhci_device_intr_done(struct usbd_xfer *); 155 156 usbd_status uhci_device_bulk_transfer(struct usbd_xfer *); 157 usbd_status uhci_device_bulk_start(struct usbd_xfer *); 158 void uhci_device_bulk_abort(struct usbd_xfer *); 159 void uhci_device_bulk_close(struct usbd_pipe *); 160 void uhci_device_bulk_done(struct usbd_xfer *); 161 162 usbd_status uhci_device_isoc_transfer(struct usbd_xfer *); 163 usbd_status uhci_device_isoc_start(struct usbd_xfer *); 164 void uhci_device_isoc_abort(struct usbd_xfer *); 165 void uhci_device_isoc_close(struct usbd_pipe *); 166 void uhci_device_isoc_done(struct usbd_xfer *); 167 168 usbd_status uhci_root_ctrl_transfer(struct usbd_xfer *); 169 usbd_status uhci_root_ctrl_start(struct usbd_xfer *); 170 void uhci_root_ctrl_abort(struct usbd_xfer *); 171 void uhci_root_ctrl_close(struct usbd_pipe *); 172 void uhci_root_ctrl_done(struct usbd_xfer *); 173 174 usbd_status uhci_root_intr_transfer(struct usbd_xfer *); 175 usbd_status uhci_root_intr_start(struct usbd_xfer *); 176 void uhci_root_intr_abort(struct usbd_xfer *); 177 void uhci_root_intr_close(struct usbd_pipe *); 178 void uhci_root_intr_done(struct usbd_xfer *); 179 180 usbd_status uhci_open(struct usbd_pipe *); 181 void uhci_poll(struct usbd_bus *); 182 void uhci_softintr(void *); 183 184 usbd_status uhci_device_request(struct usbd_xfer *xfer); 185 186 void uhci_add_intr(struct uhci_softc *, struct uhci_soft_qh *); 187 void uhci_remove_intr(struct uhci_softc *, struct uhci_soft_qh *); 188 usbd_status uhci_device_setintr(struct uhci_softc *sc, 189 struct uhci_pipe *pipe, int ival); 190 191 void uhci_device_clear_toggle(struct usbd_pipe *pipe); 192 193 static inline struct uhci_soft_qh *uhci_find_prev_qh(struct uhci_soft_qh *, 194 struct uhci_soft_qh *); 195 196 #ifdef UHCI_DEBUG 197 void uhci_dump_all(struct uhci_softc *); 198 void uhci_dumpregs(struct uhci_softc *); 199 void uhci_dump_qhs(struct uhci_soft_qh *); 200 void uhci_dump_qh(struct uhci_soft_qh *); 201 void uhci_dump_tds(struct uhci_soft_td *); 202 void uhci_dump_td(struct uhci_soft_td *); 203 void uhci_dump_xfer(struct uhci_xfer *); 204 void uhci_dump(void); 205 #endif 206 207 #define UBARR(sc) bus_space_barrier((sc)->iot, (sc)->ioh, 0, (sc)->sc_size, \ 208 BUS_SPACE_BARRIER_READ|BUS_SPACE_BARRIER_WRITE) 209 #define UWRITE1(sc, r, x) \ 210 do { UBARR(sc); bus_space_write_1((sc)->iot, (sc)->ioh, (r), (x)); \ 211 } while (/*CONSTCOND*/0) 212 #define UWRITE2(sc, r, x) \ 213 do { UBARR(sc); bus_space_write_2((sc)->iot, (sc)->ioh, (r), (x)); \ 214 } while (/*CONSTCOND*/0) 215 #define UWRITE4(sc, r, x) \ 216 do { UBARR(sc); bus_space_write_4((sc)->iot, (sc)->ioh, (r), (x)); \ 217 } while (/*CONSTCOND*/0) 218 219 __unused static __inline u_int8_t 220 UREAD1(struct uhci_softc *sc, bus_size_t r) 221 { 222 UBARR(sc); 223 return bus_space_read_1(sc->iot, sc->ioh, r); 224 } 225 226 __unused static __inline u_int16_t 227 UREAD2(struct uhci_softc *sc, bus_size_t r) 228 { 229 UBARR(sc); 230 return bus_space_read_2(sc->iot, sc->ioh, r); 231 } 232 233 __unused static __inline u_int32_t 234 UREAD4(struct uhci_softc *sc, bus_size_t r) 235 { 236 UBARR(sc); 237 return bus_space_read_4(sc->iot, sc->ioh, r); 238 } 239 240 #define UHCICMD(sc, cmd) UWRITE2(sc, UHCI_CMD, cmd) 241 #define UHCISTS(sc) UREAD2(sc, UHCI_STS) 242 243 #define UHCI_RESET_TIMEOUT 100 /* ms, reset timeout */ 244 245 #define UHCI_CURFRAME(sc) (UREAD2(sc, UHCI_FRNUM) & UHCI_FRNUM_MASK) 246 247 #define UHCI_INTR_ENDPT 1 248 249 struct usbd_bus_methods uhci_bus_methods = { 250 .open_pipe = uhci_open, 251 .dev_setaddr = usbd_set_address, 252 .soft_intr = uhci_softintr, 253 .do_poll = uhci_poll, 254 .allocx = uhci_allocx, 255 .freex = uhci_freex, 256 }; 257 258 struct usbd_pipe_methods uhci_root_ctrl_methods = { 259 .transfer = uhci_root_ctrl_transfer, 260 .start = uhci_root_ctrl_start, 261 .abort = uhci_root_ctrl_abort, 262 .close = uhci_root_ctrl_close, 263 .done = uhci_root_ctrl_done, 264 }; 265 266 struct usbd_pipe_methods uhci_root_intr_methods = { 267 .transfer = uhci_root_intr_transfer, 268 .start = uhci_root_intr_start, 269 .abort = uhci_root_intr_abort, 270 .close = uhci_root_intr_close, 271 .done = uhci_root_intr_done, 272 }; 273 274 struct usbd_pipe_methods uhci_device_ctrl_methods = { 275 .transfer = uhci_device_ctrl_transfer, 276 .start = uhci_device_ctrl_start, 277 .abort = uhci_device_ctrl_abort, 278 .close = uhci_device_ctrl_close, 279 .done = uhci_device_ctrl_done, 280 }; 281 282 struct usbd_pipe_methods uhci_device_intr_methods = { 283 .transfer = uhci_device_intr_transfer, 284 .start = uhci_device_intr_start, 285 .abort = uhci_device_intr_abort, 286 .close = uhci_device_intr_close, 287 .cleartoggle = uhci_device_clear_toggle, 288 .done = uhci_device_intr_done, 289 }; 290 291 struct usbd_pipe_methods uhci_device_bulk_methods = { 292 .transfer = uhci_device_bulk_transfer, 293 .start = uhci_device_bulk_start, 294 .abort = uhci_device_bulk_abort, 295 .close = uhci_device_bulk_close, 296 .cleartoggle = uhci_device_clear_toggle, 297 .done = uhci_device_bulk_done, 298 }; 299 300 struct usbd_pipe_methods uhci_device_isoc_methods = { 301 .transfer = uhci_device_isoc_transfer, 302 .start = uhci_device_isoc_start, 303 .abort = uhci_device_isoc_abort, 304 .close = uhci_device_isoc_close, 305 .done = uhci_device_isoc_done, 306 }; 307 308 #define uhci_add_intr_list(sc, ex) \ 309 LIST_INSERT_HEAD(&(sc)->sc_intrhead, (ex), inext) 310 #define uhci_del_intr_list(ex) \ 311 do { \ 312 LIST_REMOVE((ex), inext); \ 313 (ex)->inext.le_prev = NULL; \ 314 } while (0) 315 #define uhci_active_intr_list(ex) ((ex)->inext.le_prev != NULL) 316 317 static inline struct uhci_soft_qh * 318 uhci_find_prev_qh(struct uhci_soft_qh *pqh, struct uhci_soft_qh *sqh) 319 { 320 DPRINTFN(15,("uhci_find_prev_qh: pqh=%p sqh=%p\n", pqh, sqh)); 321 322 for (; pqh->hlink != sqh; pqh = pqh->hlink) { 323 #if defined(DIAGNOSTIC) || defined(UHCI_DEBUG) 324 if (letoh32(pqh->qh.qh_hlink) & UHCI_PTR_T) { 325 printf("uhci_find_prev_qh: QH not found\n"); 326 return (NULL); 327 } 328 #endif 329 } 330 return (pqh); 331 } 332 333 void 334 uhci_globalreset(struct uhci_softc *sc) 335 { 336 UHCICMD(sc, UHCI_CMD_GRESET); /* global reset */ 337 usb_delay_ms(&sc->sc_bus, USB_BUS_RESET_DELAY); /* wait a little */ 338 UHCICMD(sc, 0); /* do nothing */ 339 } 340 341 usbd_status 342 uhci_init(struct uhci_softc *sc) 343 { 344 usbd_status err; 345 int i, j; 346 struct uhci_soft_qh *clsqh, *chsqh, *bsqh, *sqh, *lsqh; 347 struct uhci_soft_td *std; 348 349 DPRINTFN(1,("uhci_init: start\n")); 350 351 #ifdef UHCI_DEBUG 352 thesc = sc; 353 354 if (uhcidebug > 2) 355 uhci_dumpregs(sc); 356 #endif 357 358 /* Save SOF over HC reset. */ 359 sc->sc_saved_sof = UREAD1(sc, UHCI_SOF); 360 361 UWRITE2(sc, UHCI_INTR, 0); /* disable interrupts */ 362 uhci_globalreset(sc); /* reset the controller */ 363 uhci_reset(sc); 364 365 if (uhcixfer == NULL) { 366 uhcixfer = malloc(sizeof(struct pool), M_DEVBUF, M_NOWAIT); 367 if (uhcixfer == NULL) { 368 printf("%s: unable to allocate pool descriptor\n", 369 sc->sc_bus.bdev.dv_xname); 370 return (ENOMEM); 371 } 372 pool_init(uhcixfer, sizeof(struct uhci_xfer), 0, IPL_SOFTUSB, 373 0, "uhcixfer", NULL); 374 } 375 376 /* Restore saved SOF. */ 377 UWRITE1(sc, UHCI_SOF, sc->sc_saved_sof); 378 379 /* Allocate and initialize real frame array. */ 380 err = usb_allocmem(&sc->sc_bus, 381 UHCI_FRAMELIST_COUNT * sizeof(uhci_physaddr_t), 382 UHCI_FRAMELIST_ALIGN, &sc->sc_dma); 383 if (err) 384 return (err); 385 sc->sc_pframes = KERNADDR(&sc->sc_dma, 0); 386 UWRITE2(sc, UHCI_FRNUM, 0); /* set frame number to 0 */ 387 UWRITE4(sc, UHCI_FLBASEADDR, DMAADDR(&sc->sc_dma, 0)); /* set frame list*/ 388 389 /* 390 * Allocate a TD, inactive, that hangs from the last QH. 391 * This is to avoid a bug in the PIIX that makes it run berserk 392 * otherwise. 393 */ 394 std = uhci_alloc_std(sc); 395 if (std == NULL) 396 return (USBD_NOMEM); 397 std->link.std = NULL; 398 std->td.td_link = htole32(UHCI_PTR_T); 399 std->td.td_status = htole32(0); /* inactive */ 400 std->td.td_token = htole32(0); 401 std->td.td_buffer = htole32(0); 402 403 /* Allocate the dummy QH marking the end and used for looping the QHs.*/ 404 lsqh = uhci_alloc_sqh(sc); 405 if (lsqh == NULL) 406 return (USBD_NOMEM); 407 lsqh->hlink = NULL; 408 lsqh->qh.qh_hlink = htole32(UHCI_PTR_T); /* end of QH chain */ 409 lsqh->elink = std; 410 lsqh->qh.qh_elink = htole32(std->physaddr | UHCI_PTR_TD); 411 sc->sc_last_qh = lsqh; 412 413 /* Allocate the dummy QH where bulk traffic will be queued. */ 414 bsqh = uhci_alloc_sqh(sc); 415 if (bsqh == NULL) 416 return (USBD_NOMEM); 417 bsqh->hlink = lsqh; 418 bsqh->qh.qh_hlink = htole32(lsqh->physaddr | UHCI_PTR_QH); 419 bsqh->elink = NULL; 420 bsqh->qh.qh_elink = htole32(UHCI_PTR_T); 421 sc->sc_bulk_start = sc->sc_bulk_end = bsqh; 422 423 /* Allocate dummy QH where high speed control traffic will be queued. */ 424 chsqh = uhci_alloc_sqh(sc); 425 if (chsqh == NULL) 426 return (USBD_NOMEM); 427 chsqh->hlink = bsqh; 428 chsqh->qh.qh_hlink = htole32(bsqh->physaddr | UHCI_PTR_QH); 429 chsqh->elink = NULL; 430 chsqh->qh.qh_elink = htole32(UHCI_PTR_T); 431 sc->sc_hctl_start = sc->sc_hctl_end = chsqh; 432 433 /* Allocate dummy QH where control traffic will be queued. */ 434 clsqh = uhci_alloc_sqh(sc); 435 if (clsqh == NULL) 436 return (USBD_NOMEM); 437 clsqh->hlink = chsqh; 438 clsqh->qh.qh_hlink = htole32(chsqh->physaddr | UHCI_PTR_QH); 439 clsqh->elink = NULL; 440 clsqh->qh.qh_elink = htole32(UHCI_PTR_T); 441 sc->sc_lctl_start = sc->sc_lctl_end = clsqh; 442 443 /* 444 * Make all (virtual) frame list pointers point to the interrupt 445 * queue heads and the interrupt queue heads at the control 446 * queue head and point the physical frame list to the virtual. 447 */ 448 for(i = 0; i < UHCI_VFRAMELIST_COUNT; i++) { 449 std = uhci_alloc_std(sc); 450 sqh = uhci_alloc_sqh(sc); 451 if (std == NULL || sqh == NULL) 452 return (USBD_NOMEM); 453 std->link.sqh = sqh; 454 std->td.td_link = htole32(sqh->physaddr | UHCI_PTR_QH); 455 std->td.td_status = htole32(UHCI_TD_IOS); /* iso, inactive */ 456 std->td.td_token = htole32(0); 457 std->td.td_buffer = htole32(0); 458 sqh->hlink = clsqh; 459 sqh->qh.qh_hlink = htole32(clsqh->physaddr | UHCI_PTR_QH); 460 sqh->elink = NULL; 461 sqh->qh.qh_elink = htole32(UHCI_PTR_T); 462 sc->sc_vframes[i].htd = std; 463 sc->sc_vframes[i].etd = std; 464 sc->sc_vframes[i].hqh = sqh; 465 sc->sc_vframes[i].eqh = sqh; 466 for (j = i; 467 j < UHCI_FRAMELIST_COUNT; 468 j += UHCI_VFRAMELIST_COUNT) 469 sc->sc_pframes[j] = htole32(std->physaddr); 470 } 471 472 LIST_INIT(&sc->sc_intrhead); 473 474 timeout_set(&sc->sc_root_intr, uhci_poll_hub, sc); 475 476 /* Set up the bus struct. */ 477 sc->sc_bus.methods = &uhci_bus_methods; 478 sc->sc_bus.pipe_size = sizeof(struct uhci_pipe); 479 480 sc->sc_suspend = DVACT_RESUME; 481 482 UHCICMD(sc, UHCI_CMD_MAXP); /* Assume 64 byte packets at frame end */ 483 484 DPRINTFN(1,("uhci_init: enabling\n")); 485 UWRITE2(sc, UHCI_INTR, UHCI_INTR_TOCRCIE | UHCI_INTR_RIE | 486 UHCI_INTR_IOCE | UHCI_INTR_SPIE); /* enable interrupts */ 487 488 return (uhci_run(sc, 1)); /* and here we go... */ 489 } 490 491 int 492 uhci_activate(struct device *self, int act) 493 { 494 struct uhci_softc *sc = (struct uhci_softc *)self; 495 int cmd, rv = 0; 496 497 switch (act) { 498 case DVACT_SUSPEND: 499 #ifdef UHCI_DEBUG 500 if (uhcidebug > 2) 501 uhci_dumpregs(sc); 502 #endif 503 rv = config_activate_children(self, act); 504 sc->sc_bus.use_polling++; 505 uhci_run(sc, 0); /* stop the controller */ 506 507 /* save some state if BIOS doesn't */ 508 sc->sc_saved_frnum = UREAD2(sc, UHCI_FRNUM); 509 510 UWRITE2(sc, UHCI_INTR, 0); /* disable intrs */ 511 512 cmd = UREAD2(sc, UHCI_CMD); 513 UHCICMD(sc, cmd | UHCI_CMD_EGSM); /* enter global suspend */ 514 usb_delay_ms(&sc->sc_bus, USB_RESUME_WAIT); 515 sc->sc_suspend = act; 516 sc->sc_bus.use_polling--; 517 DPRINTF(("uhci_activate: cmd=0x%x\n", UREAD2(sc, UHCI_CMD))); 518 break; 519 case DVACT_POWERDOWN: 520 rv = config_activate_children(self, act); 521 uhci_run(sc, 0); /* stop the controller */ 522 break; 523 case DVACT_RESUME: 524 #ifdef DIAGNOSTIC 525 if (sc->sc_suspend == DVACT_RESUME) 526 printf("uhci_powerhook: weird, resume without suspend.\n"); 527 #endif 528 sc->sc_bus.use_polling++; 529 sc->sc_suspend = act; 530 cmd = UREAD2(sc, UHCI_CMD); 531 if (cmd & UHCI_CMD_RS) 532 uhci_run(sc, 0); /* in case BIOS has started it */ 533 534 /* restore saved state */ 535 UWRITE4(sc, UHCI_FLBASEADDR, DMAADDR(&sc->sc_dma, 0)); 536 UWRITE2(sc, UHCI_FRNUM, sc->sc_saved_frnum); 537 UWRITE1(sc, UHCI_SOF, sc->sc_saved_sof); 538 539 UHCICMD(sc, cmd | UHCI_CMD_FGR); /* force global resume */ 540 usb_delay_ms(&sc->sc_bus, USB_RESUME_DELAY); 541 UHCICMD(sc, cmd & ~UHCI_CMD_EGSM); /* back to normal */ 542 UHCICMD(sc, UHCI_CMD_MAXP); 543 UWRITE2(sc, UHCI_INTR, UHCI_INTR_TOCRCIE | UHCI_INTR_RIE | 544 UHCI_INTR_IOCE | UHCI_INTR_SPIE); /* re-enable intrs */ 545 uhci_run(sc, 1); /* and start traffic again */ 546 usb_delay_ms(&sc->sc_bus, USB_RESUME_RECOVERY); 547 sc->sc_bus.use_polling--; 548 #ifdef UHCI_DEBUG 549 if (uhcidebug > 2) 550 uhci_dumpregs(sc); 551 #endif 552 rv = config_activate_children(self, act); 553 break; 554 default: 555 rv = config_activate_children(self, act); 556 break; 557 } 558 return (rv); 559 } 560 561 int 562 uhci_detach(struct device *self, int flags) 563 { 564 #ifdef DIAGNOSTIC 565 struct uhci_softc *sc = (struct uhci_softc *)self; 566 #endif 567 int rv; 568 569 rv = config_detach_children(self, flags); 570 if (rv != 0) 571 return (rv); 572 573 KASSERT(sc->sc_intrxfer == NULL); 574 575 /* XXX free other data structures XXX */ 576 577 return (rv); 578 } 579 580 struct usbd_xfer * 581 uhci_allocx(struct usbd_bus *bus) 582 { 583 struct uhci_xfer *ux; 584 585 ux = pool_get(uhcixfer, PR_NOWAIT | PR_ZERO); 586 #ifdef DIAGNOSTIC 587 if (ux != NULL) 588 ux->isdone = 1; 589 #endif 590 return ((struct usbd_xfer *)ux); 591 } 592 593 void 594 uhci_freex(struct usbd_bus *bus, struct usbd_xfer *xfer) 595 { 596 struct uhci_xfer *ux = (struct uhci_xfer*)xfer; 597 598 #ifdef DIAGNOSTIC 599 if (!ux->isdone) { 600 printf("%s: !isdone\n", __func__); 601 return; 602 } 603 #endif 604 pool_put(uhcixfer, ux); 605 } 606 607 #ifdef UHCI_DEBUG 608 void 609 uhci_dumpregs(struct uhci_softc *sc) 610 { 611 DPRINTFN(-1,("%s regs: cmd=%04x, sts=%04x, intr=%04x, frnum=%04x, " 612 "flbase=%08x, sof=%04x, portsc1=%04x, portsc2=%04x\n", 613 sc->sc_bus.bdev.dv_xname, 614 UREAD2(sc, UHCI_CMD), 615 UREAD2(sc, UHCI_STS), 616 UREAD2(sc, UHCI_INTR), 617 UREAD2(sc, UHCI_FRNUM), 618 UREAD4(sc, UHCI_FLBASEADDR), 619 UREAD1(sc, UHCI_SOF), 620 UREAD2(sc, UHCI_PORTSC1), 621 UREAD2(sc, UHCI_PORTSC2))); 622 } 623 624 void 625 uhci_dump_td(struct uhci_soft_td *p) 626 { 627 char sbuf[128], sbuf2[128]; 628 629 DPRINTFN(-1,("TD(%p) at %08lx = link=0x%08lx status=0x%08lx " 630 "token=0x%08lx buffer=0x%08lx\n", 631 p, (long)p->physaddr, 632 (long)letoh32(p->td.td_link), 633 (long)letoh32(p->td.td_status), 634 (long)letoh32(p->td.td_token), 635 (long)letoh32(p->td.td_buffer))); 636 637 bitmask_snprintf((u_int32_t)letoh32(p->td.td_link), "\20\1T\2Q\3VF", 638 sbuf, sizeof(sbuf)); 639 bitmask_snprintf((u_int32_t)letoh32(p->td.td_status), 640 "\20\22BITSTUFF\23CRCTO\24NAK\25BABBLE\26DBUFFER\27" 641 "STALLED\30ACTIVE\31IOC\32ISO\33LS\36SPD", 642 sbuf2, sizeof(sbuf2)); 643 644 DPRINTFN(-1,(" %s %s,errcnt=%d,actlen=%d pid=%02x,addr=%d,endpt=%d," 645 "D=%d,maxlen=%d\n", sbuf, sbuf2, 646 UHCI_TD_GET_ERRCNT(letoh32(p->td.td_status)), 647 UHCI_TD_GET_ACTLEN(letoh32(p->td.td_status)), 648 UHCI_TD_GET_PID(letoh32(p->td.td_token)), 649 UHCI_TD_GET_DEVADDR(letoh32(p->td.td_token)), 650 UHCI_TD_GET_ENDPT(letoh32(p->td.td_token)), 651 UHCI_TD_GET_DT(letoh32(p->td.td_token)), 652 UHCI_TD_GET_MAXLEN(letoh32(p->td.td_token)))); 653 } 654 655 void 656 uhci_dump_qh(struct uhci_soft_qh *sqh) 657 { 658 DPRINTFN(-1,("QH(%p) at %08x: hlink=%08x elink=%08x\n", sqh, 659 (int)sqh->physaddr, letoh32(sqh->qh.qh_hlink), 660 letoh32(sqh->qh.qh_elink))); 661 } 662 663 664 void 665 uhci_dump(void) 666 { 667 uhci_dump_all(thesc); 668 } 669 670 void 671 uhci_dump_all(struct uhci_softc *sc) 672 { 673 uhci_dumpregs(sc); 674 printf("intrs=%d\n", sc->sc_bus.no_intrs); 675 /*printf("framelist[i].link = %08x\n", sc->sc_framelist[0].link);*/ 676 uhci_dump_qh(sc->sc_lctl_start); 677 } 678 679 680 void 681 uhci_dump_qhs(struct uhci_soft_qh *sqh) 682 { 683 uhci_dump_qh(sqh); 684 685 /* uhci_dump_qhs displays all the QHs and TDs from the given QH onwards 686 * Traverses sideways first, then down. 687 * 688 * QH1 689 * QH2 690 * No QH 691 * TD2.1 692 * TD2.2 693 * TD1.1 694 * etc. 695 * 696 * TD2.x being the TDs queued at QH2 and QH1 being referenced from QH1. 697 */ 698 699 700 if (sqh->hlink != NULL && !(letoh32(sqh->qh.qh_hlink) & UHCI_PTR_T)) 701 uhci_dump_qhs(sqh->hlink); 702 else 703 DPRINTF(("No QH\n")); 704 705 if (sqh->elink != NULL && !(letoh32(sqh->qh.qh_elink) & UHCI_PTR_T)) 706 uhci_dump_tds(sqh->elink); 707 else 708 DPRINTF(("No TD\n")); 709 } 710 711 void 712 uhci_dump_tds(struct uhci_soft_td *std) 713 { 714 struct uhci_soft_td *td; 715 716 for(td = std; td != NULL; td = td->link.std) { 717 uhci_dump_td(td); 718 719 /* Check whether the link pointer in this TD marks 720 * the link pointer as end of queue. This avoids 721 * printing the free list in case the queue/TD has 722 * already been moved there (seatbelt). 723 */ 724 if (letoh32(td->td.td_link) & UHCI_PTR_T || 725 letoh32(td->td.td_link) == 0) 726 break; 727 } 728 } 729 730 void 731 uhci_dump_xfer(struct uhci_xfer *ex) 732 { 733 struct usbd_pipe *pipe; 734 usb_endpoint_descriptor_t *ed; 735 struct usbd_device *dev; 736 737 #ifdef DIAGNOSTIC 738 #define DONE ex->isdone 739 #else 740 #define DONE 0 741 #endif 742 if (ex == NULL) { 743 printf("ex NULL\n"); 744 return; 745 } 746 pipe = ex->xfer.pipe; 747 if (pipe == NULL) { 748 printf("ex %p: done=%d pipe=NULL\n", 749 ex, DONE); 750 return; 751 } 752 if (pipe->endpoint == NULL) { 753 printf("ex %p: done=%d pipe=%p pipe->endpoint=NULL\n", 754 ex, DONE, pipe); 755 return; 756 } 757 if (pipe->device == NULL) { 758 printf("ex %p: done=%d pipe=%p pipe->device=NULL\n", 759 ex, DONE, pipe); 760 return; 761 } 762 ed = pipe->endpoint->edesc; 763 dev = pipe->device; 764 printf("ex %p: done=%d dev=%p vid=0x%04x pid=0x%04x addr=%d pipe=%p ep=0x%02x attr=0x%02x\n", 765 ex, DONE, dev, 766 UGETW(dev->ddesc.idVendor), 767 UGETW(dev->ddesc.idProduct), 768 dev->address, pipe, 769 ed->bEndpointAddress, ed->bmAttributes); 770 #undef DONE 771 } 772 773 void uhci_dump_xfers(struct uhci_softc *sc); 774 void 775 uhci_dump_xfers(struct uhci_softc *sc) 776 { 777 struct uhci_xfer *ex; 778 779 printf("ex list:\n"); 780 for (ex = LIST_FIRST(&sc->sc_intrhead); ex; ex = LIST_NEXT(ex, inext)) 781 uhci_dump_xfer(ex); 782 } 783 784 void exdump(void); 785 void exdump(void) { uhci_dump_xfers(thesc); } 786 787 #endif 788 789 /* 790 * This routine is executed periodically and simulates interrupts 791 * from the root controller interrupt pipe for port status change. 792 */ 793 void 794 uhci_poll_hub(void *addr) 795 { 796 struct uhci_softc *sc = addr; 797 struct usbd_xfer *xfer; 798 int s; 799 u_char *p; 800 801 if (sc->sc_bus.dying) 802 return; 803 804 xfer = sc->sc_intrxfer; 805 if (xfer == NULL) 806 return; 807 808 p = KERNADDR(&xfer->dmabuf, 0); 809 p[0] = 0; 810 if (UREAD2(sc, UHCI_PORTSC1) & (UHCI_PORTSC_CSC|UHCI_PORTSC_OCIC)) 811 p[0] |= 1<<1; 812 if (UREAD2(sc, UHCI_PORTSC2) & (UHCI_PORTSC_CSC|UHCI_PORTSC_OCIC)) 813 p[0] |= 1<<2; 814 if (p[0] == 0) { 815 /* No change, try again in a while */ 816 timeout_add_msec(&sc->sc_root_intr, 255); 817 return; 818 } 819 820 xfer->actlen = xfer->length; 821 xfer->status = USBD_NORMAL_COMPLETION; 822 823 s = splusb(); 824 xfer->device->bus->intr_context++; 825 usb_transfer_complete(xfer); 826 xfer->device->bus->intr_context--; 827 splx(s); 828 } 829 830 void 831 uhci_root_ctrl_done(struct usbd_xfer *xfer) 832 { 833 } 834 835 /* 836 * Let the last QH loop back to the high speed control transfer QH. 837 * This is what intel calls "bandwidth reclamation" and improves 838 * USB performance a lot for some devices. 839 * If we are already looping, just count it. 840 */ 841 void 842 uhci_add_loop(struct uhci_softc *sc) { 843 #ifdef UHCI_DEBUG 844 if (uhcinoloop) 845 return; 846 #endif 847 if (++sc->sc_loops == 1) { 848 DPRINTFN(5,("uhci_add_loop\n")); 849 /* Note, we don't loop back the soft pointer. */ 850 sc->sc_last_qh->qh.qh_hlink = 851 htole32(sc->sc_hctl_start->physaddr | UHCI_PTR_QH); 852 } 853 } 854 855 void 856 uhci_rem_loop(struct uhci_softc *sc) { 857 #ifdef UHCI_DEBUG 858 if (uhcinoloop) 859 return; 860 #endif 861 if (--sc->sc_loops == 0) { 862 DPRINTFN(5,("uhci_rem_loop\n")); 863 sc->sc_last_qh->qh.qh_hlink = htole32(UHCI_PTR_T); 864 } 865 } 866 867 /* Add high speed control QH, called at splusb(). */ 868 void 869 uhci_add_hs_ctrl(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 870 { 871 struct uhci_soft_qh *eqh; 872 873 splsoftassert(IPL_SOFTUSB); 874 875 DPRINTFN(10, ("uhci_add_hs_ctrl: sqh=%p\n", sqh)); 876 eqh = sc->sc_hctl_end; 877 sqh->hlink = eqh->hlink; 878 sqh->qh.qh_hlink = eqh->qh.qh_hlink; 879 eqh->hlink = sqh; 880 eqh->qh.qh_hlink = htole32(sqh->physaddr | UHCI_PTR_QH); 881 sc->sc_hctl_end = sqh; 882 #ifdef UHCI_CTL_LOOP 883 uhci_add_loop(sc); 884 #endif 885 } 886 887 /* Remove high speed control QH, called at splusb(). */ 888 void 889 uhci_remove_hs_ctrl(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 890 { 891 struct uhci_soft_qh *pqh; 892 893 splsoftassert(IPL_SOFTUSB); 894 895 DPRINTFN(10, ("uhci_remove_hs_ctrl: sqh=%p\n", sqh)); 896 #ifdef UHCI_CTL_LOOP 897 uhci_rem_loop(sc); 898 #endif 899 /* 900 * The T bit should be set in the elink of the QH so that the HC 901 * doesn't follow the pointer. This condition may fail if the 902 * the transferred packet was short so that the QH still points 903 * at the last used TD. 904 * In this case we set the T bit and wait a little for the HC 905 * to stop looking at the TD. 906 */ 907 if (!(sqh->qh.qh_elink & htole32(UHCI_PTR_T))) { 908 sqh->qh.qh_elink = htole32(UHCI_PTR_T); 909 delay(UHCI_QH_REMOVE_DELAY); 910 } 911 912 pqh = uhci_find_prev_qh(sc->sc_hctl_start, sqh); 913 pqh->hlink = sqh->hlink; 914 pqh->qh.qh_hlink = sqh->qh.qh_hlink; 915 delay(UHCI_QH_REMOVE_DELAY); 916 if (sc->sc_hctl_end == sqh) 917 sc->sc_hctl_end = pqh; 918 } 919 920 /* Add low speed control QH, called at splusb(). */ 921 void 922 uhci_add_ls_ctrl(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 923 { 924 struct uhci_soft_qh *eqh; 925 926 splsoftassert(IPL_SOFTUSB); 927 928 DPRINTFN(10, ("uhci_add_ls_ctrl: sqh=%p\n", sqh)); 929 eqh = sc->sc_lctl_end; 930 sqh->hlink = eqh->hlink; 931 sqh->qh.qh_hlink = eqh->qh.qh_hlink; 932 eqh->hlink = sqh; 933 eqh->qh.qh_hlink = htole32(sqh->physaddr | UHCI_PTR_QH); 934 sc->sc_lctl_end = sqh; 935 } 936 937 /* Remove low speed control QH, called at splusb(). */ 938 void 939 uhci_remove_ls_ctrl(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 940 { 941 struct uhci_soft_qh *pqh; 942 943 splsoftassert(IPL_SOFTUSB); 944 945 DPRINTFN(10, ("uhci_remove_ls_ctrl: sqh=%p\n", sqh)); 946 /* See comment in uhci_remove_hs_ctrl() */ 947 if (!(sqh->qh.qh_elink & htole32(UHCI_PTR_T))) { 948 sqh->qh.qh_elink = htole32(UHCI_PTR_T); 949 delay(UHCI_QH_REMOVE_DELAY); 950 } 951 pqh = uhci_find_prev_qh(sc->sc_lctl_start, sqh); 952 pqh->hlink = sqh->hlink; 953 pqh->qh.qh_hlink = sqh->qh.qh_hlink; 954 delay(UHCI_QH_REMOVE_DELAY); 955 if (sc->sc_lctl_end == sqh) 956 sc->sc_lctl_end = pqh; 957 } 958 959 /* Add bulk QH, called at splusb(). */ 960 void 961 uhci_add_bulk(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 962 { 963 struct uhci_soft_qh *eqh; 964 965 splsoftassert(IPL_SOFTUSB); 966 967 DPRINTFN(10, ("uhci_add_bulk: sqh=%p\n", sqh)); 968 eqh = sc->sc_bulk_end; 969 sqh->hlink = eqh->hlink; 970 sqh->qh.qh_hlink = eqh->qh.qh_hlink; 971 eqh->hlink = sqh; 972 eqh->qh.qh_hlink = htole32(sqh->physaddr | UHCI_PTR_QH); 973 sc->sc_bulk_end = sqh; 974 uhci_add_loop(sc); 975 } 976 977 /* Remove bulk QH, called at splusb(). */ 978 void 979 uhci_remove_bulk(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 980 { 981 struct uhci_soft_qh *pqh; 982 983 splsoftassert(IPL_SOFTUSB); 984 985 DPRINTFN(10, ("uhci_remove_bulk: sqh=%p\n", sqh)); 986 uhci_rem_loop(sc); 987 /* See comment in uhci_remove_hs_ctrl() */ 988 if (!(sqh->qh.qh_elink & htole32(UHCI_PTR_T))) { 989 sqh->qh.qh_elink = htole32(UHCI_PTR_T); 990 delay(UHCI_QH_REMOVE_DELAY); 991 } 992 pqh = uhci_find_prev_qh(sc->sc_bulk_start, sqh); 993 pqh->hlink = sqh->hlink; 994 pqh->qh.qh_hlink = sqh->qh.qh_hlink; 995 delay(UHCI_QH_REMOVE_DELAY); 996 if (sc->sc_bulk_end == sqh) 997 sc->sc_bulk_end = pqh; 998 } 999 1000 int uhci_intr1(struct uhci_softc *); 1001 1002 int 1003 uhci_intr(void *arg) 1004 { 1005 struct uhci_softc *sc = arg; 1006 1007 if (sc->sc_bus.dying) 1008 return (0); 1009 if (sc->sc_bus.use_polling) 1010 return (0); 1011 return (uhci_intr1(sc)); 1012 } 1013 1014 int 1015 uhci_intr1(struct uhci_softc *sc) 1016 { 1017 int status; 1018 int ack; 1019 1020 status = UREAD2(sc, UHCI_STS); 1021 if (status == 0xffff) { 1022 sc->sc_bus.dying = 1; 1023 return (0); 1024 } 1025 status &= UHCI_STS_ALLINTRS; 1026 if (status == 0) /* The interrupt was not for us. */ 1027 return (0); 1028 1029 #ifdef UHCI_DEBUG 1030 if (uhcidebug > 15) { 1031 DPRINTF(("%s: uhci_intr1\n", sc->sc_bus.bdev.dv_xname)); 1032 uhci_dumpregs(sc); 1033 } 1034 #endif 1035 1036 if (sc->sc_suspend != DVACT_RESUME) { 1037 printf("%s: interrupt while not operating ignored\n", 1038 sc->sc_bus.bdev.dv_xname); 1039 return (0); 1040 } 1041 1042 ack = 0; 1043 if (status & UHCI_STS_USBINT) 1044 ack |= UHCI_STS_USBINT; 1045 if (status & UHCI_STS_USBEI) 1046 ack |= UHCI_STS_USBEI; 1047 if (status & UHCI_STS_RD) { 1048 ack |= UHCI_STS_RD; 1049 #ifdef UHCI_DEBUG 1050 printf("%s: resume detect\n", sc->sc_bus.bdev.dv_xname); 1051 #endif 1052 } 1053 if (status & UHCI_STS_HSE) { 1054 ack |= UHCI_STS_HSE; 1055 printf("%s: host system error\n", sc->sc_bus.bdev.dv_xname); 1056 } 1057 if (status & UHCI_STS_HCPE) { 1058 ack |= UHCI_STS_HCPE; 1059 printf("%s: host controller process error\n", 1060 sc->sc_bus.bdev.dv_xname); 1061 } 1062 if (status & UHCI_STS_HCH) { 1063 /* no acknowledge needed */ 1064 if (!sc->sc_bus.dying) { 1065 printf("%s: host controller halted\n", 1066 sc->sc_bus.bdev.dv_xname); 1067 #ifdef UHCI_DEBUG 1068 uhci_dump_all(sc); 1069 #endif 1070 } 1071 sc->sc_bus.dying = 1; 1072 } 1073 1074 if (!ack) 1075 return (0); /* nothing to acknowledge */ 1076 UWRITE2(sc, UHCI_STS, ack); /* acknowledge the ints */ 1077 1078 sc->sc_bus.no_intrs++; 1079 usb_schedsoftintr(&sc->sc_bus); 1080 1081 DPRINTFN(15, ("%s: uhci_intr1: exit\n", sc->sc_bus.bdev.dv_xname)); 1082 1083 return (1); 1084 } 1085 1086 void 1087 uhci_softintr(void *v) 1088 { 1089 struct uhci_softc *sc = v; 1090 struct uhci_xfer *ux, *nextex; 1091 1092 DPRINTFN(10,("%s: uhci_softintr (%d)\n", sc->sc_bus.bdev.dv_xname, 1093 sc->sc_bus.intr_context)); 1094 1095 if (sc->sc_bus.dying) 1096 return; 1097 1098 sc->sc_bus.intr_context++; 1099 1100 /* 1101 * Interrupts on UHCI really suck. When the host controller 1102 * interrupts because a transfer is completed there is no 1103 * way of knowing which transfer it was. You can scan down 1104 * the TDs and QHs of the previous frame to limit the search, 1105 * but that assumes that the interrupt was not delayed by more 1106 * than 1 ms, which may not always be true (e.g. after debug 1107 * output on a slow console). 1108 * We scan all interrupt descriptors to see if any have 1109 * completed. 1110 */ 1111 for (ux = LIST_FIRST(&sc->sc_intrhead); ux; ux = nextex) { 1112 nextex = LIST_NEXT(ux, inext); 1113 uhci_check_intr(sc, &ux->xfer); 1114 } 1115 1116 if (sc->sc_softwake) { 1117 sc->sc_softwake = 0; 1118 wakeup(&sc->sc_softwake); 1119 } 1120 1121 sc->sc_bus.intr_context--; 1122 } 1123 1124 void 1125 uhci_check_intr(struct uhci_softc *sc, struct usbd_xfer *xfer) 1126 { 1127 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 1128 struct uhci_soft_td *std, *lstd; 1129 u_int32_t status; 1130 1131 DPRINTFN(15, ("%s: ux=%p\n", __func__, ux)); 1132 #ifdef DIAGNOSTIC 1133 if (ux == NULL) { 1134 printf("%s: no ux? %p\n", __func__, ux); 1135 return; 1136 } 1137 #endif 1138 if (xfer->status == USBD_CANCELLED || xfer->status == USBD_TIMEOUT) { 1139 DPRINTF(("%s: aborted xfer=%p\n", __func__, xfer)); 1140 return; 1141 } 1142 1143 if (ux->stdstart == NULL) 1144 return; 1145 lstd = ux->stdend; 1146 #ifdef DIAGNOSTIC 1147 if (lstd == NULL) { 1148 printf("%s: std==0\n", __func__); 1149 return; 1150 } 1151 #endif 1152 /* 1153 * If the last TD is still active we need to check whether there 1154 * is an error somewhere in the middle, or whether there was a 1155 * short packet (SPD and not ACTIVE). 1156 */ 1157 if (letoh32(lstd->td.td_status) & UHCI_TD_ACTIVE) { 1158 DPRINTFN(12, ("%s: active ux=%p\n", __func__, ux)); 1159 for (std = ux->stdstart; std != lstd; std = std->link.std) { 1160 status = letoh32(std->td.td_status); 1161 /* If there's an active TD the xfer isn't done. */ 1162 if (status & UHCI_TD_ACTIVE) 1163 break; 1164 /* Any kind of error makes the xfer done. */ 1165 if (status & UHCI_TD_STALLED) 1166 goto done; 1167 /* We want short packets, and it is short: it's done */ 1168 if ((status & UHCI_TD_SPD) && 1169 UHCI_TD_GET_ACTLEN(status) < 1170 UHCI_TD_GET_MAXLEN(letoh32(std->td.td_token))) 1171 goto done; 1172 } 1173 DPRINTFN(12, ("%s: ux=%p std=%p still active\n", __func__, 1174 ux, ux->stdstart)); 1175 return; 1176 } 1177 done: 1178 DPRINTFN(12, ("uhci_check_intr: ux=%p done\n", ux)); 1179 timeout_del(&xfer->timeout_handle); 1180 usb_rem_task(xfer->pipe->device, &xfer->abort_task); 1181 uhci_idone(xfer); 1182 } 1183 1184 /* Called at splusb() */ 1185 void 1186 uhci_idone(struct usbd_xfer *xfer) 1187 { 1188 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 1189 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 1190 struct uhci_soft_td *std; 1191 u_int32_t status = 0, nstatus; 1192 int actlen; 1193 1194 DPRINTFN(12, ("uhci_idone: ux=%p\n", ux)); 1195 #ifdef DIAGNOSTIC 1196 { 1197 int s = splhigh(); 1198 if (ux->isdone) { 1199 splx(s); 1200 #ifdef UHCI_DEBUG 1201 printf("uhci_idone: ux is done!\n "); 1202 uhci_dump_xfer(ux); 1203 #else 1204 printf("uhci_idone: ux=%p is done!\n", ux); 1205 #endif 1206 return; 1207 } 1208 ux->isdone = 1; 1209 splx(s); 1210 } 1211 #endif 1212 1213 if (xfer->nframes != 0) { 1214 /* Isoc transfer, do things differently. */ 1215 struct uhci_soft_td **stds = upipe->u.iso.stds; 1216 int i, n, nframes, len; 1217 1218 DPRINTFN(5,("uhci_idone: ux=%p isoc ready\n", ux)); 1219 1220 nframes = xfer->nframes; 1221 actlen = 0; 1222 n = ux->curframe; 1223 for (i = 0; i < nframes; i++) { 1224 std = stds[n]; 1225 #ifdef UHCI_DEBUG 1226 if (uhcidebug > 5) { 1227 DPRINTFN(-1,("uhci_idone: isoc TD %d\n", i)); 1228 uhci_dump_td(std); 1229 } 1230 #endif 1231 if (++n >= UHCI_VFRAMELIST_COUNT) 1232 n = 0; 1233 status = letoh32(std->td.td_status); 1234 len = UHCI_TD_GET_ACTLEN(status); 1235 xfer->frlengths[i] = len; 1236 actlen += len; 1237 } 1238 upipe->u.iso.inuse -= nframes; 1239 xfer->actlen = actlen; 1240 xfer->status = USBD_NORMAL_COMPLETION; 1241 goto end; 1242 } 1243 1244 #ifdef UHCI_DEBUG 1245 DPRINTFN(10, ("uhci_idone: ux=%p, xfer=%p, pipe=%p ready\n", 1246 ux, xfer, upipe)); 1247 if (uhcidebug > 10) 1248 uhci_dump_tds(ux->stdstart); 1249 #endif 1250 1251 /* The transfer is done, compute actual length and status. */ 1252 actlen = 0; 1253 for (std = ux->stdstart; std != NULL; std = std->link.std) { 1254 nstatus = letoh32(std->td.td_status); 1255 if (nstatus & UHCI_TD_ACTIVE) 1256 break; 1257 1258 status = nstatus; 1259 if (UHCI_TD_GET_PID(letoh32(std->td.td_token)) != 1260 UHCI_TD_PID_SETUP) 1261 actlen += UHCI_TD_GET_ACTLEN(status); 1262 else { 1263 /* 1264 * UHCI will report CRCTO in addition to a STALL or NAK 1265 * for a SETUP transaction. See section 3.2.2, "TD 1266 * CONTROL AND STATUS". 1267 */ 1268 if (status & (UHCI_TD_STALLED | UHCI_TD_NAK)) 1269 status &= ~UHCI_TD_CRCTO; 1270 } 1271 } 1272 /* If there are left over TDs we need to update the toggle. */ 1273 if (std != NULL) 1274 upipe->nexttoggle = UHCI_TD_GET_DT(letoh32(std->td.td_token)); 1275 1276 status &= UHCI_TD_ERROR; 1277 DPRINTFN(10, ("uhci_idone: actlen=%d, status=0x%x\n", 1278 actlen, status)); 1279 xfer->actlen = actlen; 1280 if (status != 0) { 1281 #ifdef UHCI_DEBUG 1282 char sbuf[128]; 1283 1284 bitmask_snprintf((u_int32_t)status, 1285 "\20\22BITSTUFF\23CRCTO\24NAK\25" 1286 "BABBLE\26DBUFFER\27STALLED\30ACTIVE", 1287 sbuf, sizeof(sbuf)); 1288 1289 DPRINTFN((status == UHCI_TD_STALLED)*10, 1290 ("uhci_idone: error, addr=%d, endpt=0x%02x, " 1291 "status 0x%s\n", 1292 xfer->device->address, 1293 xfer->pipe->endpoint->edesc->bEndpointAddress, 1294 sbuf)); 1295 #endif 1296 1297 if (status == UHCI_TD_STALLED) 1298 xfer->status = USBD_STALLED; 1299 else 1300 xfer->status = USBD_IOERROR; /* more info XXX */ 1301 } else { 1302 xfer->status = USBD_NORMAL_COMPLETION; 1303 } 1304 1305 end: 1306 usb_transfer_complete(xfer); 1307 DPRINTFN(12, ("uhci_idone: ux=%p done\n", ux)); 1308 } 1309 1310 void 1311 uhci_timeout(void *addr) 1312 { 1313 struct usbd_xfer *xfer = addr; 1314 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 1315 1316 if (sc->sc_bus.dying) { 1317 uhci_timeout_task(addr); 1318 return; 1319 } 1320 1321 usb_init_task(&xfer->abort_task, uhci_timeout_task, addr, 1322 USB_TASK_TYPE_ABORT); 1323 usb_add_task(xfer->device, &xfer->abort_task); 1324 } 1325 1326 void 1327 uhci_timeout_task(void *addr) 1328 { 1329 struct usbd_xfer *xfer = addr; 1330 int s; 1331 1332 DPRINTF(("%s: xfer=%p\n", __func__, xfer)); 1333 1334 s = splusb(); 1335 uhci_abort_xfer(xfer, USBD_TIMEOUT); 1336 splx(s); 1337 } 1338 1339 void 1340 uhci_poll(struct usbd_bus *bus) 1341 { 1342 struct uhci_softc *sc = (struct uhci_softc *)bus; 1343 1344 if (UREAD2(sc, UHCI_STS) & UHCI_STS_ALLINTRS) 1345 uhci_intr1(sc); 1346 } 1347 1348 void 1349 uhci_reset(struct uhci_softc *sc) 1350 { 1351 int n; 1352 1353 UHCICMD(sc, UHCI_CMD_HCRESET); 1354 /* The reset bit goes low when the controller is done. */ 1355 for (n = 0; n < UHCI_RESET_TIMEOUT && 1356 (UREAD2(sc, UHCI_CMD) & UHCI_CMD_HCRESET); n++) 1357 usb_delay_ms(&sc->sc_bus, 1); 1358 if (n >= UHCI_RESET_TIMEOUT) 1359 printf("%s: controller did not reset\n", 1360 sc->sc_bus.bdev.dv_xname); 1361 } 1362 1363 usbd_status 1364 uhci_run(struct uhci_softc *sc, int run) 1365 { 1366 int s, n, running; 1367 u_int16_t cmd; 1368 1369 run = run != 0; 1370 s = splhardusb(); 1371 DPRINTF(("uhci_run: setting run=%d\n", run)); 1372 cmd = UREAD2(sc, UHCI_CMD); 1373 if (run) 1374 cmd |= UHCI_CMD_RS; 1375 else 1376 cmd &= ~UHCI_CMD_RS; 1377 UHCICMD(sc, cmd); 1378 for(n = 0; n < 10; n++) { 1379 running = !(UREAD2(sc, UHCI_STS) & UHCI_STS_HCH); 1380 /* return when we've entered the state we want */ 1381 if (run == running) { 1382 splx(s); 1383 DPRINTF(("uhci_run: done cmd=0x%x sts=0x%x\n", 1384 UREAD2(sc, UHCI_CMD), UREAD2(sc, UHCI_STS))); 1385 return (USBD_NORMAL_COMPLETION); 1386 } 1387 usb_delay_ms(&sc->sc_bus, 1); 1388 } 1389 splx(s); 1390 printf("%s: cannot %s\n", sc->sc_bus.bdev.dv_xname, 1391 run ? "start" : "stop"); 1392 return (USBD_IOERROR); 1393 } 1394 1395 /* 1396 * Memory management routines. 1397 * uhci_alloc_std allocates TDs 1398 * uhci_alloc_sqh allocates QHs 1399 * These two routines do their own free list management, 1400 * partly for speed, partly because allocating DMAable memory 1401 * has page size granularaity so much memory would be wasted if 1402 * only one TD/QH (32 bytes) was placed in each allocated chunk. 1403 */ 1404 1405 struct uhci_soft_td * 1406 uhci_alloc_std(struct uhci_softc *sc) 1407 { 1408 struct uhci_soft_td *std = NULL; 1409 usbd_status err; 1410 int i, offs; 1411 struct usb_dma dma; 1412 int s; 1413 1414 s = splusb(); 1415 if (sc->sc_freetds == NULL) { 1416 DPRINTFN(2,("uhci_alloc_std: allocating chunk\n")); 1417 err = usb_allocmem(&sc->sc_bus, UHCI_STD_SIZE * UHCI_STD_CHUNK, 1418 UHCI_TD_ALIGN, &dma); 1419 if (err) 1420 goto out; 1421 for(i = 0; i < UHCI_STD_CHUNK; i++) { 1422 offs = i * UHCI_STD_SIZE; 1423 std = KERNADDR(&dma, offs); 1424 std->physaddr = DMAADDR(&dma, offs); 1425 std->link.std = sc->sc_freetds; 1426 sc->sc_freetds = std; 1427 } 1428 } 1429 1430 std = sc->sc_freetds; 1431 sc->sc_freetds = std->link.std; 1432 memset(&std->td, 0, sizeof(struct uhci_td)); 1433 1434 out: 1435 splx(s); 1436 return (std); 1437 } 1438 1439 void 1440 uhci_free_std(struct uhci_softc *sc, struct uhci_soft_td *std) 1441 { 1442 int s; 1443 1444 #ifdef DIAGNOSTIC 1445 #define TD_IS_FREE 0x12345678 1446 if (letoh32(std->td.td_token) == TD_IS_FREE) { 1447 printf("uhci_free_std: freeing free TD %p\n", std); 1448 return; 1449 } 1450 std->td.td_token = htole32(TD_IS_FREE); 1451 #endif 1452 1453 s = splusb(); 1454 std->link.std = sc->sc_freetds; 1455 sc->sc_freetds = std; 1456 splx(s); 1457 } 1458 1459 struct uhci_soft_qh * 1460 uhci_alloc_sqh(struct uhci_softc *sc) 1461 { 1462 struct uhci_soft_qh *sqh = NULL; 1463 usbd_status err; 1464 int i, offs; 1465 struct usb_dma dma; 1466 int s; 1467 1468 s = splusb(); 1469 if (sc->sc_freeqhs == NULL) { 1470 DPRINTFN(2, ("uhci_alloc_sqh: allocating chunk\n")); 1471 err = usb_allocmem(&sc->sc_bus, UHCI_SQH_SIZE * UHCI_SQH_CHUNK, 1472 UHCI_QH_ALIGN, &dma); 1473 if (err) 1474 goto out; 1475 for (i = 0; i < UHCI_SQH_CHUNK; i++) { 1476 offs = i * UHCI_SQH_SIZE; 1477 sqh = KERNADDR(&dma, offs); 1478 sqh->physaddr = DMAADDR(&dma, offs); 1479 sqh->hlink = sc->sc_freeqhs; 1480 sc->sc_freeqhs = sqh; 1481 } 1482 } 1483 sqh = sc->sc_freeqhs; 1484 sc->sc_freeqhs = sqh->hlink; 1485 memset(&sqh->qh, 0, sizeof(struct uhci_qh)); 1486 1487 out: 1488 splx(s); 1489 return (sqh); 1490 } 1491 1492 void 1493 uhci_free_sqh(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 1494 { 1495 sqh->hlink = sc->sc_freeqhs; 1496 sc->sc_freeqhs = sqh; 1497 } 1498 1499 void 1500 uhci_free_std_chain(struct uhci_softc *sc, struct uhci_soft_td *std, 1501 struct uhci_soft_td *stdend) 1502 { 1503 struct uhci_soft_td *p; 1504 1505 for (; std != stdend; std = p) { 1506 p = std->link.std; 1507 uhci_free_std(sc, std); 1508 } 1509 } 1510 1511 usbd_status 1512 uhci_alloc_std_chain(struct uhci_softc *sc, u_int len, struct usbd_xfer *xfer, 1513 struct uhci_soft_td **sp, struct uhci_soft_td **ep) 1514 { 1515 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 1516 struct uhci_soft_td *p, *lastp; 1517 uhci_physaddr_t lastlink; 1518 int i, ntd, l, tog, mps; 1519 u_int32_t status; 1520 u_int16_t flags = xfer->flags; 1521 int rd = usbd_xfer_isread(xfer); 1522 struct usb_dma *dma = &xfer->dmabuf; 1523 int addr = xfer->device->address; 1524 int endpt = xfer->pipe->endpoint->edesc->bEndpointAddress; 1525 1526 DPRINTFN(8, ("%s: addr=%d endpt=%d len=%u speed=%d flags=0x%x\n", 1527 __func__, addr, UE_GET_ADDR(endpt), len, xfer->device->speed, 1528 flags)); 1529 1530 mps = UGETW(xfer->pipe->endpoint->edesc->wMaxPacketSize); 1531 if (mps == 0) { 1532 printf("uhci_alloc_std_chain: mps=0\n"); 1533 return (USBD_INVAL); 1534 } 1535 ntd = (len + mps - 1) / mps; 1536 if (len == 0) 1537 flags |= USBD_FORCE_SHORT_XFER; 1538 if ((flags & USBD_FORCE_SHORT_XFER) && len % mps == 0) 1539 ntd++; 1540 DPRINTFN(10, ("%s: mps=%d ntd=%d\n", __func__, mps, ntd)); 1541 tog = upipe->nexttoggle; 1542 if (ntd % 2 == 0) 1543 tog ^= 1; 1544 upipe->nexttoggle = tog ^ 1; 1545 lastp = NULL; 1546 lastlink = UHCI_PTR_T; 1547 ntd--; 1548 status = UHCI_TD_ZERO_ACTLEN(UHCI_TD_SET_ERRCNT(3) | UHCI_TD_ACTIVE); 1549 if (xfer->pipe->device->speed == USB_SPEED_LOW) 1550 status |= UHCI_TD_LS; 1551 if (flags & USBD_SHORT_XFER_OK) 1552 status |= UHCI_TD_SPD; 1553 for (i = ntd; i >= 0; i--) { 1554 p = uhci_alloc_std(sc); 1555 if (p == NULL) { 1556 uhci_free_std_chain(sc, lastp, NULL); 1557 return (USBD_NOMEM); 1558 } 1559 p->link.std = lastp; 1560 p->td.td_link = htole32(lastlink | UHCI_PTR_VF | UHCI_PTR_TD); 1561 lastp = p; 1562 lastlink = p->physaddr; 1563 p->td.td_status = htole32(status); 1564 if (i == ntd) { 1565 /* last TD */ 1566 l = len % mps; 1567 if (l == 0 && !(flags & USBD_FORCE_SHORT_XFER)) 1568 l = mps; 1569 *ep = p; 1570 } else 1571 l = mps; 1572 p->td.td_token = 1573 htole32(rd ? UHCI_TD_IN (l, endpt, addr, tog) : 1574 UHCI_TD_OUT(l, endpt, addr, tog)); 1575 p->td.td_buffer = htole32(DMAADDR(dma, i * mps)); 1576 tog ^= 1; 1577 } 1578 *sp = lastp; 1579 DPRINTFN(10, ("%s: nexttog=%d\n", __func__, upipe->nexttoggle)); 1580 return (USBD_NORMAL_COMPLETION); 1581 } 1582 1583 void 1584 uhci_device_clear_toggle(struct usbd_pipe *pipe) 1585 { 1586 struct uhci_pipe *upipe = (struct uhci_pipe *)pipe; 1587 upipe->nexttoggle = 0; 1588 } 1589 1590 usbd_status 1591 uhci_device_bulk_transfer(struct usbd_xfer *xfer) 1592 { 1593 usbd_status err; 1594 1595 /* Insert last in queue. */ 1596 err = usb_insert_transfer(xfer); 1597 if (err) 1598 return (err); 1599 1600 /* 1601 * Pipe isn't running (otherwise err would be USBD_INPROG), 1602 * so start it first. 1603 */ 1604 return (uhci_device_bulk_start(SIMPLEQ_FIRST(&xfer->pipe->queue))); 1605 } 1606 1607 usbd_status 1608 uhci_device_bulk_start(struct usbd_xfer *xfer) 1609 { 1610 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 1611 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 1612 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 1613 struct uhci_soft_td *data, *dataend; 1614 struct uhci_soft_qh *sqh; 1615 usbd_status err; 1616 u_int len; 1617 int s; 1618 1619 DPRINTFN(3, ("uhci_device_bulk_start: xfer=%p len=%u flags=%d ux=%p\n", 1620 xfer, xfer->length, xfer->flags, ux)); 1621 1622 if (sc->sc_bus.dying) 1623 return (USBD_IOERROR); 1624 1625 #ifdef DIAGNOSTIC 1626 if (xfer->rqflags & URQ_REQUEST) 1627 panic("uhci_device_bulk_start: a request"); 1628 #endif 1629 1630 len = xfer->length; 1631 sqh = upipe->u.bulk.sqh; 1632 1633 err = uhci_alloc_std_chain(sc, len, xfer, &data, &dataend); 1634 if (err) 1635 return (err); 1636 dataend->td.td_status |= htole32(UHCI_TD_IOC); 1637 1638 #ifdef UHCI_DEBUG 1639 if (uhcidebug > 8) { 1640 DPRINTF(("uhci_device_bulk_start: data(1)\n")); 1641 uhci_dump_tds(data); 1642 } 1643 #endif 1644 1645 /* Set up interrupt info. */ 1646 ux->stdstart = data; 1647 ux->stdend = dataend; 1648 #ifdef DIAGNOSTIC 1649 if (!ux->isdone) { 1650 printf("uhci_device_bulk_start: not done, ux=%p\n", ux); 1651 } 1652 ux->isdone = 0; 1653 #endif 1654 1655 sqh->elink = data; 1656 sqh->qh.qh_elink = htole32(data->physaddr | UHCI_PTR_TD); 1657 1658 s = splusb(); 1659 uhci_add_bulk(sc, sqh); 1660 uhci_add_intr_list(sc, ux); 1661 1662 if (xfer->timeout && !sc->sc_bus.use_polling) { 1663 timeout_del(&xfer->timeout_handle); 1664 timeout_set(&xfer->timeout_handle, uhci_timeout, xfer); 1665 timeout_add_msec(&xfer->timeout_handle, xfer->timeout); 1666 } 1667 xfer->status = USBD_IN_PROGRESS; 1668 splx(s); 1669 1670 #ifdef UHCI_DEBUG 1671 if (uhcidebug > 10) { 1672 DPRINTF(("uhci_device_bulk_start: data(2)\n")); 1673 uhci_dump_tds(data); 1674 } 1675 #endif 1676 1677 return (USBD_IN_PROGRESS); 1678 } 1679 1680 /* Abort a device bulk request. */ 1681 void 1682 uhci_device_bulk_abort(struct usbd_xfer *xfer) 1683 { 1684 DPRINTF(("uhci_device_bulk_abort:\n")); 1685 uhci_abort_xfer(xfer, USBD_CANCELLED); 1686 } 1687 1688 /* 1689 * Abort a device request. 1690 * If this routine is called at splusb() it guarantees that the request 1691 * will be removed from the hardware scheduling and that the callback 1692 * for it will be called with USBD_CANCELLED status. 1693 * It's impossible to guarantee that the requested transfer will not 1694 * have happened since the hardware runs concurrently. 1695 * If the transaction has already happened we rely on the ordinary 1696 * interrupt processing to process it. 1697 */ 1698 void 1699 uhci_abort_xfer(struct usbd_xfer *xfer, usbd_status status) 1700 { 1701 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 1702 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 1703 struct uhci_soft_td *std; 1704 int s; 1705 1706 DPRINTFN(1,("uhci_abort_xfer: xfer=%p, status=%d\n", xfer, status)); 1707 1708 if (sc->sc_bus.dying) { 1709 /* If we're dying, just do the software part. */ 1710 s = splusb(); 1711 xfer->status = status; /* make software ignore it */ 1712 timeout_del(&xfer->timeout_handle); 1713 usb_rem_task(xfer->device, &xfer->abort_task); 1714 #ifdef DIAGNOSTIC 1715 ux->isdone = 1; 1716 #endif 1717 usb_transfer_complete(xfer); 1718 splx(s); 1719 return; 1720 } 1721 1722 if (xfer->device->bus->intr_context || !curproc) 1723 panic("uhci_abort_xfer: not in process context"); 1724 1725 /* 1726 * Step 1: Make interrupt routine and hardware ignore xfer. 1727 */ 1728 s = splusb(); 1729 xfer->status = status; /* make software ignore it */ 1730 timeout_del(&xfer->timeout_handle); 1731 usb_rem_task(xfer->device, &xfer->abort_task); 1732 DPRINTFN(1,("uhci_abort_xfer: stop ux=%p\n", ux)); 1733 for (std = ux->stdstart; std != NULL; std = std->link.std) 1734 std->td.td_status &= htole32(~(UHCI_TD_ACTIVE | UHCI_TD_IOC)); 1735 splx(s); 1736 1737 /* 1738 * Step 2: Wait until we know hardware has finished any possible 1739 * use of the xfer. Also make sure the soft interrupt routine 1740 * has run. 1741 */ 1742 usb_delay_ms(&sc->sc_bus, 2); /* Hardware finishes in 1ms */ 1743 s = splusb(); 1744 sc->sc_softwake = 1; 1745 usb_schedsoftintr(&sc->sc_bus); 1746 DPRINTFN(1,("uhci_abort_xfer: tsleep\n")); 1747 tsleep_nsec(&sc->sc_softwake, PZERO, "uhciab", INFSLP); 1748 splx(s); 1749 1750 /* 1751 * Step 3: Execute callback. 1752 */ 1753 DPRINTFN(1,("uhci_abort_xfer: callback\n")); 1754 s = splusb(); 1755 #ifdef DIAGNOSTIC 1756 ux->isdone = 1; 1757 #endif 1758 usb_transfer_complete(xfer); 1759 splx(s); 1760 } 1761 1762 /* Close a device bulk pipe. */ 1763 void 1764 uhci_device_bulk_close(struct usbd_pipe *pipe) 1765 { 1766 struct uhci_softc *sc = (struct uhci_softc *)pipe->device->bus; 1767 struct uhci_pipe *upipe = (struct uhci_pipe *)pipe; 1768 1769 uhci_free_sqh(sc, upipe->u.bulk.sqh); 1770 pipe->endpoint->savedtoggle = upipe->nexttoggle; 1771 } 1772 1773 usbd_status 1774 uhci_device_ctrl_transfer(struct usbd_xfer *xfer) 1775 { 1776 usbd_status err; 1777 1778 /* Insert last in queue. */ 1779 err = usb_insert_transfer(xfer); 1780 if (err) 1781 return (err); 1782 1783 /* 1784 * Pipe isn't running (otherwise err would be USBD_INPROG), 1785 * so start it first. 1786 */ 1787 return (uhci_device_ctrl_start(SIMPLEQ_FIRST(&xfer->pipe->queue))); 1788 } 1789 1790 usbd_status 1791 uhci_device_ctrl_start(struct usbd_xfer *xfer) 1792 { 1793 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 1794 usbd_status err; 1795 1796 if (sc->sc_bus.dying) 1797 return (USBD_IOERROR); 1798 1799 #ifdef DIAGNOSTIC 1800 if (!(xfer->rqflags & URQ_REQUEST)) 1801 panic("uhci_device_ctrl_transfer: not a request"); 1802 #endif 1803 1804 err = uhci_device_request(xfer); 1805 if (err) 1806 return (err); 1807 1808 return (USBD_IN_PROGRESS); 1809 } 1810 1811 usbd_status 1812 uhci_device_intr_transfer(struct usbd_xfer *xfer) 1813 { 1814 usbd_status err; 1815 1816 /* Insert last in queue. */ 1817 err = usb_insert_transfer(xfer); 1818 if (err) 1819 return (err); 1820 1821 /* 1822 * Pipe isn't running (otherwise err would be USBD_INPROG), 1823 * so start it first. 1824 */ 1825 return (uhci_device_intr_start(SIMPLEQ_FIRST(&xfer->pipe->queue))); 1826 } 1827 1828 usbd_status 1829 uhci_device_intr_start(struct usbd_xfer *xfer) 1830 { 1831 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 1832 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 1833 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 1834 struct uhci_soft_td *data, *dataend; 1835 struct uhci_soft_qh *sqh; 1836 usbd_status err; 1837 int i, s; 1838 1839 if (sc->sc_bus.dying) 1840 return (USBD_IOERROR); 1841 1842 DPRINTFN(3,("uhci_device_intr_start: xfer=%p len=%u flags=%d\n", 1843 xfer, xfer->length, xfer->flags)); 1844 1845 #ifdef DIAGNOSTIC 1846 if (xfer->rqflags & URQ_REQUEST) 1847 panic("uhci_device_intr_start: a request"); 1848 #endif 1849 1850 upipe->u.intr.isread = usbd_xfer_isread(xfer); 1851 1852 err = uhci_alloc_std_chain(sc, xfer->length, xfer, &data, &dataend); 1853 1854 if (err) 1855 return (err); 1856 dataend->td.td_status |= htole32(UHCI_TD_IOC); 1857 1858 #ifdef UHCI_DEBUG 1859 if (uhcidebug > 10) { 1860 DPRINTF(("uhci_device_intr_start: data(1)\n")); 1861 uhci_dump_tds(data); 1862 uhci_dump_qh(upipe->u.intr.qhs[0]); 1863 } 1864 #endif 1865 1866 s = splusb(); 1867 /* Set up interrupt info. */ 1868 ux->stdstart = data; 1869 ux->stdend = dataend; 1870 #ifdef DIAGNOSTIC 1871 if (!ux->isdone) { 1872 printf("uhci_device_intr_transfer: not done, ux=%p\n", ux); 1873 } 1874 ux->isdone = 0; 1875 #endif 1876 1877 DPRINTFN(10,("uhci_device_intr_start: qhs[0]=%p\n", 1878 upipe->u.intr.qhs[0])); 1879 for (i = 0; i < upipe->u.intr.npoll; i++) { 1880 sqh = upipe->u.intr.qhs[i]; 1881 sqh->elink = data; 1882 sqh->qh.qh_elink = htole32(data->physaddr | UHCI_PTR_TD); 1883 } 1884 uhci_add_intr_list(sc, ux); 1885 xfer->status = USBD_IN_PROGRESS; 1886 splx(s); 1887 1888 #ifdef UHCI_DEBUG 1889 if (uhcidebug > 10) { 1890 DPRINTF(("uhci_device_intr_start: data(2)\n")); 1891 uhci_dump_tds(data); 1892 uhci_dump_qh(upipe->u.intr.qhs[0]); 1893 } 1894 #endif 1895 1896 return (USBD_IN_PROGRESS); 1897 } 1898 1899 /* Abort a device control request. */ 1900 void 1901 uhci_device_ctrl_abort(struct usbd_xfer *xfer) 1902 { 1903 DPRINTF(("uhci_device_ctrl_abort:\n")); 1904 uhci_abort_xfer(xfer, USBD_CANCELLED); 1905 } 1906 1907 /* Close a device control pipe. */ 1908 void 1909 uhci_device_ctrl_close(struct usbd_pipe *pipe) 1910 { 1911 } 1912 1913 void 1914 uhci_device_intr_abort(struct usbd_xfer *xfer) 1915 { 1916 KASSERT(!xfer->pipe->repeat || xfer->pipe->intrxfer == xfer); 1917 1918 uhci_abort_xfer(xfer, USBD_CANCELLED); 1919 } 1920 1921 /* Close a device interrupt pipe. */ 1922 void 1923 uhci_device_intr_close(struct usbd_pipe *pipe) 1924 { 1925 struct uhci_pipe *upipe = (struct uhci_pipe *)pipe; 1926 struct uhci_softc *sc = (struct uhci_softc *)pipe->device->bus; 1927 struct uhci_soft_qh **qhs; 1928 int i, npoll; 1929 int s; 1930 1931 /* Unlink descriptors from controller data structures. */ 1932 qhs = upipe->u.intr.qhs; 1933 npoll = upipe->u.intr.npoll; 1934 s = splusb(); 1935 for (i = 0; i < npoll; i++) 1936 uhci_remove_intr(sc, upipe->u.intr.qhs[i]); 1937 splx(s); 1938 1939 /* 1940 * We now have to wait for any activity on the physical 1941 * descriptors to stop. 1942 */ 1943 usb_delay_ms(&sc->sc_bus, 2); 1944 1945 for(i = 0; i < npoll; i++) 1946 uhci_free_sqh(sc, upipe->u.intr.qhs[i]); 1947 free(qhs, M_USBHC, npoll * sizeof(*qhs)); 1948 1949 /* XXX free other resources */ 1950 } 1951 1952 usbd_status 1953 uhci_device_request(struct usbd_xfer *xfer) 1954 { 1955 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 1956 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 1957 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 1958 usb_device_request_t *req = &xfer->request; 1959 int addr = xfer->device->address; 1960 int endpt = xfer->pipe->endpoint->edesc->bEndpointAddress; 1961 struct uhci_soft_td *setup, *data, *stat, *next, *dataend; 1962 struct uhci_soft_qh *sqh; 1963 u_int len; 1964 u_int32_t ls; 1965 usbd_status err; 1966 int s; 1967 1968 DPRINTFN(3,("uhci_device_request type=0x%02x, request=0x%02x, " 1969 "wValue=0x%04x, wIndex=0x%04x len=%u, addr=%d, endpt=%d\n", 1970 req->bmRequestType, req->bRequest, UGETW(req->wValue), 1971 UGETW(req->wIndex), UGETW(req->wLength), 1972 addr, endpt)); 1973 1974 ls = xfer->device->speed == USB_SPEED_LOW ? UHCI_TD_LS : 0; 1975 len = UGETW(req->wLength); 1976 1977 setup = upipe->u.ctl.setup; 1978 stat = upipe->u.ctl.stat; 1979 sqh = upipe->u.ctl.sqh; 1980 1981 /* Set up data transaction */ 1982 if (len != 0) { 1983 upipe->nexttoggle = 1; 1984 err = uhci_alloc_std_chain(sc, len, xfer, &data, &dataend); 1985 if (err) 1986 return (err); 1987 next = data; 1988 dataend->link.std = stat; 1989 dataend->td.td_link = htole32(stat->physaddr | UHCI_PTR_VF | UHCI_PTR_TD); 1990 } else { 1991 next = stat; 1992 } 1993 upipe->u.ctl.length = len; 1994 1995 memcpy(KERNADDR(&upipe->u.ctl.reqdma, 0), req, sizeof *req); 1996 1997 setup->link.std = next; 1998 setup->td.td_link = htole32(next->physaddr | UHCI_PTR_VF | UHCI_PTR_TD); 1999 setup->td.td_status = htole32(UHCI_TD_SET_ERRCNT(3) | ls | 2000 UHCI_TD_ACTIVE); 2001 setup->td.td_token = htole32(UHCI_TD_SETUP(sizeof *req, endpt, addr)); 2002 setup->td.td_buffer = htole32(DMAADDR(&upipe->u.ctl.reqdma, 0)); 2003 2004 stat->link.std = NULL; 2005 stat->td.td_link = htole32(UHCI_PTR_T); 2006 stat->td.td_status = htole32(UHCI_TD_SET_ERRCNT(3) | ls | 2007 UHCI_TD_ACTIVE | UHCI_TD_IOC); 2008 stat->td.td_token = htole32(usbd_xfer_isread(xfer) ? 2009 UHCI_TD_OUT(0, endpt, addr, 1) : UHCI_TD_IN (0, endpt, addr, 1)); 2010 stat->td.td_buffer = htole32(0); 2011 2012 #ifdef UHCI_DEBUG 2013 if (uhcidebug > 10) { 2014 DPRINTF(("uhci_device_request: before transfer\n")); 2015 uhci_dump_tds(setup); 2016 } 2017 #endif 2018 2019 /* Set up interrupt info. */ 2020 ux->stdstart = setup; 2021 ux->stdend = stat; 2022 #ifdef DIAGNOSTIC 2023 if (!ux->isdone) { 2024 printf("%s: not done, ux=%p\n", __func__, ux); 2025 } 2026 ux->isdone = 0; 2027 #endif 2028 2029 sqh->elink = setup; 2030 sqh->qh.qh_elink = htole32(setup->physaddr | UHCI_PTR_TD); 2031 2032 s = splusb(); 2033 if (xfer->device->speed == USB_SPEED_LOW) 2034 uhci_add_ls_ctrl(sc, sqh); 2035 else 2036 uhci_add_hs_ctrl(sc, sqh); 2037 uhci_add_intr_list(sc, ux); 2038 #ifdef UHCI_DEBUG 2039 if (uhcidebug > 12) { 2040 struct uhci_soft_td *std; 2041 struct uhci_soft_qh *xqh; 2042 struct uhci_soft_qh *sxqh; 2043 int maxqh = 0; 2044 uhci_physaddr_t link; 2045 DPRINTF(("uhci_device_request: follow from [0]\n")); 2046 for (std = sc->sc_vframes[0].htd, link = 0; 2047 (link & UHCI_PTR_QH) == 0; 2048 std = std->link.std) { 2049 link = letoh32(std->td.td_link); 2050 uhci_dump_td(std); 2051 } 2052 sxqh = (struct uhci_soft_qh *)std; 2053 uhci_dump_qh(sxqh); 2054 for (xqh = sxqh; 2055 xqh != NULL; 2056 xqh = (maxqh++ == 5 || xqh->hlink == sxqh || 2057 xqh->hlink == xqh ? NULL : xqh->hlink)) { 2058 uhci_dump_qh(xqh); 2059 } 2060 DPRINTF(("Enqueued QH:\n")); 2061 uhci_dump_qh(sqh); 2062 uhci_dump_tds(sqh->elink); 2063 } 2064 #endif 2065 if (xfer->timeout && !sc->sc_bus.use_polling) { 2066 timeout_del(&xfer->timeout_handle); 2067 timeout_set(&xfer->timeout_handle, uhci_timeout, xfer); 2068 timeout_add_msec(&xfer->timeout_handle, xfer->timeout); 2069 } 2070 xfer->status = USBD_IN_PROGRESS; 2071 splx(s); 2072 2073 return (USBD_NORMAL_COMPLETION); 2074 } 2075 2076 usbd_status 2077 uhci_device_isoc_transfer(struct usbd_xfer *xfer) 2078 { 2079 usbd_status err; 2080 2081 DPRINTFN(5,("uhci_device_isoc_transfer: xfer=%p\n", xfer)); 2082 2083 /* Put it on our queue, */ 2084 err = usb_insert_transfer(xfer); 2085 2086 /* bail out on error, */ 2087 if (err && err != USBD_IN_PROGRESS) 2088 return (err); 2089 2090 /* XXX should check inuse here */ 2091 2092 /* insert into schedule, */ 2093 uhci_device_isoc_enter(xfer); 2094 2095 /* and start if the pipe wasn't running */ 2096 if (!err) 2097 uhci_device_isoc_start(SIMPLEQ_FIRST(&xfer->pipe->queue)); 2098 2099 return (err); 2100 } 2101 2102 void 2103 uhci_device_isoc_enter(struct usbd_xfer *xfer) 2104 { 2105 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 2106 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 2107 struct iso *iso = &upipe->u.iso; 2108 struct uhci_soft_td *std; 2109 u_int32_t buf, len, status; 2110 int s, i, next, nframes; 2111 2112 DPRINTFN(5,("uhci_device_isoc_enter: used=%d next=%d xfer=%p " 2113 "nframes=%d\n", 2114 iso->inuse, iso->next, xfer, xfer->nframes)); 2115 2116 if (sc->sc_bus.dying) 2117 return; 2118 2119 if (xfer->status == USBD_IN_PROGRESS) { 2120 /* This request has already been entered into the frame list */ 2121 printf("uhci_device_isoc_enter: xfer=%p in frame list\n", xfer); 2122 /* XXX */ 2123 } 2124 2125 #ifdef DIAGNOSTIC 2126 if (iso->inuse >= UHCI_VFRAMELIST_COUNT) 2127 printf("uhci_device_isoc_enter: overflow!\n"); 2128 #endif 2129 2130 next = iso->next; 2131 if (next == -1) { 2132 /* Not in use yet, schedule it a few frames ahead. */ 2133 next = (UREAD2(sc, UHCI_FRNUM) + 3) % UHCI_VFRAMELIST_COUNT; 2134 DPRINTFN(2,("uhci_device_isoc_enter: start next=%d\n", next)); 2135 } 2136 2137 xfer->status = USBD_IN_PROGRESS; 2138 ((struct uhci_xfer *)xfer)->curframe = next; 2139 2140 buf = DMAADDR(&xfer->dmabuf, 0); 2141 status = UHCI_TD_ZERO_ACTLEN(UHCI_TD_SET_ERRCNT(0) | 2142 UHCI_TD_ACTIVE | 2143 UHCI_TD_IOS); 2144 nframes = xfer->nframes; 2145 s = splusb(); 2146 for (i = 0; i < nframes; i++) { 2147 std = iso->stds[next]; 2148 if (++next >= UHCI_VFRAMELIST_COUNT) 2149 next = 0; 2150 len = xfer->frlengths[i]; 2151 std->td.td_buffer = htole32(buf); 2152 if (i == nframes - 1) 2153 status |= UHCI_TD_IOC; 2154 std->td.td_status = htole32(status); 2155 std->td.td_token &= htole32(~UHCI_TD_MAXLEN_MASK); 2156 std->td.td_token |= htole32(UHCI_TD_SET_MAXLEN(len)); 2157 #ifdef UHCI_DEBUG 2158 if (uhcidebug > 5) { 2159 DPRINTFN(5,("uhci_device_isoc_enter: TD %d\n", i)); 2160 uhci_dump_td(std); 2161 } 2162 #endif 2163 buf += len; 2164 } 2165 iso->next = next; 2166 iso->inuse += xfer->nframes; 2167 2168 splx(s); 2169 } 2170 2171 usbd_status 2172 uhci_device_isoc_start(struct usbd_xfer *xfer) 2173 { 2174 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 2175 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 2176 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 2177 struct uhci_soft_td *end; 2178 int s, i; 2179 2180 DPRINTFN(5,("uhci_device_isoc_start: xfer=%p\n", xfer)); 2181 2182 if (sc->sc_bus.dying) 2183 return (USBD_IOERROR); 2184 2185 #ifdef DIAGNOSTIC 2186 if (xfer->status != USBD_IN_PROGRESS) 2187 printf("uhci_device_isoc_start: not in progress %p\n", xfer); 2188 #endif 2189 2190 /* Find the last TD */ 2191 i = ux->curframe + (xfer->nframes - 1); 2192 if (i >= UHCI_VFRAMELIST_COUNT) 2193 i -= UHCI_VFRAMELIST_COUNT; 2194 end = upipe->u.iso.stds[i]; 2195 2196 #ifdef DIAGNOSTIC 2197 if (end == NULL) { 2198 printf("uhci_device_isoc_start: end == NULL\n"); 2199 return (USBD_INVAL); 2200 } 2201 #endif 2202 2203 s = splusb(); 2204 2205 /* Set up interrupt info. */ 2206 ux->stdstart = end; 2207 ux->stdend = end; 2208 #ifdef DIAGNOSTIC 2209 if (!ux->isdone) 2210 printf("%s: not done, ux=%p\n", __func__, ux); 2211 ux->isdone = 0; 2212 #endif 2213 uhci_add_intr_list(sc, ux); 2214 2215 splx(s); 2216 2217 return (USBD_IN_PROGRESS); 2218 } 2219 2220 void 2221 uhci_device_isoc_abort(struct usbd_xfer *xfer) 2222 { 2223 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 2224 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 2225 struct uhci_soft_td **stds = upipe->u.iso.stds; 2226 struct uhci_soft_td *std; 2227 int i, n, s, nframes, maxlen, len; 2228 2229 s = splusb(); 2230 2231 /* Transfer is already done. */ 2232 if (xfer->status != USBD_NOT_STARTED && 2233 xfer->status != USBD_IN_PROGRESS) { 2234 splx(s); 2235 return; 2236 } 2237 2238 /* Give xfer the requested abort code. */ 2239 xfer->status = USBD_CANCELLED; 2240 2241 /* make hardware ignore it, */ 2242 nframes = xfer->nframes; 2243 n = ux->curframe; 2244 maxlen = 0; 2245 for (i = 0; i < nframes; i++) { 2246 std = stds[n]; 2247 std->td.td_status &= htole32(~(UHCI_TD_ACTIVE | UHCI_TD_IOC)); 2248 len = UHCI_TD_GET_MAXLEN(letoh32(std->td.td_token)); 2249 if (len > maxlen) 2250 maxlen = len; 2251 if (++n >= UHCI_VFRAMELIST_COUNT) 2252 n = 0; 2253 } 2254 2255 /* and wait until we are sure the hardware has finished. */ 2256 delay(maxlen); 2257 2258 #ifdef DIAGNOSTIC 2259 ux->isdone = 1; 2260 #endif 2261 /* Run callback and remove from interrupt list. */ 2262 usb_transfer_complete(xfer); 2263 2264 splx(s); 2265 } 2266 2267 void 2268 uhci_device_isoc_close(struct usbd_pipe *pipe) 2269 { 2270 struct uhci_softc *sc = (struct uhci_softc *)pipe->device->bus; 2271 struct uhci_pipe *upipe = (struct uhci_pipe *)pipe; 2272 struct uhci_soft_td *std, *vstd; 2273 struct iso *iso; 2274 int i, s; 2275 2276 /* 2277 * Make sure all TDs are marked as inactive. 2278 * Wait for completion. 2279 * Unschedule. 2280 * Deallocate. 2281 */ 2282 iso = &upipe->u.iso; 2283 2284 for (i = 0; i < UHCI_VFRAMELIST_COUNT; i++) 2285 iso->stds[i]->td.td_status &= htole32(~UHCI_TD_ACTIVE); 2286 usb_delay_ms(&sc->sc_bus, 2); /* wait for completion */ 2287 2288 s = splusb(); 2289 for (i = 0; i < UHCI_VFRAMELIST_COUNT; i++) { 2290 std = iso->stds[i]; 2291 for (vstd = sc->sc_vframes[i].htd; 2292 vstd != NULL && vstd->link.std != std; 2293 vstd = vstd->link.std) 2294 ; 2295 if (vstd == NULL) { 2296 /*panic*/ 2297 printf("uhci_device_isoc_close: %p not found\n", std); 2298 splx(s); 2299 return; 2300 } 2301 vstd->link = std->link; 2302 vstd->td.td_link = std->td.td_link; 2303 uhci_free_std(sc, std); 2304 } 2305 splx(s); 2306 2307 free(iso->stds, M_USBHC, UHCI_VFRAMELIST_COUNT * sizeof(*iso->stds)); 2308 } 2309 2310 usbd_status 2311 uhci_setup_isoc(struct usbd_pipe *pipe) 2312 { 2313 struct uhci_softc *sc = (struct uhci_softc *)pipe->device->bus; 2314 struct uhci_pipe *upipe = (struct uhci_pipe *)pipe; 2315 int addr = pipe->device->address; 2316 int endpt = pipe->endpoint->edesc->bEndpointAddress; 2317 int rd = UE_GET_DIR(endpt) == UE_DIR_IN; 2318 struct uhci_soft_td *std, *vstd; 2319 u_int32_t token; 2320 struct iso *iso; 2321 int i, s; 2322 2323 iso = &upipe->u.iso; 2324 iso->stds = mallocarray(UHCI_VFRAMELIST_COUNT, sizeof(*iso->stds), 2325 M_USBHC, M_WAITOK); 2326 2327 token = rd ? UHCI_TD_IN (0, endpt, addr, 0) : 2328 UHCI_TD_OUT(0, endpt, addr, 0); 2329 2330 /* Allocate the TDs and mark as inactive; */ 2331 for (i = 0; i < UHCI_VFRAMELIST_COUNT; i++) { 2332 std = uhci_alloc_std(sc); 2333 if (std == 0) 2334 goto bad; 2335 std->td.td_status = htole32(UHCI_TD_IOS); /* iso, inactive */ 2336 std->td.td_token = htole32(token); 2337 iso->stds[i] = std; 2338 } 2339 2340 /* Insert TDs into schedule. */ 2341 s = splusb(); 2342 for (i = 0; i < UHCI_VFRAMELIST_COUNT; i++) { 2343 std = iso->stds[i]; 2344 vstd = sc->sc_vframes[i].htd; 2345 std->link = vstd->link; 2346 std->td.td_link = vstd->td.td_link; 2347 vstd->link.std = std; 2348 vstd->td.td_link = htole32(std->physaddr | UHCI_PTR_TD); 2349 } 2350 splx(s); 2351 2352 iso->next = -1; 2353 iso->inuse = 0; 2354 2355 return (USBD_NORMAL_COMPLETION); 2356 2357 bad: 2358 while (--i >= 0) 2359 uhci_free_std(sc, iso->stds[i]); 2360 free(iso->stds, M_USBHC, UHCI_VFRAMELIST_COUNT * sizeof(*iso->stds)); 2361 return (USBD_NOMEM); 2362 } 2363 2364 void 2365 uhci_device_isoc_done(struct usbd_xfer *xfer) 2366 { 2367 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 2368 2369 DPRINTFN(4, ("uhci_device_isoc_done: length=%d\n", xfer->actlen)); 2370 2371 if (!uhci_active_intr_list(ux)) 2372 return; 2373 2374 #ifdef DIAGNOSTIC 2375 if (ux->stdend == NULL) { 2376 printf("uhci_device_isoc_done: xfer=%p stdend==NULL\n", xfer); 2377 #ifdef UHCI_DEBUG 2378 uhci_dump_xfer(ux); 2379 #endif 2380 return; 2381 } 2382 #endif 2383 2384 /* Turn off the interrupt since it is active even if the TD is not. */ 2385 ux->stdend->td.td_status &= htole32(~UHCI_TD_IOC); 2386 2387 uhci_del_intr_list(ux); /* remove from active list */ 2388 } 2389 2390 void 2391 uhci_device_intr_done(struct usbd_xfer *xfer) 2392 { 2393 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 2394 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 2395 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 2396 struct uhci_soft_qh *sqh; 2397 int i, npoll; 2398 2399 DPRINTFN(5, ("uhci_device_intr_done: length=%d\n", xfer->actlen)); 2400 2401 npoll = upipe->u.intr.npoll; 2402 for(i = 0; i < npoll; i++) { 2403 sqh = upipe->u.intr.qhs[i]; 2404 sqh->elink = NULL; 2405 sqh->qh.qh_elink = htole32(UHCI_PTR_T); 2406 } 2407 uhci_free_std_chain(sc, ux->stdstart, NULL); 2408 2409 /* XXX Wasteful. */ 2410 if (xfer->pipe->repeat) { 2411 struct uhci_soft_td *data, *dataend; 2412 2413 DPRINTFN(5,("uhci_device_intr_done: requeuing\n")); 2414 2415 /* This alloc cannot fail since we freed the chain above. */ 2416 uhci_alloc_std_chain(sc, xfer->length, xfer, &data, &dataend); 2417 dataend->td.td_status |= htole32(UHCI_TD_IOC); 2418 2419 #ifdef UHCI_DEBUG 2420 if (uhcidebug > 10) { 2421 DPRINTF(("uhci_device_intr_done: data(1)\n")); 2422 uhci_dump_tds(data); 2423 uhci_dump_qh(upipe->u.intr.qhs[0]); 2424 } 2425 #endif 2426 2427 ux->stdstart = data; 2428 ux->stdend = dataend; 2429 #ifdef DIAGNOSTIC 2430 if (!ux->isdone) { 2431 printf("%s: not done, ux=%p\n", __func__, ux); 2432 } 2433 ux->isdone = 0; 2434 #endif 2435 for (i = 0; i < npoll; i++) { 2436 sqh = upipe->u.intr.qhs[i]; 2437 sqh->elink = data; 2438 sqh->qh.qh_elink = htole32(data->physaddr | UHCI_PTR_TD); 2439 } 2440 xfer->status = USBD_IN_PROGRESS; 2441 /* The ux is already on the examined list, just leave it. */ 2442 } else { 2443 DPRINTFN(5,("uhci_device_intr_done: removing\n")); 2444 if (uhci_active_intr_list(ux)) 2445 uhci_del_intr_list(ux); 2446 } 2447 } 2448 2449 /* Deallocate request data structures */ 2450 void 2451 uhci_device_ctrl_done(struct usbd_xfer *xfer) 2452 { 2453 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 2454 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 2455 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 2456 2457 #ifdef DIAGNOSTIC 2458 if (!(xfer->rqflags & URQ_REQUEST)) 2459 panic("uhci_device_ctrl_done: not a request"); 2460 #endif 2461 2462 if (!uhci_active_intr_list(ux)) 2463 return; 2464 2465 uhci_del_intr_list(ux); /* remove from active list */ 2466 2467 if (xfer->device->speed == USB_SPEED_LOW) 2468 uhci_remove_ls_ctrl(sc, upipe->u.ctl.sqh); 2469 else 2470 uhci_remove_hs_ctrl(sc, upipe->u.ctl.sqh); 2471 2472 if (upipe->u.ctl.length != 0) 2473 uhci_free_std_chain(sc, ux->stdstart->link.std, ux->stdend); 2474 2475 DPRINTFN(5, ("uhci_device_ctrl_done: length=%d\n", xfer->actlen)); 2476 } 2477 2478 /* Deallocate request data structures */ 2479 void 2480 uhci_device_bulk_done(struct usbd_xfer *xfer) 2481 { 2482 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 2483 struct uhci_pipe *upipe = (struct uhci_pipe *)xfer->pipe; 2484 struct uhci_xfer *ux = (struct uhci_xfer *)xfer; 2485 2486 DPRINTFN(5,("uhci_device_bulk_done: xfer=%p ux=%p sc=%p upipe=%p\n", 2487 xfer, ux, sc, upipe)); 2488 2489 if (!uhci_active_intr_list(ux)) 2490 return; 2491 2492 uhci_del_intr_list(ux); /* remove from active list */ 2493 2494 uhci_remove_bulk(sc, upipe->u.bulk.sqh); 2495 2496 uhci_free_std_chain(sc, ux->stdstart, NULL); 2497 2498 DPRINTFN(5, ("uhci_device_bulk_done: length=%d\n", xfer->actlen)); 2499 } 2500 2501 /* Add interrupt QH, called with vflock. */ 2502 void 2503 uhci_add_intr(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 2504 { 2505 struct uhci_vframe *vf = &sc->sc_vframes[sqh->pos]; 2506 struct uhci_soft_qh *eqh; 2507 2508 DPRINTFN(4, ("uhci_add_intr: n=%d sqh=%p\n", sqh->pos, sqh)); 2509 2510 eqh = vf->eqh; 2511 sqh->hlink = eqh->hlink; 2512 sqh->qh.qh_hlink = eqh->qh.qh_hlink; 2513 eqh->hlink = sqh; 2514 eqh->qh.qh_hlink = htole32(sqh->physaddr | UHCI_PTR_QH); 2515 vf->eqh = sqh; 2516 vf->bandwidth++; 2517 } 2518 2519 /* Remove interrupt QH. */ 2520 void 2521 uhci_remove_intr(struct uhci_softc *sc, struct uhci_soft_qh *sqh) 2522 { 2523 struct uhci_vframe *vf = &sc->sc_vframes[sqh->pos]; 2524 struct uhci_soft_qh *pqh; 2525 2526 DPRINTFN(4, ("uhci_remove_intr: n=%d sqh=%p\n", sqh->pos, sqh)); 2527 2528 /* See comment in uhci_remove_ctrl() */ 2529 if (!(sqh->qh.qh_elink & htole32(UHCI_PTR_T))) { 2530 sqh->qh.qh_elink = htole32(UHCI_PTR_T); 2531 delay(UHCI_QH_REMOVE_DELAY); 2532 } 2533 2534 pqh = uhci_find_prev_qh(vf->hqh, sqh); 2535 pqh->hlink = sqh->hlink; 2536 pqh->qh.qh_hlink = sqh->qh.qh_hlink; 2537 delay(UHCI_QH_REMOVE_DELAY); 2538 if (vf->eqh == sqh) 2539 vf->eqh = pqh; 2540 vf->bandwidth--; 2541 } 2542 2543 usbd_status 2544 uhci_device_setintr(struct uhci_softc *sc, struct uhci_pipe *upipe, int ival) 2545 { 2546 struct uhci_soft_qh *sqh, **qhs; 2547 int i, npoll, s; 2548 u_int bestbw, bw, bestoffs, offs; 2549 2550 DPRINTFN(2, ("uhci_device_setintr: pipe=%p\n", upipe)); 2551 if (ival == 0) { 2552 printf("uhci_device_setintr: 0 interval\n"); 2553 return (USBD_INVAL); 2554 } 2555 2556 if (ival > UHCI_VFRAMELIST_COUNT) 2557 ival = UHCI_VFRAMELIST_COUNT; 2558 npoll = (UHCI_VFRAMELIST_COUNT + ival - 1) / ival; 2559 DPRINTFN(2, ("uhci_device_setintr: ival=%d npoll=%d\n", ival, npoll)); 2560 2561 qhs = mallocarray(npoll, sizeof(*qhs), M_USBHC, M_NOWAIT); 2562 if (qhs == NULL) 2563 return (USBD_NOMEM); 2564 2565 /* 2566 * Figure out which offset in the schedule that has most 2567 * bandwidth left over. 2568 */ 2569 #define MOD(i) ((i) & (UHCI_VFRAMELIST_COUNT-1)) 2570 for (bestoffs = offs = 0, bestbw = ~0; offs < ival; offs++) { 2571 for (bw = i = 0; i < npoll; i++) 2572 bw += sc->sc_vframes[MOD(i * ival + offs)].bandwidth; 2573 if (bw < bestbw) { 2574 bestbw = bw; 2575 bestoffs = offs; 2576 } 2577 } 2578 DPRINTFN(1, ("uhci_device_setintr: bw=%d offs=%d\n", bestbw, bestoffs)); 2579 2580 for(i = 0; i < npoll; i++) { 2581 sqh = uhci_alloc_sqh(sc); 2582 if (sqh == NULL) { 2583 while (i > 0) 2584 uhci_free_sqh(sc, qhs[--i]); 2585 free(qhs, M_USBHC, npoll * sizeof(*qhs)); 2586 return (USBD_NOMEM); 2587 } 2588 sqh->elink = NULL; 2589 sqh->qh.qh_elink = htole32(UHCI_PTR_T); 2590 sqh->pos = MOD(i * ival + bestoffs); 2591 qhs[i] = sqh; 2592 } 2593 #undef MOD 2594 2595 upipe->u.intr.npoll = npoll; 2596 upipe->u.intr.qhs = qhs; 2597 2598 s = splusb(); 2599 /* Enter QHs into the controller data structures. */ 2600 for(i = 0; i < npoll; i++) 2601 uhci_add_intr(sc, upipe->u.intr.qhs[i]); 2602 splx(s); 2603 2604 DPRINTFN(5, ("uhci_device_setintr: returns %p\n", upipe)); 2605 return (USBD_NORMAL_COMPLETION); 2606 } 2607 2608 /* Open a new pipe. */ 2609 usbd_status 2610 uhci_open(struct usbd_pipe *pipe) 2611 { 2612 struct uhci_softc *sc = (struct uhci_softc *)pipe->device->bus; 2613 struct uhci_pipe *upipe = (struct uhci_pipe *)pipe; 2614 usb_endpoint_descriptor_t *ed = pipe->endpoint->edesc; 2615 usbd_status err; 2616 int ival; 2617 2618 DPRINTFN(1, ("uhci_open: pipe=%p, addr=%d, endpt=%d\n", 2619 pipe, pipe->device->address, ed->bEndpointAddress)); 2620 2621 upipe->nexttoggle = pipe->endpoint->savedtoggle; 2622 2623 /* Root Hub */ 2624 if (pipe->device->depth == 0) { 2625 switch (ed->bEndpointAddress) { 2626 case USB_CONTROL_ENDPOINT: 2627 pipe->methods = &uhci_root_ctrl_methods; 2628 break; 2629 case UE_DIR_IN | UHCI_INTR_ENDPT: 2630 pipe->methods = &uhci_root_intr_methods; 2631 break; 2632 default: 2633 return (USBD_INVAL); 2634 } 2635 } else { 2636 switch (UE_GET_XFERTYPE(ed->bmAttributes)) { 2637 case UE_CONTROL: 2638 pipe->methods = &uhci_device_ctrl_methods; 2639 upipe->u.ctl.sqh = uhci_alloc_sqh(sc); 2640 if (upipe->u.ctl.sqh == NULL) 2641 goto bad; 2642 upipe->u.ctl.setup = uhci_alloc_std(sc); 2643 if (upipe->u.ctl.setup == NULL) { 2644 uhci_free_sqh(sc, upipe->u.ctl.sqh); 2645 goto bad; 2646 } 2647 upipe->u.ctl.stat = uhci_alloc_std(sc); 2648 if (upipe->u.ctl.stat == NULL) { 2649 uhci_free_sqh(sc, upipe->u.ctl.sqh); 2650 uhci_free_std(sc, upipe->u.ctl.setup); 2651 goto bad; 2652 } 2653 err = usb_allocmem(&sc->sc_bus, 2654 sizeof(usb_device_request_t), 2655 0, &upipe->u.ctl.reqdma); 2656 if (err) { 2657 uhci_free_sqh(sc, upipe->u.ctl.sqh); 2658 uhci_free_std(sc, upipe->u.ctl.setup); 2659 uhci_free_std(sc, upipe->u.ctl.stat); 2660 goto bad; 2661 } 2662 break; 2663 case UE_INTERRUPT: 2664 pipe->methods = &uhci_device_intr_methods; 2665 ival = pipe->interval; 2666 if (ival == USBD_DEFAULT_INTERVAL) 2667 ival = ed->bInterval; 2668 return (uhci_device_setintr(sc, upipe, ival)); 2669 case UE_ISOCHRONOUS: 2670 pipe->methods = &uhci_device_isoc_methods; 2671 return (uhci_setup_isoc(pipe)); 2672 case UE_BULK: 2673 pipe->methods = &uhci_device_bulk_methods; 2674 upipe->u.bulk.sqh = uhci_alloc_sqh(sc); 2675 if (upipe->u.bulk.sqh == NULL) 2676 goto bad; 2677 break; 2678 } 2679 } 2680 return (USBD_NORMAL_COMPLETION); 2681 2682 bad: 2683 return (USBD_NOMEM); 2684 } 2685 2686 /* 2687 * Data structures and routines to emulate the root hub. 2688 */ 2689 usb_device_descriptor_t uhci_devd = { 2690 USB_DEVICE_DESCRIPTOR_SIZE, 2691 UDESC_DEVICE, /* type */ 2692 {0x00, 0x01}, /* USB version */ 2693 UDCLASS_HUB, /* class */ 2694 UDSUBCLASS_HUB, /* subclass */ 2695 UDPROTO_FSHUB, /* protocol */ 2696 64, /* max packet */ 2697 {0},{0},{0x00,0x01}, /* device id */ 2698 1,2,0, /* string indices */ 2699 1 /* # of configurations */ 2700 }; 2701 2702 usb_config_descriptor_t uhci_confd = { 2703 USB_CONFIG_DESCRIPTOR_SIZE, 2704 UDESC_CONFIG, 2705 {USB_CONFIG_DESCRIPTOR_SIZE + 2706 USB_INTERFACE_DESCRIPTOR_SIZE + 2707 USB_ENDPOINT_DESCRIPTOR_SIZE}, 2708 1, 2709 1, 2710 0, 2711 UC_BUS_POWERED | UC_SELF_POWERED, 2712 0 /* max power */ 2713 }; 2714 2715 usb_interface_descriptor_t uhci_ifcd = { 2716 USB_INTERFACE_DESCRIPTOR_SIZE, 2717 UDESC_INTERFACE, 2718 0, 2719 0, 2720 1, 2721 UICLASS_HUB, 2722 UISUBCLASS_HUB, 2723 UIPROTO_FSHUB, 2724 0 2725 }; 2726 2727 usb_endpoint_descriptor_t uhci_endpd = { 2728 USB_ENDPOINT_DESCRIPTOR_SIZE, 2729 UDESC_ENDPOINT, 2730 UE_DIR_IN | UHCI_INTR_ENDPT, 2731 UE_INTERRUPT, 2732 {8}, 2733 255 2734 }; 2735 2736 usb_hub_descriptor_t uhci_hubd_piix = { 2737 USB_HUB_DESCRIPTOR_SIZE, 2738 UDESC_HUB, 2739 2, 2740 { UHD_PWR_NO_SWITCH | UHD_OC_INDIVIDUAL, 0 }, 2741 50, /* power on to power good */ 2742 0, 2743 { 0x00 }, /* both ports are removable */ 2744 }; 2745 2746 /* 2747 * The USB hub protocol requires that SET_FEATURE(PORT_RESET) also 2748 * enables the port, and also states that SET_FEATURE(PORT_ENABLE) 2749 * should not be used by the USB subsystem. As we cannot issue a 2750 * SET_FEATURE(PORT_ENABLE) externally, we must ensure that the port 2751 * will be enabled as part of the reset. 2752 * 2753 * On the VT83C572, the port cannot be successfully enabled until the 2754 * outstanding "port enable change" and "connection status change" 2755 * events have been reset. 2756 */ 2757 usbd_status 2758 uhci_portreset(struct uhci_softc *sc, int index) 2759 { 2760 int lim, port, x; 2761 2762 if (index == 1) 2763 port = UHCI_PORTSC1; 2764 else if (index == 2) 2765 port = UHCI_PORTSC2; 2766 else 2767 return (USBD_IOERROR); 2768 2769 x = URWMASK(UREAD2(sc, port)); 2770 UWRITE2(sc, port, x | UHCI_PORTSC_PR); 2771 2772 usb_delay_ms(&sc->sc_bus, USB_PORT_ROOT_RESET_DELAY); 2773 2774 DPRINTFN(3,("uhci port %d reset, status0 = 0x%04x\n", 2775 index, UREAD2(sc, port))); 2776 2777 x = URWMASK(UREAD2(sc, port)); 2778 UWRITE2(sc, port, x & ~UHCI_PORTSC_PR); 2779 2780 delay(100); 2781 2782 DPRINTFN(3,("uhci port %d reset, status1 = 0x%04x\n", 2783 index, UREAD2(sc, port))); 2784 2785 x = URWMASK(UREAD2(sc, port)); 2786 UWRITE2(sc, port, x | UHCI_PORTSC_PE); 2787 2788 for (lim = 10; --lim > 0;) { 2789 usb_delay_ms(&sc->sc_bus, USB_PORT_RESET_DELAY); 2790 2791 x = UREAD2(sc, port); 2792 2793 DPRINTFN(3,("uhci port %d iteration %u, status = 0x%04x\n", 2794 index, lim, x)); 2795 2796 if (!(x & UHCI_PORTSC_CCS)) { 2797 /* 2798 * No device is connected (or was disconnected 2799 * during reset). Consider the port reset. 2800 * The delay must be long enough to ensure on 2801 * the initial iteration that the device 2802 * connection will have been registered. 50ms 2803 * appears to be sufficient, but 20ms is not. 2804 */ 2805 DPRINTFN(3,("uhci port %d loop %u, device detached\n", 2806 index, lim)); 2807 break; 2808 } 2809 2810 if (x & (UHCI_PORTSC_POEDC | UHCI_PORTSC_CSC)) { 2811 /* 2812 * Port enabled changed and/or connection 2813 * status changed were set. Reset either or 2814 * both raised flags (by writing a 1 to that 2815 * bit), and wait again for state to settle. 2816 */ 2817 UWRITE2(sc, port, URWMASK(x) | 2818 (x & (UHCI_PORTSC_POEDC | UHCI_PORTSC_CSC))); 2819 continue; 2820 } 2821 2822 if (x & UHCI_PORTSC_PE) 2823 /* Port is enabled */ 2824 break; 2825 2826 UWRITE2(sc, port, URWMASK(x) | UHCI_PORTSC_PE); 2827 } 2828 2829 DPRINTFN(3,("uhci port %d reset, status2 = 0x%04x\n", 2830 index, UREAD2(sc, port))); 2831 2832 if (lim <= 0) { 2833 DPRINTFN(1,("uhci port %d reset timed out\n", index)); 2834 return (USBD_TIMEOUT); 2835 } 2836 2837 sc->sc_isreset = 1; 2838 return (USBD_NORMAL_COMPLETION); 2839 } 2840 2841 /* 2842 * Simulate a hardware hub by handling all the necessary requests. 2843 */ 2844 usbd_status 2845 uhci_root_ctrl_transfer(struct usbd_xfer *xfer) 2846 { 2847 usbd_status err; 2848 2849 /* Insert last in queue. */ 2850 err = usb_insert_transfer(xfer); 2851 if (err) 2852 return (err); 2853 2854 /* 2855 * Pipe isn't running (otherwise err would be USBD_INPROG), 2856 * so start it first. 2857 */ 2858 return (uhci_root_ctrl_start(SIMPLEQ_FIRST(&xfer->pipe->queue))); 2859 } 2860 2861 usbd_status 2862 uhci_root_ctrl_start(struct usbd_xfer *xfer) 2863 { 2864 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 2865 usb_device_request_t *req; 2866 void *buf = NULL; 2867 int port, x; 2868 int s, len, value, index, status, change, l, totlen = 0; 2869 usb_port_status_t ps; 2870 usbd_status err; 2871 2872 if (sc->sc_bus.dying) 2873 return (USBD_IOERROR); 2874 2875 #ifdef DIAGNOSTIC 2876 if (!(xfer->rqflags & URQ_REQUEST)) 2877 panic("uhci_root_ctrl_start: not a request"); 2878 #endif 2879 req = &xfer->request; 2880 2881 DPRINTFN(2,("uhci_root_ctrl_start type=0x%02x request=%02x\n", 2882 req->bmRequestType, req->bRequest)); 2883 2884 len = UGETW(req->wLength); 2885 value = UGETW(req->wValue); 2886 index = UGETW(req->wIndex); 2887 2888 if (len != 0) 2889 buf = KERNADDR(&xfer->dmabuf, 0); 2890 2891 #define C(x,y) ((x) | ((y) << 8)) 2892 switch(C(req->bRequest, req->bmRequestType)) { 2893 case C(UR_CLEAR_FEATURE, UT_WRITE_DEVICE): 2894 case C(UR_CLEAR_FEATURE, UT_WRITE_INTERFACE): 2895 case C(UR_CLEAR_FEATURE, UT_WRITE_ENDPOINT): 2896 /* 2897 * DEVICE_REMOTE_WAKEUP and ENDPOINT_HALT are no-ops 2898 * for the integrated root hub. 2899 */ 2900 break; 2901 case C(UR_GET_CONFIG, UT_READ_DEVICE): 2902 if (len > 0) { 2903 *(u_int8_t *)buf = sc->sc_conf; 2904 totlen = 1; 2905 } 2906 break; 2907 case C(UR_GET_DESCRIPTOR, UT_READ_DEVICE): 2908 DPRINTFN(2,("uhci_root_ctrl_start wValue=0x%04x\n", value)); 2909 switch(value >> 8) { 2910 case UDESC_DEVICE: 2911 if ((value & 0xff) != 0) { 2912 err = USBD_IOERROR; 2913 goto ret; 2914 } 2915 totlen = l = min(len, USB_DEVICE_DESCRIPTOR_SIZE); 2916 USETW(uhci_devd.idVendor, sc->sc_id_vendor); 2917 memcpy(buf, &uhci_devd, l); 2918 break; 2919 case UDESC_CONFIG: 2920 if ((value & 0xff) != 0) { 2921 err = USBD_IOERROR; 2922 goto ret; 2923 } 2924 totlen = l = min(len, USB_CONFIG_DESCRIPTOR_SIZE); 2925 memcpy(buf, &uhci_confd, l); 2926 buf = (char *)buf + l; 2927 len -= l; 2928 l = min(len, USB_INTERFACE_DESCRIPTOR_SIZE); 2929 totlen += l; 2930 memcpy(buf, &uhci_ifcd, l); 2931 buf = (char *)buf + l; 2932 len -= l; 2933 l = min(len, USB_ENDPOINT_DESCRIPTOR_SIZE); 2934 totlen += l; 2935 memcpy(buf, &uhci_endpd, l); 2936 break; 2937 case UDESC_STRING: 2938 if (len == 0) 2939 break; 2940 *(u_int8_t *)buf = 0; 2941 totlen = 1; 2942 switch (value & 0xff) { 2943 case 0: /* Language table */ 2944 totlen = usbd_str(buf, len, "\001"); 2945 break; 2946 case 1: /* Vendor */ 2947 totlen = usbd_str(buf, len, sc->sc_vendor); 2948 break; 2949 case 2: /* Product */ 2950 totlen = usbd_str(buf, len, "UHCI root hub"); 2951 break; 2952 } 2953 break; 2954 default: 2955 err = USBD_IOERROR; 2956 goto ret; 2957 } 2958 break; 2959 case C(UR_GET_INTERFACE, UT_READ_INTERFACE): 2960 if (len > 0) { 2961 *(u_int8_t *)buf = 0; 2962 totlen = 1; 2963 } 2964 break; 2965 case C(UR_GET_STATUS, UT_READ_DEVICE): 2966 if (len > 1) { 2967 USETW(((usb_status_t *)buf)->wStatus,UDS_SELF_POWERED); 2968 totlen = 2; 2969 } 2970 break; 2971 case C(UR_GET_STATUS, UT_READ_INTERFACE): 2972 case C(UR_GET_STATUS, UT_READ_ENDPOINT): 2973 if (len > 1) { 2974 USETW(((usb_status_t *)buf)->wStatus, 0); 2975 totlen = 2; 2976 } 2977 break; 2978 case C(UR_SET_ADDRESS, UT_WRITE_DEVICE): 2979 if (value >= USB_MAX_DEVICES) { 2980 err = USBD_IOERROR; 2981 goto ret; 2982 } 2983 break; 2984 case C(UR_SET_CONFIG, UT_WRITE_DEVICE): 2985 if (value != 0 && value != 1) { 2986 err = USBD_IOERROR; 2987 goto ret; 2988 } 2989 sc->sc_conf = value; 2990 break; 2991 case C(UR_SET_DESCRIPTOR, UT_WRITE_DEVICE): 2992 break; 2993 case C(UR_SET_FEATURE, UT_WRITE_DEVICE): 2994 case C(UR_SET_FEATURE, UT_WRITE_INTERFACE): 2995 case C(UR_SET_FEATURE, UT_WRITE_ENDPOINT): 2996 err = USBD_IOERROR; 2997 goto ret; 2998 case C(UR_SET_INTERFACE, UT_WRITE_INTERFACE): 2999 break; 3000 case C(UR_SYNCH_FRAME, UT_WRITE_ENDPOINT): 3001 break; 3002 /* Hub requests */ 3003 case C(UR_CLEAR_FEATURE, UT_WRITE_CLASS_DEVICE): 3004 break; 3005 case C(UR_CLEAR_FEATURE, UT_WRITE_CLASS_OTHER): 3006 DPRINTFN(3, ("uhci_root_ctrl_start: UR_CLEAR_PORT_FEATURE " 3007 "port=%d feature=%d\n", 3008 index, value)); 3009 if (index == 1) 3010 port = UHCI_PORTSC1; 3011 else if (index == 2) 3012 port = UHCI_PORTSC2; 3013 else { 3014 err = USBD_IOERROR; 3015 goto ret; 3016 } 3017 switch(value) { 3018 case UHF_PORT_ENABLE: 3019 x = URWMASK(UREAD2(sc, port)); 3020 UWRITE2(sc, port, x & ~UHCI_PORTSC_PE); 3021 break; 3022 case UHF_PORT_SUSPEND: 3023 x = URWMASK(UREAD2(sc, port)); 3024 UWRITE2(sc, port, x & ~UHCI_PORTSC_SUSP); 3025 break; 3026 case UHF_PORT_RESET: 3027 x = URWMASK(UREAD2(sc, port)); 3028 UWRITE2(sc, port, x & ~UHCI_PORTSC_PR); 3029 break; 3030 case UHF_C_PORT_CONNECTION: 3031 x = URWMASK(UREAD2(sc, port)); 3032 UWRITE2(sc, port, x | UHCI_PORTSC_CSC); 3033 break; 3034 case UHF_C_PORT_ENABLE: 3035 x = URWMASK(UREAD2(sc, port)); 3036 UWRITE2(sc, port, x | UHCI_PORTSC_POEDC); 3037 break; 3038 case UHF_C_PORT_OVER_CURRENT: 3039 x = URWMASK(UREAD2(sc, port)); 3040 UWRITE2(sc, port, x | UHCI_PORTSC_OCIC); 3041 break; 3042 case UHF_C_PORT_RESET: 3043 sc->sc_isreset = 0; 3044 err = USBD_NORMAL_COMPLETION; 3045 goto ret; 3046 case UHF_PORT_CONNECTION: 3047 case UHF_PORT_OVER_CURRENT: 3048 case UHF_PORT_POWER: 3049 case UHF_PORT_LOW_SPEED: 3050 case UHF_C_PORT_SUSPEND: 3051 default: 3052 err = USBD_IOERROR; 3053 goto ret; 3054 } 3055 break; 3056 case C(UR_GET_BUS_STATE, UT_READ_CLASS_OTHER): 3057 if (index == 1) 3058 port = UHCI_PORTSC1; 3059 else if (index == 2) 3060 port = UHCI_PORTSC2; 3061 else { 3062 err = USBD_IOERROR; 3063 goto ret; 3064 } 3065 if (len > 0) { 3066 *(u_int8_t *)buf = 3067 (UREAD2(sc, port) & UHCI_PORTSC_LS) >> 3068 UHCI_PORTSC_LS_SHIFT; 3069 totlen = 1; 3070 } 3071 break; 3072 case C(UR_GET_DESCRIPTOR, UT_READ_CLASS_DEVICE): 3073 if ((value & 0xff) != 0) { 3074 err = USBD_IOERROR; 3075 goto ret; 3076 } 3077 l = min(len, USB_HUB_DESCRIPTOR_SIZE); 3078 totlen = l; 3079 memcpy(buf, &uhci_hubd_piix, l); 3080 break; 3081 case C(UR_GET_STATUS, UT_READ_CLASS_DEVICE): 3082 if (len != 4) { 3083 err = USBD_IOERROR; 3084 goto ret; 3085 } 3086 memset(buf, 0, len); 3087 totlen = len; 3088 break; 3089 case C(UR_GET_STATUS, UT_READ_CLASS_OTHER): 3090 if (index == 1) 3091 port = UHCI_PORTSC1; 3092 else if (index == 2) 3093 port = UHCI_PORTSC2; 3094 else { 3095 err = USBD_IOERROR; 3096 goto ret; 3097 } 3098 if (len != 4) { 3099 err = USBD_IOERROR; 3100 goto ret; 3101 } 3102 x = UREAD2(sc, port); 3103 status = change = 0; 3104 if (x & UHCI_PORTSC_CCS) 3105 status |= UPS_CURRENT_CONNECT_STATUS; 3106 if (x & UHCI_PORTSC_CSC) 3107 change |= UPS_C_CONNECT_STATUS; 3108 if (x & UHCI_PORTSC_PE) 3109 status |= UPS_PORT_ENABLED; 3110 if (x & UHCI_PORTSC_POEDC) 3111 change |= UPS_C_PORT_ENABLED; 3112 if (x & UHCI_PORTSC_OCI) 3113 status |= UPS_OVERCURRENT_INDICATOR; 3114 if (x & UHCI_PORTSC_OCIC) 3115 change |= UPS_C_OVERCURRENT_INDICATOR; 3116 if (x & UHCI_PORTSC_SUSP) 3117 status |= UPS_SUSPEND; 3118 if (x & UHCI_PORTSC_LSDA) 3119 status |= UPS_LOW_SPEED; 3120 status |= UPS_PORT_POWER; 3121 if (sc->sc_isreset) 3122 change |= UPS_C_PORT_RESET; 3123 USETW(ps.wPortStatus, status); 3124 USETW(ps.wPortChange, change); 3125 l = min(len, sizeof ps); 3126 memcpy(buf, &ps, l); 3127 totlen = l; 3128 break; 3129 case C(UR_SET_DESCRIPTOR, UT_WRITE_CLASS_DEVICE): 3130 err = USBD_IOERROR; 3131 goto ret; 3132 case C(UR_SET_FEATURE, UT_WRITE_CLASS_DEVICE): 3133 break; 3134 case C(UR_SET_FEATURE, UT_WRITE_CLASS_OTHER): 3135 if (index == 1) 3136 port = UHCI_PORTSC1; 3137 else if (index == 2) 3138 port = UHCI_PORTSC2; 3139 else { 3140 err = USBD_IOERROR; 3141 goto ret; 3142 } 3143 switch(value) { 3144 case UHF_PORT_ENABLE: 3145 x = URWMASK(UREAD2(sc, port)); 3146 UWRITE2(sc, port, x | UHCI_PORTSC_PE); 3147 break; 3148 case UHF_PORT_SUSPEND: 3149 x = URWMASK(UREAD2(sc, port)); 3150 UWRITE2(sc, port, x | UHCI_PORTSC_SUSP); 3151 break; 3152 case UHF_PORT_RESET: 3153 err = uhci_portreset(sc, index); 3154 goto ret; 3155 case UHF_PORT_POWER: 3156 /* Pretend we turned on power */ 3157 err = USBD_NORMAL_COMPLETION; 3158 goto ret; 3159 case UHF_PORT_DISOWN_TO_1_1: 3160 /* accept, but do nothing */ 3161 err = USBD_NORMAL_COMPLETION; 3162 goto ret; 3163 case UHF_C_PORT_CONNECTION: 3164 case UHF_C_PORT_ENABLE: 3165 case UHF_C_PORT_OVER_CURRENT: 3166 case UHF_PORT_CONNECTION: 3167 case UHF_PORT_OVER_CURRENT: 3168 case UHF_PORT_LOW_SPEED: 3169 case UHF_C_PORT_SUSPEND: 3170 case UHF_C_PORT_RESET: 3171 default: 3172 err = USBD_IOERROR; 3173 goto ret; 3174 } 3175 break; 3176 default: 3177 err = USBD_IOERROR; 3178 goto ret; 3179 } 3180 xfer->actlen = totlen; 3181 err = USBD_NORMAL_COMPLETION; 3182 ret: 3183 xfer->status = err; 3184 s = splusb(); 3185 usb_transfer_complete(xfer); 3186 splx(s); 3187 return (err); 3188 } 3189 3190 /* Abort a root control request. */ 3191 void 3192 uhci_root_ctrl_abort(struct usbd_xfer *xfer) 3193 { 3194 /* Nothing to do, all transfers are synchronous. */ 3195 } 3196 3197 /* Close the root pipe. */ 3198 void 3199 uhci_root_ctrl_close(struct usbd_pipe *pipe) 3200 { 3201 DPRINTF(("uhci_root_ctrl_close\n")); 3202 } 3203 3204 void 3205 uhci_root_intr_abort(struct usbd_xfer *xfer) 3206 { 3207 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 3208 int s; 3209 3210 timeout_del(&sc->sc_root_intr); 3211 sc->sc_intrxfer = NULL; 3212 3213 xfer->status = USBD_CANCELLED; 3214 s = splusb(); 3215 usb_transfer_complete(xfer); 3216 splx(s); 3217 } 3218 3219 usbd_status 3220 uhci_root_intr_transfer(struct usbd_xfer *xfer) 3221 { 3222 usbd_status err; 3223 3224 /* Insert last in queue. */ 3225 err = usb_insert_transfer(xfer); 3226 if (err) 3227 return (err); 3228 3229 /* Pipe isn't running (otherwise err would be USBD_INPROG), 3230 * start first 3231 */ 3232 return (uhci_root_intr_start(SIMPLEQ_FIRST(&xfer->pipe->queue))); 3233 } 3234 3235 /* Start a transfer on the root interrupt pipe */ 3236 usbd_status 3237 uhci_root_intr_start(struct usbd_xfer *xfer) 3238 { 3239 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 3240 3241 if (sc->sc_bus.dying) 3242 return (USBD_IOERROR); 3243 3244 sc->sc_intrxfer = xfer; 3245 timeout_add_msec(&sc->sc_root_intr, 255); 3246 3247 return (USBD_IN_PROGRESS); 3248 } 3249 3250 void 3251 uhci_root_intr_close(struct usbd_pipe *pipe) 3252 { 3253 } 3254 3255 void 3256 uhci_root_intr_done(struct usbd_xfer *xfer) 3257 { 3258 struct uhci_softc *sc = (struct uhci_softc *)xfer->device->bus; 3259 3260 if (xfer->pipe->repeat) 3261 timeout_add_msec(&sc->sc_root_intr, 255); 3262 } 3263