1 /* 2 * Copyright (C) 2008 The Android Open Source Project 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * * Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * * Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in 12 * the documentation and/or other materials provided with the 13 * distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 16 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 17 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 18 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 19 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 21 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 22 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 23 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 24 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 25 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 29 #include <stdio.h> 30 #include <stdlib.h> 31 #include <unistd.h> 32 #include <string.h> 33 34 #include <sys/ioctl.h> 35 #include <sys/stat.h> 36 #include <sys/types.h> 37 #include <dirent.h> 38 #include <fcntl.h> 39 #include <errno.h> 40 #include <pthread.h> 41 #include <ctype.h> 42 43 #include <linux/usbdevice_fs.h> 44 #include <linux/usbdevice_fs.h> 45 #include <linux/version.h> 46 #if LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 20) 47 #include <linux/usb/ch9.h> 48 #else 49 #include <linux/usb_ch9.h> 50 #endif 51 #include <asm/byteorder.h> 52 53 #include "fastboot.h" 54 #include "usb.h" 55 56 #define MAX_RETRIES 5 57 58 /* Timeout in seconds for usb_wait_for_disconnect. 59 * It doesn't usually take long for a device to disconnect (almost always 60 * under 2 seconds) but we'll time out after 3 seconds just in case. 61 */ 62 #define WAIT_FOR_DISCONNECT_TIMEOUT 3 63 64 #ifdef TRACE_USB 65 #define DBG1(x...) fprintf(stderr, x) 66 #define DBG(x...) fprintf(stderr, x) 67 #else 68 #define DBG(x...) 69 #define DBG1(x...) 70 #endif 71 72 /* The max bulk size for linux is 16384 which is defined 73 * in drivers/usb/core/devio.c. 74 */ 75 #define MAX_USBFS_BULK_SIZE (16 * 1024) 76 77 struct usb_handle 78 { 79 char fname[64]; 80 int desc; 81 unsigned char ep_in; 82 unsigned char ep_out; 83 }; 84 85 /* True if name isn't a valid name for a USB device in /sys/bus/usb/devices. 86 * Device names are made up of numbers, dots, and dashes, e.g., '7-1.5'. 87 * We reject interfaces (e.g., '7-1.5:1.0') and host controllers (e.g. 'usb1'). 88 * The name must also start with a digit, to disallow '.' and '..' 89 */ 90 static inline int badname(const char *name) 91 { 92 if (!isdigit(*name)) 93 return 1; 94 while(*++name) { 95 if(!isdigit(*name) && *name != '.' && *name != '-') 96 return 1; 97 } 98 return 0; 99 } 100 101 static int check(void *_desc, int len, unsigned type, int size) 102 { 103 struct usb_descriptor_header *hdr = (struct usb_descriptor_header *)_desc; 104 105 if(len < size) return -1; 106 if(hdr->bLength < size) return -1; 107 if(hdr->bLength > len) return -1; 108 if(hdr->bDescriptorType != type) return -1; 109 110 return 0; 111 } 112 113 static int filter_usb_device(char* sysfs_name, 114 char *ptr, int len, int writable, 115 ifc_match_func callback, 116 int *ept_in_id, int *ept_out_id, int *ifc_id) 117 { 118 struct usb_device_descriptor *dev; 119 struct usb_config_descriptor *cfg; 120 struct usb_interface_descriptor *ifc; 121 struct usb_endpoint_descriptor *ept; 122 struct usb_ifc_info info; 123 124 int in, out; 125 unsigned i; 126 unsigned e; 127 128 if (check(ptr, len, USB_DT_DEVICE, USB_DT_DEVICE_SIZE)) 129 return -1; 130 dev = (struct usb_device_descriptor *)ptr; 131 len -= dev->bLength; 132 ptr += dev->bLength; 133 134 if (check(ptr, len, USB_DT_CONFIG, USB_DT_CONFIG_SIZE)) 135 return -1; 136 cfg = (struct usb_config_descriptor *)ptr; 137 len -= cfg->bLength; 138 ptr += cfg->bLength; 139 140 info.dev_vendor = dev->idVendor; 141 info.dev_product = dev->idProduct; 142 info.dev_class = dev->bDeviceClass; 143 info.dev_subclass = dev->bDeviceSubClass; 144 info.dev_protocol = dev->bDeviceProtocol; 145 info.writable = writable; 146 147 snprintf(info.device_path, sizeof(info.device_path), "usb:%s", sysfs_name); 148 149 /* Read device serial number (if there is one). 150 * We read the serial number from sysfs, since it's faster and more 151 * reliable than issuing a control pipe read, and also won't 152 * cause problems for devices which don't like getting descriptor 153 * requests while they're in the middle of flashing. 154 */ 155 info.serial_number[0] = '\0'; 156 if (dev->iSerialNumber) { 157 char path[80]; 158 int fd; 159 160 snprintf(path, sizeof(path), 161 "/sys/bus/usb/devices/%s/serial", sysfs_name); 162 path[sizeof(path) - 1] = '\0'; 163 164 fd = open(path, O_RDONLY); 165 if (fd >= 0) { 166 int chars_read = read(fd, info.serial_number, 167 sizeof(info.serial_number) - 1); 168 close(fd); 169 170 if (chars_read <= 0) 171 info.serial_number[0] = '\0'; 172 else if (info.serial_number[chars_read - 1] == '\n') { 173 // strip trailing newline 174 info.serial_number[chars_read - 1] = '\0'; 175 } 176 } 177 } 178 179 for(i = 0; i < cfg->bNumInterfaces; i++) { 180 181 while (len > 0) { 182 struct usb_descriptor_header *hdr = (struct usb_descriptor_header *)ptr; 183 if (check(hdr, len, USB_DT_INTERFACE, USB_DT_INTERFACE_SIZE) == 0) 184 break; 185 len -= hdr->bLength; 186 ptr += hdr->bLength; 187 } 188 189 if (len <= 0) 190 return -1; 191 192 ifc = (struct usb_interface_descriptor *)ptr; 193 len -= ifc->bLength; 194 ptr += ifc->bLength; 195 196 in = -1; 197 out = -1; 198 info.ifc_class = ifc->bInterfaceClass; 199 info.ifc_subclass = ifc->bInterfaceSubClass; 200 info.ifc_protocol = ifc->bInterfaceProtocol; 201 202 for(e = 0; e < ifc->bNumEndpoints; e++) { 203 while (len > 0) { 204 struct usb_descriptor_header *hdr = (struct usb_descriptor_header *)ptr; 205 if (check(hdr, len, USB_DT_ENDPOINT, USB_DT_ENDPOINT_SIZE) == 0) 206 break; 207 len -= hdr->bLength; 208 ptr += hdr->bLength; 209 } 210 if (len < 0) { 211 break; 212 } 213 214 ept = (struct usb_endpoint_descriptor *)ptr; 215 len -= ept->bLength; 216 ptr += ept->bLength; 217 218 if((ept->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK) != USB_ENDPOINT_XFER_BULK) 219 continue; 220 221 if(ept->bEndpointAddress & USB_ENDPOINT_DIR_MASK) { 222 in = ept->bEndpointAddress; 223 } else { 224 out = ept->bEndpointAddress; 225 } 226 } 227 228 info.has_bulk_in = (in != -1); 229 info.has_bulk_out = (out != -1); 230 231 if(callback(&info) == 0) { 232 *ept_in_id = in; 233 *ept_out_id = out; 234 *ifc_id = ifc->bInterfaceNumber; 235 return 0; 236 } 237 } 238 239 return -1; 240 } 241 242 static int read_sysfs_string(const char *sysfs_name, const char *sysfs_node, 243 char* buf, int bufsize) 244 { 245 char path[80]; 246 int fd, n; 247 248 snprintf(path, sizeof(path), 249 "/sys/bus/usb/devices/%s/%s", sysfs_name, sysfs_node); 250 path[sizeof(path) - 1] = '\0'; 251 252 fd = open(path, O_RDONLY); 253 if (fd < 0) 254 return -1; 255 256 n = read(fd, buf, bufsize - 1); 257 close(fd); 258 259 if (n < 0) 260 return -1; 261 262 buf[n] = '\0'; 263 264 return n; 265 } 266 267 static int read_sysfs_number(const char *sysfs_name, const char *sysfs_node) 268 { 269 char buf[16]; 270 int value; 271 272 if (read_sysfs_string(sysfs_name, sysfs_node, buf, sizeof(buf)) < 0) 273 return -1; 274 275 if (sscanf(buf, "%d", &value) != 1) 276 return -1; 277 278 return value; 279 } 280 281 /* Given the name of a USB device in sysfs, get the name for the same 282 * device in devfs. Returns 0 for success, -1 for failure. 283 */ 284 static int convert_to_devfs_name(const char* sysfs_name, 285 char* devname, int devname_size) 286 { 287 int busnum, devnum; 288 289 busnum = read_sysfs_number(sysfs_name, "busnum"); 290 if (busnum < 0) 291 return -1; 292 293 devnum = read_sysfs_number(sysfs_name, "devnum"); 294 if (devnum < 0) 295 return -1; 296 297 snprintf(devname, devname_size, "/dev/bus/usb/%03d/%03d", busnum, devnum); 298 return 0; 299 } 300 301 static usb_handle *find_usb_device(const char *base, ifc_match_func callback) 302 { 303 usb_handle *usb = 0; 304 char devname[64]; 305 char desc[1024]; 306 int n, in, out, ifc; 307 308 DIR *busdir; 309 struct dirent *de; 310 int fd; 311 int writable; 312 313 busdir = opendir(base); 314 if(busdir == 0) return 0; 315 316 while((de = readdir(busdir)) && (usb == 0)) { 317 if(badname(de->d_name)) continue; 318 319 if(!convert_to_devfs_name(de->d_name, devname, sizeof(devname))) { 320 321 // DBG("[ scanning %s ]\n", devname); 322 writable = 1; 323 if((fd = open(devname, O_RDWR)) < 0) { 324 // Check if we have read-only access, so we can give a helpful 325 // diagnostic like "adb devices" does. 326 writable = 0; 327 if((fd = open(devname, O_RDONLY)) < 0) { 328 continue; 329 } 330 } 331 332 n = read(fd, desc, sizeof(desc)); 333 334 if(filter_usb_device(de->d_name, desc, n, writable, callback, 335 &in, &out, &ifc) == 0) { 336 usb = calloc(1, sizeof(usb_handle)); 337 strcpy(usb->fname, devname); 338 usb->ep_in = in; 339 usb->ep_out = out; 340 usb->desc = fd; 341 342 n = ioctl(fd, USBDEVFS_CLAIMINTERFACE, &ifc); 343 if(n != 0) { 344 close(fd); 345 free(usb); 346 usb = 0; 347 continue; 348 } 349 } else { 350 close(fd); 351 } 352 } 353 } 354 closedir(busdir); 355 356 return usb; 357 } 358 359 int usb_write(usb_handle *h, const void *_data, int len) 360 { 361 unsigned char *data = (unsigned char*) _data; 362 unsigned count = 0; 363 struct usbdevfs_bulktransfer bulk; 364 int n; 365 366 if(h->ep_out == 0 || h->desc == -1) { 367 return -1; 368 } 369 370 do { 371 int xfer; 372 xfer = (len > MAX_USBFS_BULK_SIZE) ? MAX_USBFS_BULK_SIZE : len; 373 374 bulk.ep = h->ep_out; 375 bulk.len = xfer; 376 bulk.data = data; 377 bulk.timeout = 0; 378 379 n = ioctl(h->desc, USBDEVFS_BULK, &bulk); 380 if(n != xfer) { 381 DBG("ERROR: n = %d, errno = %d (%s)\n", 382 n, errno, strerror(errno)); 383 return -1; 384 } 385 386 count += xfer; 387 len -= xfer; 388 data += xfer; 389 } while(len > 0); 390 391 return count; 392 } 393 394 int usb_read(usb_handle *h, void *_data, int len) 395 { 396 unsigned char *data = (unsigned char*) _data; 397 unsigned count = 0; 398 struct usbdevfs_bulktransfer bulk; 399 int n, retry; 400 401 if(h->ep_in == 0 || h->desc == -1) { 402 return -1; 403 } 404 405 while(len > 0) { 406 int xfer = (len > MAX_USBFS_BULK_SIZE) ? MAX_USBFS_BULK_SIZE : len; 407 408 bulk.ep = h->ep_in; 409 bulk.len = xfer; 410 bulk.data = data; 411 bulk.timeout = 0; 412 retry = 0; 413 414 do{ 415 DBG("[ usb read %d fd = %d], fname=%s\n", xfer, h->desc, h->fname); 416 n = ioctl(h->desc, USBDEVFS_BULK, &bulk); 417 DBG("[ usb read %d ] = %d, fname=%s, Retry %d \n", xfer, n, h->fname, retry); 418 419 if( n < 0 ) { 420 DBG1("ERROR: n = %d, errno = %d (%s)\n",n, errno, strerror(errno)); 421 if ( ++retry > MAX_RETRIES ) return -1; 422 sleep( 1 ); 423 } 424 } 425 while( n < 0 ); 426 427 count += n; 428 len -= n; 429 data += n; 430 431 if(n < xfer) { 432 break; 433 } 434 } 435 436 return count; 437 } 438 439 void usb_kick(usb_handle *h) 440 { 441 int fd; 442 443 fd = h->desc; 444 h->desc = -1; 445 if(fd >= 0) { 446 close(fd); 447 DBG("[ usb closed %d ]\n", fd); 448 } 449 } 450 451 int usb_close(usb_handle *h) 452 { 453 int fd; 454 455 fd = h->desc; 456 h->desc = -1; 457 if(fd >= 0) { 458 close(fd); 459 DBG("[ usb closed %d ]\n", fd); 460 } 461 462 return 0; 463 } 464 465 usb_handle *usb_open(ifc_match_func callback) 466 { 467 return find_usb_device("/sys/bus/usb/devices", callback); 468 } 469 470 /* Wait for the system to notice the device is gone, so that a subsequent 471 * fastboot command won't try to access the device before it's rebooted. 472 * Returns 0 for success, -1 for timeout. 473 */ 474 int usb_wait_for_disconnect(usb_handle *usb) 475 { 476 double deadline = now() + WAIT_FOR_DISCONNECT_TIMEOUT; 477 while (now() < deadline) { 478 if (access(usb->fname, F_OK)) 479 return 0; 480 usleep(50000); 481 } 482 return -1; 483 } 484