libusb10.c revision 203774
1/* $FreeBSD: head/lib/libusb/libusb10.c 203774 2010-02-11 08:30:43Z wkoszek $ */ 2/*- 3 * Copyright (c) 2009 Sylvestre Gallon. All rights reserved. 4 * Copyright (c) 2009 Hans Petter Selasky. All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25 * SUCH DAMAGE. 26 */ 27 28#include <assert.h> 29#include <stdlib.h> 30#include <unistd.h> 31#include <stdio.h> 32#include <poll.h> 33#include <pthread.h> 34#include <errno.h> 35#include <sys/ioctl.h> 36#include <sys/fcntl.h> 37#include <sys/queue.h> 38 39#include "libusb20.h" 40#include "libusb20_desc.h" 41#include "libusb20_int.h" 42#include "libusb.h" 43#include "libusb10.h" 44 45static pthread_mutex_t default_context_lock = PTHREAD_MUTEX_INITIALIZER; 46struct libusb_context *usbi_default_context = NULL; 47 48/* Prototypes */ 49 50static struct libusb20_transfer *libusb10_get_transfer(struct libusb20_device *, uint8_t, uint8_t); 51static int libusb10_get_maxframe(struct libusb20_device *, libusb_transfer *); 52static int libusb10_get_buffsize(struct libusb20_device *, libusb_transfer *); 53static int libusb10_convert_error(uint8_t status); 54static void libusb10_complete_transfer(struct libusb20_transfer *, struct libusb_super_transfer *, int); 55static void libusb10_isoc_proxy(struct libusb20_transfer *); 56static void libusb10_bulk_intr_proxy(struct libusb20_transfer *); 57static void libusb10_ctrl_proxy(struct libusb20_transfer *); 58static void libusb10_submit_transfer_sub(struct libusb20_device *, uint8_t); 59 60/* Library initialisation / deinitialisation */ 61 62void 63libusb_set_debug(libusb_context *ctx, int level) 64{ 65 ctx = GET_CONTEXT(ctx); 66 if (ctx) 67 ctx->debug = level; 68} 69 70int 71libusb_init(libusb_context **context) 72{ 73 struct libusb_context *ctx; 74 char *debug; 75 int flag; 76 int ret; 77 78 ctx = malloc(sizeof(*ctx)); 79 if (!ctx) 80 return (LIBUSB_ERROR_INVALID_PARAM); 81 82 memset(ctx, 0, sizeof(*ctx)); 83 84 debug = getenv("LIBUSB_DEBUG"); 85 if (debug != NULL) { 86 ctx->debug = atoi(debug); 87 if (ctx->debug != 0) 88 ctx->debug_fixed = 1; 89 } 90 TAILQ_INIT(&ctx->pollfds); 91 TAILQ_INIT(&ctx->tr_done); 92 93 pthread_mutex_init(&ctx->ctx_lock, NULL); 94 pthread_cond_init(&ctx->ctx_cond, NULL); 95 96 ctx->ctx_handler = NO_THREAD; 97 98 ret = pipe(ctx->ctrl_pipe); 99 if (ret < 0) { 100 pthread_mutex_destroy(&ctx->ctx_lock); 101 pthread_cond_destroy(&ctx->ctx_cond); 102 free(ctx); 103 return (LIBUSB_ERROR_OTHER); 104 } 105 /* set non-blocking mode on the control pipe to avoid deadlock */ 106 flag = 1; 107 ret = fcntl(ctx->ctrl_pipe[0], O_NONBLOCK, &flag); 108 assert(ret != -1 && "Couldn't set O_NONBLOCK for ctx->ctrl_pipe[0]"); 109 flag = 1; 110 ret = fcntl(ctx->ctrl_pipe[1], O_NONBLOCK, &flag); 111 assert(ret != -1 && "Couldn't set O_NONBLOCK for ctx->ctrl_pipe[1]"); 112 113 libusb10_add_pollfd(ctx, &ctx->ctx_poll, NULL, ctx->ctrl_pipe[0], POLLIN); 114 115 pthread_mutex_lock(&default_context_lock); 116 if (usbi_default_context == NULL) { 117 usbi_default_context = ctx; 118 } 119 pthread_mutex_unlock(&default_context_lock); 120 121 if (context) 122 *context = ctx; 123 124 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_init complete"); 125 126 return (0); 127} 128 129void 130libusb_exit(libusb_context *ctx) 131{ 132 ctx = GET_CONTEXT(ctx); 133 134 if (ctx == NULL) 135 return; 136 137 /* XXX cleanup devices */ 138 139 libusb10_remove_pollfd(ctx, &ctx->ctx_poll); 140 close(ctx->ctrl_pipe[0]); 141 close(ctx->ctrl_pipe[1]); 142 pthread_mutex_destroy(&ctx->ctx_lock); 143 pthread_cond_destroy(&ctx->ctx_cond); 144 145 pthread_mutex_lock(&default_context_lock); 146 if (ctx == usbi_default_context) { 147 usbi_default_context = NULL; 148 } 149 pthread_mutex_unlock(&default_context_lock); 150 151 free(ctx); 152} 153 154/* Device handling and initialisation. */ 155 156ssize_t 157libusb_get_device_list(libusb_context *ctx, libusb_device ***list) 158{ 159 struct libusb20_backend *usb_backend; 160 struct libusb20_device *pdev; 161 struct libusb_device *dev; 162 int i; 163 164 ctx = GET_CONTEXT(ctx); 165 166 if (ctx == NULL) 167 return (LIBUSB_ERROR_INVALID_PARAM); 168 169 if (list == NULL) 170 return (LIBUSB_ERROR_INVALID_PARAM); 171 172 usb_backend = libusb20_be_alloc_default(); 173 if (usb_backend == NULL) 174 return (LIBUSB_ERROR_NO_MEM); 175 176 /* figure out how many USB devices are present */ 177 pdev = NULL; 178 i = 0; 179 while ((pdev = libusb20_be_device_foreach(usb_backend, pdev))) 180 i++; 181 182 /* allocate device pointer list */ 183 *list = malloc((i + 1) * sizeof(void *)); 184 if (*list == NULL) { 185 libusb20_be_free(usb_backend); 186 return (LIBUSB_ERROR_NO_MEM); 187 } 188 /* create libusb v1.0 compliant devices */ 189 i = 0; 190 while ((pdev = libusb20_be_device_foreach(usb_backend, NULL))) { 191 192 dev = malloc(sizeof(*dev)); 193 if (dev == NULL) { 194 while (i != 0) { 195 libusb_unref_device((*list)[i - 1]); 196 i--; 197 } 198 free(*list); 199 *list = NULL; 200 libusb20_be_free(usb_backend); 201 return (LIBUSB_ERROR_NO_MEM); 202 } 203 204 /* get device into libUSB v1.0 list */ 205 libusb20_be_dequeue_device(usb_backend, pdev); 206 207 memset(dev, 0, sizeof(*dev)); 208 209 /* init transfer queues */ 210 TAILQ_INIT(&dev->tr_head); 211 212 /* set context we belong to */ 213 dev->ctx = ctx; 214 215 /* link together the two structures */ 216 dev->os_priv = pdev; 217 pdev->privLuData = dev; 218 219 (*list)[i] = libusb_ref_device(dev); 220 i++; 221 } 222 (*list)[i] = NULL; 223 224 libusb20_be_free(usb_backend); 225 return (i); 226} 227 228void 229libusb_free_device_list(libusb_device **list, int unref_devices) 230{ 231 int i; 232 233 if (list == NULL) 234 return; /* be NULL safe */ 235 236 if (unref_devices) { 237 for (i = 0; list[i] != NULL; i++) 238 libusb_unref_device(list[i]); 239 } 240 free(list); 241} 242 243uint8_t 244libusb_get_bus_number(libusb_device *dev) 245{ 246 if (dev == NULL) 247 return (0); /* should not happen */ 248 return (libusb20_dev_get_bus_number(dev->os_priv)); 249} 250 251uint8_t 252libusb_get_device_address(libusb_device *dev) 253{ 254 if (dev == NULL) 255 return (0); /* should not happen */ 256 return (libusb20_dev_get_address(dev->os_priv)); 257} 258 259int 260libusb_get_max_packet_size(libusb_device *dev, uint8_t endpoint) 261{ 262 struct libusb_config_descriptor *pdconf; 263 struct libusb_interface *pinf; 264 struct libusb_interface_descriptor *pdinf; 265 struct libusb_endpoint_descriptor *pdend; 266 int i; 267 int j; 268 int k; 269 int ret; 270 271 if (dev == NULL) 272 return (LIBUSB_ERROR_NO_DEVICE); 273 274 ret = libusb_get_active_config_descriptor(dev, &pdconf); 275 if (ret < 0) 276 return (ret); 277 278 ret = LIBUSB_ERROR_NOT_FOUND; 279 for (i = 0; i < pdconf->bNumInterfaces; i++) { 280 pinf = &pdconf->interface[i]; 281 for (j = 0; j < pinf->num_altsetting; j++) { 282 pdinf = &pinf->altsetting[j]; 283 for (k = 0; k < pdinf->bNumEndpoints; k++) { 284 pdend = &pdinf->endpoint[k]; 285 if (pdend->bEndpointAddress == endpoint) { 286 ret = pdend->wMaxPacketSize; 287 goto out; 288 } 289 } 290 } 291 } 292 293out: 294 libusb_free_config_descriptor(pdconf); 295 return (ret); 296} 297 298libusb_device * 299libusb_ref_device(libusb_device *dev) 300{ 301 if (dev == NULL) 302 return (NULL); /* be NULL safe */ 303 304 CTX_LOCK(dev->ctx); 305 dev->refcnt++; 306 CTX_UNLOCK(dev->ctx); 307 308 return (dev); 309} 310 311void 312libusb_unref_device(libusb_device *dev) 313{ 314 if (dev == NULL) 315 return; /* be NULL safe */ 316 317 CTX_LOCK(dev->ctx); 318 dev->refcnt--; 319 CTX_UNLOCK(dev->ctx); 320 321 if (dev->refcnt == 0) { 322 libusb20_dev_free(dev->os_priv); 323 free(dev); 324 } 325} 326 327int 328libusb_open(libusb_device *dev, libusb_device_handle **devh) 329{ 330 libusb_context *ctx = dev->ctx; 331 struct libusb20_device *pdev = dev->os_priv; 332 uint8_t dummy; 333 int err; 334 335 if (devh == NULL) 336 return (LIBUSB_ERROR_INVALID_PARAM); 337 338 /* set default device handle value */ 339 *devh = NULL; 340 341 dev = libusb_ref_device(dev); 342 if (dev == NULL) 343 return (LIBUSB_ERROR_INVALID_PARAM); 344 345 err = libusb20_dev_open(pdev, 16 * 4 /* number of endpoints */ ); 346 if (err) { 347 libusb_unref_device(dev); 348 return (LIBUSB_ERROR_NO_MEM); 349 } 350 libusb10_add_pollfd(ctx, &dev->dev_poll, pdev, libusb20_dev_get_fd(pdev), POLLIN | 351 POLLOUT | POLLRDNORM | POLLWRNORM); 352 353 /* make sure our event loop detects the new device */ 354 dummy = 0; 355 err = write(ctx->ctrl_pipe[1], &dummy, sizeof(dummy)); 356 if (err < sizeof(dummy)) { 357 /* ignore error, if any */ 358 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_open write failed!"); 359 } 360 *devh = pdev; 361 362 return (0); 363} 364 365libusb_device_handle * 366libusb_open_device_with_vid_pid(libusb_context *ctx, uint16_t vendor_id, 367 uint16_t product_id) 368{ 369 struct libusb_device **devs; 370 struct libusb20_device *pdev; 371 struct LIBUSB20_DEVICE_DESC_DECODED *pdesc; 372 int i; 373 int j; 374 375 ctx = GET_CONTEXT(ctx); 376 if (ctx == NULL) 377 return (NULL); /* be NULL safe */ 378 379 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_open_device_width_vid_pid enter"); 380 381 if ((i = libusb_get_device_list(ctx, &devs)) < 0) 382 return (NULL); 383 384 for (j = 0; j < i; j++) { 385 pdev = devs[j]->os_priv; 386 pdesc = libusb20_dev_get_device_desc(pdev); 387 /* 388 * NOTE: The USB library will automatically swap the 389 * fields in the device descriptor to be of host 390 * endian type! 391 */ 392 if (pdesc->idVendor == vendor_id && 393 pdesc->idProduct == product_id) { 394 if (libusb_open(devs[j], &pdev) < 0) 395 pdev = NULL; 396 break; 397 } 398 } 399 if (j == i) 400 pdev = NULL; 401 402 libusb_free_device_list(devs, 1); 403 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_open_device_width_vid_pid leave"); 404 return (pdev); 405} 406 407void 408libusb_close(struct libusb20_device *pdev) 409{ 410 libusb_context *ctx; 411 struct libusb_device *dev; 412 uint8_t dummy; 413 int err; 414 415 if (pdev == NULL) 416 return; /* be NULL safe */ 417 418 dev = libusb_get_device(pdev); 419 ctx = dev->ctx; 420 421 libusb10_remove_pollfd(ctx, &dev->dev_poll); 422 423 libusb20_dev_close(pdev); 424 425 /* unref will free the "pdev" when the refcount reaches zero */ 426 libusb_unref_device(dev); 427 428 /* make sure our event loop detects the closed device */ 429 dummy = 0; 430 err = write(ctx->ctrl_pipe[1], &dummy, sizeof(dummy)); 431 if (err < sizeof(dummy)) { 432 /* ignore error, if any */ 433 DPRINTF(ctx, LIBUSB_DEBUG_FUNCTION, "libusb_close write failed!"); 434 } 435} 436 437libusb_device * 438libusb_get_device(struct libusb20_device *pdev) 439{ 440 if (pdev == NULL) 441 return (NULL); 442 return ((libusb_device *)pdev->privLuData); 443} 444 445int 446libusb_get_configuration(struct libusb20_device *pdev, int *config) 447{ 448 struct libusb20_config *pconf; 449 450 if (pdev == NULL || config == NULL) 451 return (LIBUSB_ERROR_INVALID_PARAM); 452 453 pconf = libusb20_dev_alloc_config(pdev, libusb20_dev_get_config_index(pdev)); 454 if (pconf == NULL) 455 return (LIBUSB_ERROR_NO_MEM); 456 457 *config = pconf->desc.bConfigurationValue; 458 459 free(pconf); 460 461 return (0); 462} 463 464int 465libusb_set_configuration(struct libusb20_device *pdev, int configuration) 466{ 467 struct libusb20_config *pconf; 468 struct libusb_device *dev; 469 int err; 470 uint8_t i; 471 472 dev = libusb_get_device(pdev); 473 474 if (dev == NULL) 475 return (LIBUSB_ERROR_INVALID_PARAM); 476 477 if (configuration < 1) { 478 /* unconfigure */ 479 i = 255; 480 } else { 481 for (i = 0; i != 255; i++) { 482 uint8_t found; 483 484 pconf = libusb20_dev_alloc_config(pdev, i); 485 if (pconf == NULL) 486 return (LIBUSB_ERROR_INVALID_PARAM); 487 found = (pconf->desc.bConfigurationValue 488 == configuration); 489 free(pconf); 490 491 if (found) 492 goto set_config; 493 } 494 return (LIBUSB_ERROR_INVALID_PARAM); 495 } 496 497set_config: 498 499 libusb10_cancel_all_transfer(dev); 500 501 libusb10_remove_pollfd(dev->ctx, &dev->dev_poll); 502 503 err = libusb20_dev_set_config_index(pdev, i); 504 505 libusb10_add_pollfd(dev->ctx, &dev->dev_poll, pdev, libusb20_dev_get_fd(pdev), POLLIN | 506 POLLOUT | POLLRDNORM | POLLWRNORM); 507 508 return (err ? LIBUSB_ERROR_INVALID_PARAM : 0); 509} 510 511int 512libusb_claim_interface(struct libusb20_device *pdev, int interface_number) 513{ 514 libusb_device *dev; 515 int err = 0; 516 517 dev = libusb_get_device(pdev); 518 if (dev == NULL) 519 return (LIBUSB_ERROR_INVALID_PARAM); 520 521 if (interface_number < 0 || interface_number > 31) 522 return (LIBUSB_ERROR_INVALID_PARAM); 523 524 CTX_LOCK(dev->ctx); 525 if (dev->claimed_interfaces & (1 << interface_number)) 526 err = LIBUSB_ERROR_BUSY; 527 528 if (!err) 529 dev->claimed_interfaces |= (1 << interface_number); 530 CTX_UNLOCK(dev->ctx); 531 return (err); 532} 533 534int 535libusb_release_interface(struct libusb20_device *pdev, int interface_number) 536{ 537 libusb_device *dev; 538 int err = 0; 539 540 dev = libusb_get_device(pdev); 541 if (dev == NULL) 542 return (LIBUSB_ERROR_INVALID_PARAM); 543 544 if (interface_number < 0 || interface_number > 31) 545 return (LIBUSB_ERROR_INVALID_PARAM); 546 547 CTX_LOCK(dev->ctx); 548 if (!(dev->claimed_interfaces & (1 << interface_number))) 549 err = LIBUSB_ERROR_NOT_FOUND; 550 551 if (!err) 552 dev->claimed_interfaces &= ~(1 << interface_number); 553 CTX_UNLOCK(dev->ctx); 554 return (err); 555} 556 557int 558libusb_set_interface_alt_setting(struct libusb20_device *pdev, 559 int interface_number, int alternate_setting) 560{ 561 libusb_device *dev; 562 int err = 0; 563 564 dev = libusb_get_device(pdev); 565 if (dev == NULL) 566 return (LIBUSB_ERROR_INVALID_PARAM); 567 568 if (interface_number < 0 || interface_number > 31) 569 return (LIBUSB_ERROR_INVALID_PARAM); 570 571 CTX_LOCK(dev->ctx); 572 if (!(dev->claimed_interfaces & (1 << interface_number))) 573 err = LIBUSB_ERROR_NOT_FOUND; 574 CTX_UNLOCK(dev->ctx); 575 576 if (err) 577 return (err); 578 579 libusb10_cancel_all_transfer(dev); 580 581 libusb10_remove_pollfd(dev->ctx, &dev->dev_poll); 582 583 err = libusb20_dev_set_alt_index(pdev, 584 interface_number, alternate_setting); 585 586 libusb10_add_pollfd(dev->ctx, &dev->dev_poll, 587 pdev, libusb20_dev_get_fd(pdev), 588 POLLIN | POLLOUT | POLLRDNORM | POLLWRNORM); 589 590 return (err ? LIBUSB_ERROR_OTHER : 0); 591} 592 593static struct libusb20_transfer * 594libusb10_get_transfer(struct libusb20_device *pdev, 595 uint8_t endpoint, uint8_t index) 596{ 597 index &= 1; /* double buffering */ 598 599 index |= (endpoint & LIBUSB20_ENDPOINT_ADDRESS_MASK) * 4; 600 601 if (endpoint & LIBUSB20_ENDPOINT_DIR_MASK) { 602 /* this is an IN endpoint */ 603 index |= 2; 604 } 605 return (libusb20_tr_get_pointer(pdev, index)); 606} 607 608int 609libusb_clear_halt(struct libusb20_device *pdev, uint8_t endpoint) 610{ 611 struct libusb20_transfer *xfer; 612 struct libusb_device *dev; 613 int err; 614 615 xfer = libusb10_get_transfer(pdev, endpoint, 0); 616 if (xfer == NULL) 617 return (LIBUSB_ERROR_INVALID_PARAM); 618 619 dev = libusb_get_device(pdev); 620 621 CTX_LOCK(dev->ctx); 622 err = libusb20_tr_open(xfer, 0, 0, endpoint); 623 CTX_UNLOCK(dev->ctx); 624 625 if (err != 0 && err != LIBUSB20_ERROR_BUSY) 626 return (LIBUSB_ERROR_OTHER); 627 628 libusb20_tr_clear_stall_sync(xfer); 629 630 /* check if we opened the transfer */ 631 if (err == 0) { 632 CTX_LOCK(dev->ctx); 633 libusb20_tr_close(xfer); 634 CTX_UNLOCK(dev->ctx); 635 } 636 return (0); /* success */ 637} 638 639int 640libusb_reset_device(struct libusb20_device *pdev) 641{ 642 libusb_device *dev; 643 int err; 644 645 dev = libusb_get_device(pdev); 646 if (dev == NULL) 647 return (LIBUSB20_ERROR_INVALID_PARAM); 648 649 libusb10_cancel_all_transfer(dev); 650 651 libusb10_remove_pollfd(dev->ctx, &dev->dev_poll); 652 653 err = libusb20_dev_reset(pdev); 654 655 libusb10_add_pollfd(dev->ctx, &dev->dev_poll, 656 pdev, libusb20_dev_get_fd(pdev), 657 POLLIN | POLLOUT | POLLRDNORM | POLLWRNORM); 658 659 return (err ? LIBUSB_ERROR_OTHER : 0); 660} 661 662int 663libusb_kernel_driver_active(struct libusb20_device *pdev, int interface) 664{ 665 if (pdev == NULL) 666 return (LIBUSB_ERROR_INVALID_PARAM); 667 668 return (libusb20_dev_kernel_driver_active( 669 pdev, interface)); 670} 671 672int 673libusb_detach_kernel_driver(struct libusb20_device *pdev, int interface) 674{ 675 int err; 676 677 if (pdev == NULL) 678 return (LIBUSB_ERROR_INVALID_PARAM); 679 680 err = libusb20_dev_detach_kernel_driver( 681 pdev, interface); 682 683 return (err ? LIBUSB20_ERROR_OTHER : 0); 684} 685 686int 687libusb_attach_kernel_driver(struct libusb20_device *pdev, int interface) 688{ 689 if (pdev == NULL) 690 return (LIBUSB_ERROR_INVALID_PARAM); 691 /* stub - currently not supported by libusb20 */ 692 return (0); 693} 694 695/* Asynchronous device I/O */ 696 697struct libusb_transfer * 698libusb_alloc_transfer(int iso_packets) 699{ 700 struct libusb_transfer *uxfer; 701 struct libusb_super_transfer *sxfer; 702 int len; 703 704 len = sizeof(struct libusb_transfer) + 705 sizeof(struct libusb_super_transfer) + 706 (iso_packets * sizeof(libusb_iso_packet_descriptor)); 707 708 sxfer = malloc(len); 709 if (sxfer == NULL) 710 return (NULL); 711 712 memset(sxfer, 0, len); 713 714 uxfer = (struct libusb_transfer *)( 715 ((uint8_t *)sxfer) + sizeof(*sxfer)); 716 717 /* set default value */ 718 uxfer->num_iso_packets = iso_packets; 719 720 return (uxfer); 721} 722 723void 724libusb_free_transfer(struct libusb_transfer *uxfer) 725{ 726 struct libusb_super_transfer *sxfer; 727 728 if (uxfer == NULL) 729 return; /* be NULL safe */ 730 731 sxfer = (struct libusb_super_transfer *)( 732 (uint8_t *)uxfer - sizeof(*sxfer)); 733 734 free(sxfer); 735} 736 737static int 738libusb10_get_maxframe(struct libusb20_device *pdev, libusb_transfer *xfer) 739{ 740 int ret; 741 int usb_speed; 742 743 usb_speed = libusb20_dev_get_speed(pdev); 744 745 switch (xfer->type) { 746 case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS: 747 switch (usb_speed) { 748 case LIBUSB20_SPEED_LOW: 749 case LIBUSB20_SPEED_FULL: 750 ret = 60 * 1; 751 break; 752 default: 753 ret = 60 * 8; 754 break; 755 } 756 break; 757 case LIBUSB_TRANSFER_TYPE_CONTROL: 758 ret = 2; 759 break; 760 default: 761 ret = 1; 762 break; 763 } 764 return (ret); 765} 766 767static int 768libusb10_get_buffsize(struct libusb20_device *pdev, libusb_transfer *xfer) 769{ 770 int ret; 771 int usb_speed; 772 773 usb_speed = libusb20_dev_get_speed(pdev); 774 775 switch (xfer->type) { 776 case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS: 777 ret = 0; /* kernel will auto-select */ 778 break; 779 case LIBUSB_TRANSFER_TYPE_CONTROL: 780 ret = 1024; 781 break; 782 default: 783 switch (usb_speed) { 784 case LIBUSB20_SPEED_LOW: 785 ret = 256; 786 break; 787 case LIBUSB20_SPEED_FULL: 788 ret = 4096; 789 break; 790 default: 791 ret = 16384; 792 break; 793 } 794 break; 795 } 796 return (ret); 797} 798 799static int 800libusb10_convert_error(uint8_t status) 801{ 802 ; /* indent fix */ 803 804 switch (status) { 805 case LIBUSB20_TRANSFER_START: 806 case LIBUSB20_TRANSFER_COMPLETED: 807 return (LIBUSB_TRANSFER_COMPLETED); 808 case LIBUSB20_TRANSFER_OVERFLOW: 809 return (LIBUSB_TRANSFER_OVERFLOW); 810 case LIBUSB20_TRANSFER_NO_DEVICE: 811 return (LIBUSB_TRANSFER_NO_DEVICE); 812 case LIBUSB20_TRANSFER_STALL: 813 return (LIBUSB_TRANSFER_STALL); 814 case LIBUSB20_TRANSFER_CANCELLED: 815 return (LIBUSB_TRANSFER_CANCELLED); 816 case LIBUSB20_TRANSFER_TIMED_OUT: 817 return (LIBUSB_TRANSFER_TIMED_OUT); 818 default: 819 return (LIBUSB_TRANSFER_ERROR); 820 } 821} 822 823/* This function must be called locked */ 824 825static void 826libusb10_complete_transfer(struct libusb20_transfer *pxfer, 827 struct libusb_super_transfer *sxfer, int status) 828{ 829 struct libusb_transfer *uxfer; 830 struct libusb_device *dev; 831 832 uxfer = (struct libusb_transfer *)( 833 ((uint8_t *)sxfer) + sizeof(*sxfer)); 834 835 if (pxfer != NULL) 836 libusb20_tr_set_priv_sc1(pxfer, NULL); 837 838 /* set transfer status */ 839 uxfer->status = status; 840 841 /* update super transfer state */ 842 sxfer->state = LIBUSB_SUPER_XFER_ST_NONE; 843 844 dev = libusb_get_device(uxfer->dev_handle); 845 846 TAILQ_INSERT_TAIL(&dev->ctx->tr_done, sxfer, entry); 847} 848 849/* This function must be called locked */ 850 851static void 852libusb10_isoc_proxy(struct libusb20_transfer *pxfer) 853{ 854 struct libusb_super_transfer *sxfer; 855 struct libusb_transfer *uxfer; 856 uint32_t actlen; 857 uint16_t iso_packets; 858 uint16_t i; 859 uint8_t status; 860 uint8_t flags; 861 862 status = libusb20_tr_get_status(pxfer); 863 sxfer = libusb20_tr_get_priv_sc1(pxfer); 864 actlen = libusb20_tr_get_actual_length(pxfer); 865 iso_packets = libusb20_tr_get_max_frames(pxfer); 866 867 if (sxfer == NULL) 868 return; /* cancelled - nothing to do */ 869 870 uxfer = (struct libusb_transfer *)( 871 ((uint8_t *)sxfer) + sizeof(*sxfer)); 872 873 if (iso_packets > uxfer->num_iso_packets) 874 iso_packets = uxfer->num_iso_packets; 875 876 if (iso_packets == 0) 877 return; /* nothing to do */ 878 879 /* make sure that the number of ISOCHRONOUS packets is valid */ 880 uxfer->num_iso_packets = iso_packets; 881 882 flags = uxfer->flags; 883 884 switch (status) { 885 case LIBUSB20_TRANSFER_COMPLETED: 886 887 /* update actual length */ 888 uxfer->actual_length = actlen; 889 for (i = 0; i != iso_packets; i++) { 890 uxfer->iso_packet_desc[i].actual_length = 891 libusb20_tr_get_length(pxfer, i); 892 } 893 libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED); 894 break; 895 896 case LIBUSB20_TRANSFER_START: 897 898 /* setup length(s) */ 899 actlen = 0; 900 for (i = 0; i != iso_packets; i++) { 901 libusb20_tr_setup_isoc(pxfer, 902 &uxfer->buffer[actlen], 903 uxfer->iso_packet_desc[i].length, i); 904 actlen += uxfer->iso_packet_desc[i].length; 905 } 906 907 /* no remainder */ 908 sxfer->rem_len = 0; 909 910 libusb20_tr_set_total_frames(pxfer, iso_packets); 911 libusb20_tr_submit(pxfer); 912 913 /* fork another USB transfer, if any */ 914 libusb10_submit_transfer_sub(libusb20_tr_get_priv_sc0(pxfer), uxfer->endpoint); 915 break; 916 917 default: 918 libusb10_complete_transfer(pxfer, sxfer, libusb10_convert_error(status)); 919 break; 920 } 921} 922 923/* This function must be called locked */ 924 925static void 926libusb10_bulk_intr_proxy(struct libusb20_transfer *pxfer) 927{ 928 struct libusb_super_transfer *sxfer; 929 struct libusb_transfer *uxfer; 930 uint32_t max_bulk; 931 uint32_t actlen; 932 uint8_t status; 933 uint8_t flags; 934 935 status = libusb20_tr_get_status(pxfer); 936 sxfer = libusb20_tr_get_priv_sc1(pxfer); 937 max_bulk = libusb20_tr_get_max_total_length(pxfer); 938 actlen = libusb20_tr_get_actual_length(pxfer); 939 940 if (sxfer == NULL) 941 return; /* cancelled - nothing to do */ 942 943 uxfer = (struct libusb_transfer *)( 944 ((uint8_t *)sxfer) + sizeof(*sxfer)); 945 946 flags = uxfer->flags; 947 948 switch (status) { 949 case LIBUSB20_TRANSFER_COMPLETED: 950 951 uxfer->actual_length += actlen; 952 953 /* check for short packet */ 954 if (sxfer->last_len != actlen) { 955 if (flags & LIBUSB_TRANSFER_SHORT_NOT_OK) { 956 libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_ERROR); 957 } else { 958 libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED); 959 } 960 break; 961 } 962 /* check for end of data */ 963 if (sxfer->rem_len == 0) { 964 libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED); 965 break; 966 } 967 /* FALLTHROUGH */ 968 969 case LIBUSB20_TRANSFER_START: 970 if (max_bulk > sxfer->rem_len) { 971 max_bulk = sxfer->rem_len; 972 } 973 /* setup new BULK or INTERRUPT transaction */ 974 libusb20_tr_setup_bulk(pxfer, 975 sxfer->curr_data, max_bulk, uxfer->timeout); 976 977 /* update counters */ 978 sxfer->last_len = max_bulk; 979 sxfer->curr_data += max_bulk; 980 sxfer->rem_len -= max_bulk; 981 982 libusb20_tr_submit(pxfer); 983 984 /* check if we can fork another USB transfer */ 985 if (sxfer->rem_len == 0) 986 libusb10_submit_transfer_sub(libusb20_tr_get_priv_sc0(pxfer), uxfer->endpoint); 987 break; 988 989 default: 990 libusb10_complete_transfer(pxfer, sxfer, libusb10_convert_error(status)); 991 break; 992 } 993} 994 995/* This function must be called locked */ 996 997static void 998libusb10_ctrl_proxy(struct libusb20_transfer *pxfer) 999{ 1000 struct libusb_super_transfer *sxfer; 1001 struct libusb_transfer *uxfer; 1002 uint32_t max_bulk; 1003 uint32_t actlen; 1004 uint8_t status; 1005 uint8_t flags; 1006 1007 status = libusb20_tr_get_status(pxfer); 1008 sxfer = libusb20_tr_get_priv_sc1(pxfer); 1009 max_bulk = libusb20_tr_get_max_total_length(pxfer); 1010 actlen = libusb20_tr_get_actual_length(pxfer); 1011 1012 if (sxfer == NULL) 1013 return; /* cancelled - nothing to do */ 1014 1015 uxfer = (struct libusb_transfer *)( 1016 ((uint8_t *)sxfer) + sizeof(*sxfer)); 1017 1018 flags = uxfer->flags; 1019 1020 switch (status) { 1021 case LIBUSB20_TRANSFER_COMPLETED: 1022 1023 uxfer->actual_length += actlen; 1024 1025 /* subtract length of SETUP packet, if any */ 1026 actlen -= libusb20_tr_get_length(pxfer, 0); 1027 1028 /* check for short packet */ 1029 if (sxfer->last_len != actlen) { 1030 if (flags & LIBUSB_TRANSFER_SHORT_NOT_OK) { 1031 libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_ERROR); 1032 } else { 1033 libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED); 1034 } 1035 break; 1036 } 1037 /* check for end of data */ 1038 if (sxfer->rem_len == 0) { 1039 libusb10_complete_transfer(pxfer, sxfer, LIBUSB_TRANSFER_COMPLETED); 1040 break; 1041 } 1042 /* FALLTHROUGH */ 1043 1044 case LIBUSB20_TRANSFER_START: 1045 if (max_bulk > sxfer->rem_len) { 1046 max_bulk = sxfer->rem_len; 1047 } 1048 /* setup new CONTROL transaction */ 1049 if (status == LIBUSB20_TRANSFER_COMPLETED) { 1050 /* next fragment - don't send SETUP packet */ 1051 libusb20_tr_set_length(pxfer, 0, 0); 1052 } else { 1053 /* first fragment - send SETUP packet */ 1054 libusb20_tr_set_length(pxfer, 8, 0); 1055 libusb20_tr_set_buffer(pxfer, uxfer->buffer, 0); 1056 } 1057 1058 if (max_bulk != 0) { 1059 libusb20_tr_set_length(pxfer, max_bulk, 1); 1060 libusb20_tr_set_buffer(pxfer, sxfer->curr_data, 1); 1061 libusb20_tr_set_total_frames(pxfer, 2); 1062 } else { 1063 libusb20_tr_set_total_frames(pxfer, 1); 1064 } 1065 1066 /* update counters */ 1067 sxfer->last_len = max_bulk; 1068 sxfer->curr_data += max_bulk; 1069 sxfer->rem_len -= max_bulk; 1070 1071 libusb20_tr_submit(pxfer); 1072 1073 /* check if we can fork another USB transfer */ 1074 if (sxfer->rem_len == 0) 1075 libusb10_submit_transfer_sub(libusb20_tr_get_priv_sc0(pxfer), uxfer->endpoint); 1076 break; 1077 1078 default: 1079 libusb10_complete_transfer(pxfer, sxfer, libusb10_convert_error(status)); 1080 break; 1081 } 1082} 1083 1084/* The following function must be called locked */ 1085 1086static void 1087libusb10_submit_transfer_sub(struct libusb20_device *pdev, uint8_t endpoint) 1088{ 1089 struct libusb20_transfer *pxfer0; 1090 struct libusb20_transfer *pxfer1; 1091 struct libusb_super_transfer *sxfer; 1092 struct libusb_transfer *uxfer; 1093 struct libusb_device *dev; 1094 int err; 1095 int buffsize; 1096 int maxframe; 1097 int temp; 1098 uint8_t dummy; 1099 1100 dev = libusb_get_device(pdev); 1101 1102 pxfer0 = libusb10_get_transfer(pdev, endpoint, 0); 1103 pxfer1 = libusb10_get_transfer(pdev, endpoint, 1); 1104 1105 if (pxfer0 == NULL || pxfer1 == NULL) 1106 return; /* shouldn't happen */ 1107 1108 temp = 0; 1109 if (libusb20_tr_pending(pxfer0)) 1110 temp |= 1; 1111 if (libusb20_tr_pending(pxfer1)) 1112 temp |= 2; 1113 1114 switch (temp) { 1115 case 3: 1116 /* wait till one of the transfers complete */ 1117 return; 1118 case 2: 1119 sxfer = libusb20_tr_get_priv_sc1(pxfer1); 1120 if (sxfer == NULL) 1121 return; /* cancelling */ 1122 if (sxfer->rem_len) 1123 return; /* cannot queue another one */ 1124 /* swap transfers */ 1125 pxfer1 = pxfer0; 1126 break; 1127 case 1: 1128 sxfer = libusb20_tr_get_priv_sc1(pxfer0); 1129 if (sxfer == NULL) 1130 return; /* cancelling */ 1131 if (sxfer->rem_len) 1132 return; /* cannot queue another one */ 1133 /* swap transfers */ 1134 pxfer0 = pxfer1; 1135 break; 1136 default: 1137 break; 1138 } 1139 1140 /* find next transfer on same endpoint */ 1141 TAILQ_FOREACH(sxfer, &dev->tr_head, entry) { 1142 1143 uxfer = (struct libusb_transfer *)( 1144 ((uint8_t *)sxfer) + sizeof(*sxfer)); 1145 1146 if (uxfer->endpoint == endpoint) { 1147 TAILQ_REMOVE(&dev->tr_head, sxfer, entry); 1148 sxfer->entry.tqe_prev = NULL; 1149 goto found; 1150 } 1151 } 1152 return; /* success */ 1153 1154found: 1155 1156 libusb20_tr_set_priv_sc0(pxfer0, pdev); 1157 libusb20_tr_set_priv_sc1(pxfer0, sxfer); 1158 1159 /* reset super transfer state */ 1160 sxfer->rem_len = uxfer->length; 1161 sxfer->curr_data = uxfer->buffer; 1162 uxfer->actual_length = 0; 1163 1164 switch (uxfer->type) { 1165 case LIBUSB_TRANSFER_TYPE_ISOCHRONOUS: 1166 libusb20_tr_set_callback(pxfer0, libusb10_isoc_proxy); 1167 break; 1168 case LIBUSB_TRANSFER_TYPE_BULK: 1169 case LIBUSB_TRANSFER_TYPE_INTERRUPT: 1170 libusb20_tr_set_callback(pxfer0, libusb10_bulk_intr_proxy); 1171 break; 1172 case LIBUSB_TRANSFER_TYPE_CONTROL: 1173 libusb20_tr_set_callback(pxfer0, libusb10_ctrl_proxy); 1174 if (sxfer->rem_len < 8) 1175 goto failure; 1176 1177 /* remove SETUP packet from data */ 1178 sxfer->rem_len -= 8; 1179 sxfer->curr_data += 8; 1180 break; 1181 default: 1182 goto failure; 1183 } 1184 1185 buffsize = libusb10_get_buffsize(pdev, uxfer); 1186 maxframe = libusb10_get_maxframe(pdev, uxfer); 1187 1188 /* make sure the transfer is opened */ 1189 err = libusb20_tr_open(pxfer0, buffsize, maxframe, endpoint); 1190 if (err && (err != LIBUSB20_ERROR_BUSY)) { 1191 goto failure; 1192 } 1193 libusb20_tr_start(pxfer0); 1194 return; 1195 1196failure: 1197 libusb10_complete_transfer(pxfer0, sxfer, LIBUSB_TRANSFER_ERROR); 1198 1199 /* make sure our event loop spins the done handler */ 1200 dummy = 0; 1201 write(dev->ctx->ctrl_pipe[1], &dummy, sizeof(dummy)); 1202} 1203 1204/* The following function must be called unlocked */ 1205 1206int 1207libusb_submit_transfer(struct libusb_transfer *uxfer) 1208{ 1209 struct libusb20_transfer *pxfer0; 1210 struct libusb20_transfer *pxfer1; 1211 struct libusb_super_transfer *sxfer; 1212 struct libusb_device *dev; 1213 uint32_t endpoint; 1214 int err; 1215 1216 if (uxfer == NULL) 1217 return (LIBUSB_ERROR_INVALID_PARAM); 1218 1219 if (uxfer->dev_handle == NULL) 1220 return (LIBUSB_ERROR_INVALID_PARAM); 1221 1222 endpoint = uxfer->endpoint; 1223 1224 if (endpoint > 255) 1225 return (LIBUSB_ERROR_INVALID_PARAM); 1226 1227 dev = libusb_get_device(uxfer->dev_handle); 1228 1229 DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_submit_transfer enter"); 1230 1231 sxfer = (struct libusb_super_transfer *)( 1232 (uint8_t *)uxfer - sizeof(*sxfer)); 1233 1234 CTX_LOCK(dev->ctx); 1235 1236 pxfer0 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 0); 1237 pxfer1 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 1); 1238 1239 if (pxfer0 == NULL || pxfer1 == NULL) { 1240 err = LIBUSB_ERROR_OTHER; 1241 } else if ((sxfer->entry.tqe_prev != NULL) || 1242 (libusb20_tr_get_priv_sc1(pxfer0) == sxfer) || 1243 (libusb20_tr_get_priv_sc1(pxfer1) == sxfer)) { 1244 err = LIBUSB_ERROR_BUSY; 1245 } else { 1246 1247 /* set pending state */ 1248 sxfer->state = LIBUSB_SUPER_XFER_ST_PEND; 1249 1250 /* insert transfer into transfer head list */ 1251 TAILQ_INSERT_TAIL(&dev->tr_head, sxfer, entry); 1252 1253 /* start work transfers */ 1254 libusb10_submit_transfer_sub( 1255 uxfer->dev_handle, endpoint); 1256 1257 err = 0; /* success */ 1258 } 1259 1260 CTX_UNLOCK(dev->ctx); 1261 1262 DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_submit_transfer leave %d", err); 1263 1264 return (err); 1265} 1266 1267/* Asynchronous transfer cancel */ 1268 1269int 1270libusb_cancel_transfer(struct libusb_transfer *uxfer) 1271{ 1272 struct libusb20_transfer *pxfer0; 1273 struct libusb20_transfer *pxfer1; 1274 struct libusb_super_transfer *sxfer; 1275 struct libusb_device *dev; 1276 uint32_t endpoint; 1277 int retval; 1278 1279 if (uxfer == NULL) 1280 return (LIBUSB_ERROR_INVALID_PARAM); 1281 1282 /* check if not initialised */ 1283 if (uxfer->dev_handle == NULL) 1284 return (LIBUSB_ERROR_NOT_FOUND); 1285 1286 endpoint = uxfer->endpoint; 1287 1288 if (endpoint > 255) 1289 return (LIBUSB_ERROR_INVALID_PARAM); 1290 1291 dev = libusb_get_device(uxfer->dev_handle); 1292 1293 DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_cancel_transfer enter"); 1294 1295 sxfer = (struct libusb_super_transfer *)( 1296 (uint8_t *)uxfer - sizeof(*sxfer)); 1297 1298 retval = 0; 1299 1300 CTX_LOCK(dev->ctx); 1301 1302 pxfer0 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 0); 1303 pxfer1 = libusb10_get_transfer(uxfer->dev_handle, endpoint, 1); 1304 1305 if (sxfer->state != LIBUSB_SUPER_XFER_ST_PEND) { 1306 /* only update the transfer status */ 1307 uxfer->status = LIBUSB_TRANSFER_CANCELLED; 1308 retval = LIBUSB_ERROR_NOT_FOUND; 1309 } else if (sxfer->entry.tqe_prev != NULL) { 1310 /* we are lucky - transfer is on a queue */ 1311 TAILQ_REMOVE(&dev->tr_head, sxfer, entry); 1312 sxfer->entry.tqe_prev = NULL; 1313 libusb10_complete_transfer(NULL, 1314 sxfer, LIBUSB_TRANSFER_CANCELLED); 1315 } else if (pxfer0 == NULL || pxfer1 == NULL) { 1316 /* not started */ 1317 retval = LIBUSB_ERROR_NOT_FOUND; 1318 } else if (libusb20_tr_get_priv_sc1(pxfer0) == sxfer) { 1319 libusb10_complete_transfer(pxfer0, 1320 sxfer, LIBUSB_TRANSFER_CANCELLED); 1321 libusb20_tr_stop(pxfer0); 1322 /* make sure the queue doesn't stall */ 1323 libusb10_submit_transfer_sub( 1324 uxfer->dev_handle, endpoint); 1325 } else if (libusb20_tr_get_priv_sc1(pxfer1) == sxfer) { 1326 libusb10_complete_transfer(pxfer1, 1327 sxfer, LIBUSB_TRANSFER_CANCELLED); 1328 libusb20_tr_stop(pxfer1); 1329 /* make sure the queue doesn't stall */ 1330 libusb10_submit_transfer_sub( 1331 uxfer->dev_handle, endpoint); 1332 } else { 1333 /* not started */ 1334 retval = LIBUSB_ERROR_NOT_FOUND; 1335 } 1336 1337 CTX_UNLOCK(dev->ctx); 1338 1339 DPRINTF(dev->ctx, LIBUSB_DEBUG_FUNCTION, "libusb_cancel_transfer leave"); 1340 1341 return (retval); 1342} 1343 1344UNEXPORTED void 1345libusb10_cancel_all_transfer(libusb_device *dev) 1346{ 1347 /* TODO */ 1348} 1349 1350uint16_t 1351libusb_cpu_to_le16(uint16_t x) 1352{ 1353 return (htole16(x)); 1354} 1355 1356uint16_t 1357libusb_le16_to_cpu(uint16_t x) 1358{ 1359 return (le16toh(x)); 1360} 1361 1362