1 /* 2 * (C) Copyright 2008 - 2009 3 * Windriver, <www.windriver.com> 4 * Tom Rix <Tom.Rix@windriver.com> 5 * 6 * Copyright 2011 Sebastian Andrzej Siewior <bigeasy@linutronix.de> 7 * 8 * Copyright 2014 Linaro, Ltd. 9 * Rob Herring <robh@kernel.org> 10 * 11 * SPDX-License-Identifier: GPL-2.0+ 12 */ 13 #include <config.h> 14 #include <common.h> 15 #include <errno.h> 16 #include <fastboot.h> 17 #include <malloc.h> 18 #include <linux/usb/ch9.h> 19 #include <linux/usb/gadget.h> 20 #include <linux/usb/composite.h> 21 #include <linux/compiler.h> 22 #include <version.h> 23 #include <g_dnl.h> 24 #include <android_avb/avb_ops_user.h> 25 #ifdef CONFIG_FASTBOOT_FLASH_MMC_DEV 26 #include <fb_mmc.h> 27 #endif 28 #ifdef CONFIG_FASTBOOT_FLASH_NAND_DEV 29 #include <fb_nand.h> 30 #endif 31 32 #define FASTBOOT_VERSION "0.4" 33 34 #define FASTBOOT_INTERFACE_CLASS 0xff 35 #define FASTBOOT_INTERFACE_SUB_CLASS 0x42 36 #define FASTBOOT_INTERFACE_PROTOCOL 0x03 37 38 #define RX_ENDPOINT_MAXIMUM_PACKET_SIZE_2_0 (0x0200) 39 #define RX_ENDPOINT_MAXIMUM_PACKET_SIZE_1_1 (0x0040) 40 #define TX_ENDPOINT_MAXIMUM_PACKET_SIZE (0x0040) 41 42 #define EP_BUFFER_SIZE 4096 43 /* 44 * EP_BUFFER_SIZE must always be an integral multiple of maxpacket size 45 * (64 or 512 or 1024), else we break on certain controllers like DWC3 46 * that expect bulk OUT requests to be divisible by maxpacket size. 47 */ 48 49 struct f_fastboot { 50 struct usb_function usb_function; 51 52 /* IN/OUT EP's and corresponding requests */ 53 struct usb_ep *in_ep, *out_ep; 54 struct usb_request *in_req, *out_req; 55 }; 56 57 static inline struct f_fastboot *func_to_fastboot(struct usb_function *f) 58 { 59 return container_of(f, struct f_fastboot, usb_function); 60 } 61 62 static struct f_fastboot *fastboot_func; 63 static unsigned int download_size; 64 static unsigned int download_bytes; 65 static unsigned int upload_size; 66 static unsigned int upload_bytes; 67 static bool start_upload; 68 69 static struct usb_endpoint_descriptor fs_ep_in = { 70 .bLength = USB_DT_ENDPOINT_SIZE, 71 .bDescriptorType = USB_DT_ENDPOINT, 72 .bEndpointAddress = USB_DIR_IN, 73 .bmAttributes = USB_ENDPOINT_XFER_BULK, 74 .wMaxPacketSize = cpu_to_le16(64), 75 }; 76 77 static struct usb_endpoint_descriptor fs_ep_out = { 78 .bLength = USB_DT_ENDPOINT_SIZE, 79 .bDescriptorType = USB_DT_ENDPOINT, 80 .bEndpointAddress = USB_DIR_OUT, 81 .bmAttributes = USB_ENDPOINT_XFER_BULK, 82 .wMaxPacketSize = cpu_to_le16(64), 83 }; 84 85 static struct usb_endpoint_descriptor hs_ep_in = { 86 .bLength = USB_DT_ENDPOINT_SIZE, 87 .bDescriptorType = USB_DT_ENDPOINT, 88 .bEndpointAddress = USB_DIR_IN, 89 .bmAttributes = USB_ENDPOINT_XFER_BULK, 90 .wMaxPacketSize = cpu_to_le16(512), 91 }; 92 93 static struct usb_endpoint_descriptor hs_ep_out = { 94 .bLength = USB_DT_ENDPOINT_SIZE, 95 .bDescriptorType = USB_DT_ENDPOINT, 96 .bEndpointAddress = USB_DIR_OUT, 97 .bmAttributes = USB_ENDPOINT_XFER_BULK, 98 .wMaxPacketSize = cpu_to_le16(512), 99 }; 100 101 static struct usb_interface_descriptor interface_desc = { 102 .bLength = USB_DT_INTERFACE_SIZE, 103 .bDescriptorType = USB_DT_INTERFACE, 104 .bInterfaceNumber = 0x00, 105 .bAlternateSetting = 0x00, 106 .bNumEndpoints = 0x02, 107 .bInterfaceClass = FASTBOOT_INTERFACE_CLASS, 108 .bInterfaceSubClass = FASTBOOT_INTERFACE_SUB_CLASS, 109 .bInterfaceProtocol = FASTBOOT_INTERFACE_PROTOCOL, 110 }; 111 112 static struct usb_descriptor_header *fb_fs_function[] = { 113 (struct usb_descriptor_header *)&interface_desc, 114 (struct usb_descriptor_header *)&fs_ep_in, 115 (struct usb_descriptor_header *)&fs_ep_out, 116 }; 117 118 static struct usb_descriptor_header *fb_hs_function[] = { 119 (struct usb_descriptor_header *)&interface_desc, 120 (struct usb_descriptor_header *)&hs_ep_in, 121 (struct usb_descriptor_header *)&hs_ep_out, 122 NULL, 123 }; 124 125 static struct usb_endpoint_descriptor * 126 fb_ep_desc(struct usb_gadget *g, struct usb_endpoint_descriptor *fs, 127 struct usb_endpoint_descriptor *hs) 128 { 129 if (gadget_is_dualspeed(g) && g->speed == USB_SPEED_HIGH) 130 return hs; 131 return fs; 132 } 133 134 /* 135 * static strings, in UTF-8 136 */ 137 static const char fastboot_name[] = "Android Fastboot"; 138 139 static struct usb_string fastboot_string_defs[] = { 140 [0].s = fastboot_name, 141 { } /* end of list */ 142 }; 143 144 static struct usb_gadget_strings stringtab_fastboot = { 145 .language = 0x0409, /* en-us */ 146 .strings = fastboot_string_defs, 147 }; 148 149 static struct usb_gadget_strings *fastboot_strings[] = { 150 &stringtab_fastboot, 151 NULL, 152 }; 153 154 static void rx_handler_command(struct usb_ep *ep, struct usb_request *req); 155 static int strcmp_l1(const char *s1, const char *s2); 156 157 static void fastboot_complete(struct usb_ep *ep, struct usb_request *req) 158 { 159 int status = req->status; 160 if (!status) 161 return; 162 printf("status: %d ep '%s' trans: %d\n", status, ep->name, req->actual); 163 } 164 165 static int fastboot_bind(struct usb_configuration *c, struct usb_function *f) 166 { 167 int id; 168 struct usb_gadget *gadget = c->cdev->gadget; 169 struct f_fastboot *f_fb = func_to_fastboot(f); 170 const char *s; 171 172 /* DYNAMIC interface numbers assignments */ 173 id = usb_interface_id(c, f); 174 if (id < 0) 175 return id; 176 interface_desc.bInterfaceNumber = id; 177 178 id = usb_string_id(c->cdev); 179 if (id < 0) 180 return id; 181 fastboot_string_defs[0].id = id; 182 interface_desc.iInterface = id; 183 184 f_fb->in_ep = usb_ep_autoconfig(gadget, &fs_ep_in); 185 if (!f_fb->in_ep) 186 return -ENODEV; 187 f_fb->in_ep->driver_data = c->cdev; 188 189 f_fb->out_ep = usb_ep_autoconfig(gadget, &fs_ep_out); 190 if (!f_fb->out_ep) 191 return -ENODEV; 192 f_fb->out_ep->driver_data = c->cdev; 193 194 f->descriptors = fb_fs_function; 195 196 if (gadget_is_dualspeed(gadget)) { 197 /* Assume endpoint addresses are the same for both speeds */ 198 hs_ep_in.bEndpointAddress = fs_ep_in.bEndpointAddress; 199 hs_ep_out.bEndpointAddress = fs_ep_out.bEndpointAddress; 200 /* copy HS descriptors */ 201 f->hs_descriptors = fb_hs_function; 202 } 203 204 s = env_get("serial#"); 205 if (s) 206 g_dnl_set_serialnumber((char *)s); 207 208 return 0; 209 } 210 211 static void fastboot_unbind(struct usb_configuration *c, struct usb_function *f) 212 { 213 memset(fastboot_func, 0, sizeof(*fastboot_func)); 214 } 215 216 static void fastboot_disable(struct usb_function *f) 217 { 218 struct f_fastboot *f_fb = func_to_fastboot(f); 219 220 usb_ep_disable(f_fb->out_ep); 221 usb_ep_disable(f_fb->in_ep); 222 223 if (f_fb->out_req) { 224 free(f_fb->out_req->buf); 225 usb_ep_free_request(f_fb->out_ep, f_fb->out_req); 226 f_fb->out_req = NULL; 227 } 228 if (f_fb->in_req) { 229 free(f_fb->in_req->buf); 230 usb_ep_free_request(f_fb->in_ep, f_fb->in_req); 231 f_fb->in_req = NULL; 232 } 233 } 234 235 static struct usb_request *fastboot_start_ep(struct usb_ep *ep) 236 { 237 struct usb_request *req; 238 239 req = usb_ep_alloc_request(ep, 0); 240 if (!req) 241 return NULL; 242 243 req->length = EP_BUFFER_SIZE; 244 req->buf = memalign(CONFIG_SYS_CACHELINE_SIZE, EP_BUFFER_SIZE); 245 if (!req->buf) { 246 usb_ep_free_request(ep, req); 247 return NULL; 248 } 249 250 memset(req->buf, 0, req->length); 251 return req; 252 } 253 254 static int fastboot_set_alt(struct usb_function *f, 255 unsigned interface, unsigned alt) 256 { 257 int ret; 258 struct usb_composite_dev *cdev = f->config->cdev; 259 struct usb_gadget *gadget = cdev->gadget; 260 struct f_fastboot *f_fb = func_to_fastboot(f); 261 const struct usb_endpoint_descriptor *d; 262 263 debug("%s: func: %s intf: %d alt: %d\n", 264 __func__, f->name, interface, alt); 265 266 d = fb_ep_desc(gadget, &fs_ep_out, &hs_ep_out); 267 ret = usb_ep_enable(f_fb->out_ep, d); 268 if (ret) { 269 puts("failed to enable out ep\n"); 270 return ret; 271 } 272 273 f_fb->out_req = fastboot_start_ep(f_fb->out_ep); 274 if (!f_fb->out_req) { 275 puts("failed to alloc out req\n"); 276 ret = -EINVAL; 277 goto err; 278 } 279 f_fb->out_req->complete = rx_handler_command; 280 281 d = fb_ep_desc(gadget, &fs_ep_in, &hs_ep_in); 282 ret = usb_ep_enable(f_fb->in_ep, d); 283 if (ret) { 284 puts("failed to enable in ep\n"); 285 goto err; 286 } 287 288 f_fb->in_req = fastboot_start_ep(f_fb->in_ep); 289 if (!f_fb->in_req) { 290 puts("failed alloc req in\n"); 291 ret = -EINVAL; 292 goto err; 293 } 294 f_fb->in_req->complete = fastboot_complete; 295 296 ret = usb_ep_queue(f_fb->out_ep, f_fb->out_req, 0); 297 if (ret) 298 goto err; 299 300 return 0; 301 err: 302 fastboot_disable(f); 303 return ret; 304 } 305 306 static int fastboot_add(struct usb_configuration *c) 307 { 308 struct f_fastboot *f_fb = fastboot_func; 309 int status; 310 311 debug("%s: cdev: 0x%p\n", __func__, c->cdev); 312 313 if (!f_fb) { 314 f_fb = memalign(CONFIG_SYS_CACHELINE_SIZE, sizeof(*f_fb)); 315 if (!f_fb) 316 return -ENOMEM; 317 318 fastboot_func = f_fb; 319 memset(f_fb, 0, sizeof(*f_fb)); 320 } 321 322 f_fb->usb_function.name = "f_fastboot"; 323 f_fb->usb_function.bind = fastboot_bind; 324 f_fb->usb_function.unbind = fastboot_unbind; 325 f_fb->usb_function.set_alt = fastboot_set_alt; 326 f_fb->usb_function.disable = fastboot_disable; 327 f_fb->usb_function.strings = fastboot_strings; 328 329 status = usb_add_function(c, &f_fb->usb_function); 330 if (status) { 331 free(f_fb); 332 fastboot_func = f_fb; 333 } 334 335 return status; 336 } 337 DECLARE_GADGET_BIND_CALLBACK(usb_dnl_fastboot, fastboot_add); 338 339 static int fastboot_tx_write(const char *buffer, unsigned int buffer_size) 340 { 341 struct usb_request *in_req = fastboot_func->in_req; 342 int ret; 343 344 memcpy(in_req->buf, buffer, buffer_size); 345 in_req->length = buffer_size; 346 347 usb_ep_dequeue(fastboot_func->in_ep, in_req); 348 349 ret = usb_ep_queue(fastboot_func->in_ep, in_req, 0); 350 if (ret) 351 printf("Error %d on queue\n", ret); 352 return 0; 353 } 354 355 static int fastboot_tx_write_str(const char *buffer) 356 { 357 return fastboot_tx_write(buffer, strlen(buffer)); 358 } 359 360 static void compl_do_reset(struct usb_ep *ep, struct usb_request *req) 361 { 362 do_reset(NULL, 0, 0, NULL); 363 } 364 365 int __weak fb_set_reboot_flag(void) 366 { 367 return -ENOSYS; 368 } 369 370 static void cb_reboot(struct usb_ep *ep, struct usb_request *req) 371 { 372 char *cmd = req->buf; 373 if (!strcmp_l1("reboot-bootloader", cmd)) { 374 if (fb_set_reboot_flag()) { 375 fastboot_tx_write_str("FAILCannot set reboot flag"); 376 return; 377 } 378 } 379 fastboot_func->in_req->complete = compl_do_reset; 380 fastboot_tx_write_str("OKAY"); 381 } 382 383 static int strcmp_l1(const char *s1, const char *s2) 384 { 385 if (!s1 || !s2) 386 return -1; 387 return strncmp(s1, s2, strlen(s1)); 388 } 389 390 static void cb_getvar(struct usb_ep *ep, struct usb_request *req) 391 { 392 char *cmd = req->buf; 393 char response[FASTBOOT_RESPONSE_LEN]; 394 const char *s; 395 size_t chars_left; 396 397 strcpy(response, "OKAY"); 398 chars_left = sizeof(response) - strlen(response) - 1; 399 400 strsep(&cmd, ":"); 401 if (!cmd) { 402 error("missing variable"); 403 fastboot_tx_write_str("FAILmissing var"); 404 return; 405 } 406 407 if (!strcmp_l1("version", cmd)) { 408 strncat(response, FASTBOOT_VERSION, chars_left); 409 } else if (!strcmp_l1("bootloader-version", cmd)) { 410 strncat(response, U_BOOT_VERSION, chars_left); 411 } else if (!strcmp_l1("downloadsize", cmd) || 412 !strcmp_l1("max-download-size", cmd)) { 413 char str_num[12]; 414 415 sprintf(str_num, "0x%08x", CONFIG_FASTBOOT_BUF_SIZE); 416 strncat(response, str_num, chars_left); 417 } else if (!strcmp_l1("serialno", cmd)) { 418 s = env_get("serial#"); 419 if (s) 420 strncat(response, s, chars_left); 421 else 422 strcpy(response, "FAILValue not set"); 423 } else if (strncmp("at-attest-dh", cmd, 12) == 0) { 424 char dh[32] = {0}; 425 426 strncat(response, dh, chars_left); 427 } else if (strncmp("at-attest-uuid", cmd, 14) == 0) { 428 char uuid[32] = {0}; 429 430 strncat(response, uuid, chars_left); 431 } else if (strncmp("at-vboot-state", cmd, 14) == 0) { 432 char uuid[32] = {0}; 433 434 strncat(response, uuid, chars_left); 435 } else if (!strcmp_l1("slot-count", cmd)) { 436 #ifdef CONFIG_AVB_LIBAVB_USER 437 char slot_count[2]; 438 char temp; 439 440 slot_count[1] = '\0'; 441 read_slot_count(&temp); 442 slot_count[0] = temp + 0x30; 443 strncat(response, slot_count, chars_left); 444 #else 445 fastboot_tx_write_str("FAILnot implemented"); 446 return; 447 #endif 448 } else if (!strcmp_l1("current-slot", cmd)) { 449 #ifdef CONFIG_AVB_LIBAVB_USER 450 char slot_surrent[8] = {0}; 451 452 if (!get_current_slot(slot_surrent)) 453 strncat(response, slot_surrent, chars_left); 454 else 455 strcpy(response, "FAILgeterror"); 456 #else 457 fastboot_tx_write_str("FAILnot implemented"); 458 return; 459 #endif 460 } else if (!strcmp_l1("slot-suffixes", cmd)) { 461 #ifdef CONFIG_AVB_LIBAVB_USER 462 char slot_suffixes_temp[4]; 463 char slot_suffixes[9]; 464 int slot_cnt = 0; 465 466 memset(slot_suffixes_temp, 0, 4); 467 memset(slot_suffixes, 0, 9); 468 read_slot_suffixes(slot_suffixes_temp); 469 while (slot_suffixes_temp[slot_cnt] != '\0') { 470 slot_suffixes[slot_cnt * 2] 471 = slot_suffixes_temp[slot_cnt]; 472 slot_suffixes[slot_cnt * 2 + 1] = ','; 473 slot_cnt++; 474 } 475 strncat(response, slot_suffixes, chars_left); 476 #else 477 fastboot_tx_write_str("FAILnot implemented"); 478 return; 479 #endif 480 } else if (!strncmp("has-slot", cmd, 8)) { 481 #ifdef CONFIG_AVB_LIBAVB_USER 482 char *part_name = cmd; 483 484 cmd = strsep(&part_name, ":"); 485 if (!strcmp(part_name, "boot") || 486 !strcmp(part_name, "system") || 487 !strcmp(part_name, "boot")) { 488 strncat(response, "yes", chars_left); 489 } else { 490 strcpy(response, "FAILno"); 491 } 492 #else 493 fastboot_tx_write_str("FAILnot implemented"); 494 return; 495 #endif 496 } else if (!strncmp("partition-type", cmd, 14) || 497 !strncmp("partition-size", cmd, 14)) { 498 disk_partition_t part_info; 499 struct blk_desc *dev_desc; 500 char *part_name = cmd; 501 char part_size_str[20]; 502 503 cmd = strsep(&part_name, ":"); 504 dev_desc = blk_get_dev("mmc", 0); 505 if (!dev_desc) { 506 strcpy(response, "FAILblock device not found"); 507 } else if (part_get_info_by_name(dev_desc, part_name, &part_info) < 0) { 508 strcpy(response, "FAILpartition not found"); 509 } else if (!strncmp("partition-type", cmd, 14)) { 510 strncat(response, (char *)part_info.type, chars_left); 511 } else if (!strncmp("partition-size", cmd, 14)) { 512 sprintf(part_size_str, "0x%016x", (int)part_info.size); 513 strncat(response, part_size_str, chars_left); 514 } 515 } else { 516 char *envstr; 517 518 envstr = malloc(strlen("fastboot.") + strlen(cmd) + 1); 519 if (!envstr) { 520 fastboot_tx_write_str("FAILmalloc error"); 521 return; 522 } 523 524 sprintf(envstr, "fastboot.%s", cmd); 525 s = env_get(envstr); 526 if (s) { 527 strncat(response, s, chars_left); 528 } else { 529 printf("WARNING: unknown variable: %s\n", cmd); 530 strcpy(response, "FAILVariable not implemented"); 531 } 532 533 free(envstr); 534 } 535 fastboot_tx_write_str(response); 536 } 537 538 static unsigned int rx_bytes_expected(struct usb_ep *ep) 539 { 540 int rx_remain = download_size - download_bytes; 541 unsigned int rem; 542 unsigned int maxpacket = ep->maxpacket; 543 544 if (rx_remain <= 0) 545 return 0; 546 else if (rx_remain > EP_BUFFER_SIZE) 547 return EP_BUFFER_SIZE; 548 549 /* 550 * Some controllers e.g. DWC3 don't like OUT transfers to be 551 * not ending in maxpacket boundary. So just make them happy by 552 * always requesting for integral multiple of maxpackets. 553 * This shouldn't bother controllers that don't care about it. 554 */ 555 rem = rx_remain % maxpacket; 556 if (rem > 0) 557 rx_remain = rx_remain + (maxpacket - rem); 558 559 return rx_remain; 560 } 561 562 #define BYTES_PER_DOT 0x20000 563 static void rx_handler_dl_image(struct usb_ep *ep, struct usb_request *req) 564 { 565 char response[FASTBOOT_RESPONSE_LEN]; 566 unsigned int transfer_size = download_size - download_bytes; 567 const unsigned char *buffer = req->buf; 568 unsigned int buffer_size = req->actual; 569 unsigned int pre_dot_num, now_dot_num; 570 571 if (req->status != 0) { 572 printf("Bad status: %d\n", req->status); 573 return; 574 } 575 576 if (buffer_size < transfer_size) 577 transfer_size = buffer_size; 578 579 memcpy((void *)CONFIG_FASTBOOT_BUF_ADDR + download_bytes, 580 buffer, transfer_size); 581 582 pre_dot_num = download_bytes / BYTES_PER_DOT; 583 download_bytes += transfer_size; 584 now_dot_num = download_bytes / BYTES_PER_DOT; 585 586 if (pre_dot_num != now_dot_num) { 587 putc('.'); 588 if (!(now_dot_num % 74)) 589 putc('\n'); 590 } 591 592 /* Check if transfer is done */ 593 if (download_bytes >= download_size) { 594 /* 595 * Reset global transfer variable, keep download_bytes because 596 * it will be used in the next possible flashing command 597 */ 598 download_size = 0; 599 req->complete = rx_handler_command; 600 req->length = EP_BUFFER_SIZE; 601 602 strcpy(response, "OKAY"); 603 fastboot_tx_write_str(response); 604 605 printf("\ndownloading of %d bytes finished\n", download_bytes); 606 } else { 607 req->length = rx_bytes_expected(ep); 608 } 609 610 req->actual = 0; 611 usb_ep_queue(ep, req, 0); 612 } 613 614 static void cb_download(struct usb_ep *ep, struct usb_request *req) 615 { 616 char *cmd = req->buf; 617 char response[FASTBOOT_RESPONSE_LEN]; 618 619 strsep(&cmd, ":"); 620 download_size = simple_strtoul(cmd, NULL, 16); 621 download_bytes = 0; 622 623 printf("Starting download of %d bytes\n", download_size); 624 625 if (0 == download_size) { 626 strcpy(response, "FAILdata invalid size"); 627 } else if (download_size > CONFIG_FASTBOOT_BUF_SIZE) { 628 download_size = 0; 629 strcpy(response, "FAILdata too large"); 630 } else { 631 sprintf(response, "DATA%08x", download_size); 632 req->complete = rx_handler_dl_image; 633 req->length = rx_bytes_expected(ep); 634 } 635 636 fastboot_tx_write_str(response); 637 } 638 639 static void tx_handler_ul(struct usb_ep *ep, struct usb_request *req) 640 { 641 unsigned int xfer_size = 0; 642 unsigned int pre_dot_num, now_dot_num; 643 unsigned int remain_size = 0; 644 unsigned int transferred_size = req->actual; 645 646 if (req->status != 0) { 647 printf("Bad status: %d\n", req->status); 648 return; 649 } 650 651 if (start_upload) { 652 pre_dot_num = upload_bytes / BYTES_PER_DOT; 653 upload_bytes += transferred_size; 654 now_dot_num = upload_bytes / BYTES_PER_DOT; 655 656 if (pre_dot_num != now_dot_num) { 657 putc('.'); 658 if (!(now_dot_num % 74)) 659 putc('\n'); 660 } 661 } 662 663 remain_size = upload_size - upload_bytes; 664 xfer_size = (remain_size > EP_BUFFER_SIZE) ? 665 EP_BUFFER_SIZE : remain_size; 666 667 debug("%s: remain_size=%d, transferred_size=%d", 668 __func__, remain_size, transferred_size); 669 debug("xfer_size=%d, upload_bytes=%d, upload_size=%d!\n", 670 xfer_size, upload_bytes, upload_size); 671 672 if (remain_size <= 0) { 673 fastboot_func->in_req->complete = fastboot_complete; 674 fastboot_tx_write_str("OKAY"); 675 printf("\nuploading of %d bytes finished\n", upload_bytes); 676 upload_bytes = 0; 677 upload_size = 0; 678 start_upload = false; 679 return; 680 } 681 682 /* Remove the transfer callback which response the upload */ 683 /* request from host */ 684 if (!upload_bytes) 685 start_upload = true; 686 687 fastboot_tx_write((char *)(CONFIG_FASTBOOT_BUF_ADDR + upload_bytes), 688 xfer_size); 689 } 690 691 static void cb_upload(struct usb_ep *ep, struct usb_request *req) 692 { 693 char response[FASTBOOT_RESPONSE_LEN]; 694 695 upload_size = download_bytes; 696 697 printf("Starting upload of %d bytes\n", upload_size); 698 699 if (0 == upload_size) { 700 strcpy(response, "FAILdata invalid size"); 701 } else { 702 start_upload = false; 703 sprintf(response, "DATA%08x", upload_size); 704 fastboot_func->in_req->complete = tx_handler_ul; 705 } 706 707 fastboot_tx_write_str(response); 708 } 709 710 static void do_bootm_on_complete(struct usb_ep *ep, struct usb_request *req) 711 { 712 char boot_addr_start[12]; 713 char *bootm_args[] = { "bootm", boot_addr_start, NULL }; 714 715 puts("Booting kernel..\n"); 716 717 sprintf(boot_addr_start, "0x%lx", (long)CONFIG_FASTBOOT_BUF_ADDR); 718 do_bootm(NULL, 0, 2, bootm_args); 719 720 /* This only happens if image is somehow faulty so we start over */ 721 do_reset(NULL, 0, 0, NULL); 722 } 723 724 static void cb_boot(struct usb_ep *ep, struct usb_request *req) 725 { 726 fastboot_func->in_req->complete = do_bootm_on_complete; 727 fastboot_tx_write_str("OKAY"); 728 } 729 730 static void do_exit_on_complete(struct usb_ep *ep, struct usb_request *req) 731 { 732 g_dnl_trigger_detach(); 733 } 734 735 static void cb_continue(struct usb_ep *ep, struct usb_request *req) 736 { 737 fastboot_func->in_req->complete = do_exit_on_complete; 738 fastboot_tx_write_str("OKAY"); 739 } 740 741 static void cb_set_active(struct usb_ep *ep, struct usb_request *req) 742 { 743 char *cmd = req->buf; 744 745 debug("%s: %s\n", __func__, cmd); 746 747 strsep(&cmd, ":"); 748 if (!cmd) { 749 error("missing slot name"); 750 fastboot_tx_write_str("FAIL: missing slot name"); 751 return; 752 } 753 #ifdef CONFIG_AVB_LIBAVB_USER 754 unsigned int slot_number; 755 if (strncmp("a", cmd, 1) == 0) { 756 slot_number = 0; 757 set_slot_active(&slot_number); 758 } else if (strncmp("b", cmd, 1) == 0) { 759 slot_number = 1; 760 set_slot_active(&slot_number); 761 } else { 762 fastboot_tx_write_str("FAIL: unkown slot name"); 763 return; 764 } 765 766 fastboot_tx_write_str("OKAY"); 767 return; 768 #else 769 fastboot_tx_write_str("FAILnot implemented"); 770 return; 771 #endif 772 } 773 774 #ifdef CONFIG_FASTBOOT_FLASH 775 static void cb_flash(struct usb_ep *ep, struct usb_request *req) 776 { 777 char *cmd = req->buf; 778 char response[FASTBOOT_RESPONSE_LEN]; 779 780 strsep(&cmd, ":"); 781 if (!cmd) { 782 error("missing partition name"); 783 fastboot_tx_write_str("FAILmissing partition name"); 784 return; 785 } 786 787 fastboot_fail("no flash device defined", response); 788 #ifdef CONFIG_FASTBOOT_FLASH_MMC_DEV 789 fb_mmc_flash_write(cmd, (void *)CONFIG_FASTBOOT_BUF_ADDR, 790 download_bytes, response); 791 #endif 792 #ifdef CONFIG_FASTBOOT_FLASH_NAND_DEV 793 fb_nand_flash_write(cmd, (void *)CONFIG_FASTBOOT_BUF_ADDR, 794 download_bytes, response); 795 #endif 796 fastboot_tx_write_str(response); 797 } 798 #endif 799 800 static void cb_flashing(struct usb_ep *ep, struct usb_request *req) 801 { 802 char *cmd = req->buf; 803 804 if (strncmp("lock", cmd + 9, 4) == 0) { 805 fastboot_tx_write_str("FAILnot implemented"); 806 } else if (strncmp("unlock", cmd + 9, 6) == 0) { 807 fastboot_tx_write_str("FAILnot implemented"); 808 } else if (strncmp("lock_critical", cmd + 9, 12) == 0) { 809 fastboot_tx_write_str("FAILnot implemented"); 810 } else if (strncmp("unlock_critical", cmd + 9, 14) == 0) { 811 fastboot_tx_write_str("FAILnot implemented"); 812 } else if (strncmp("get_unlock_ability", cmd + 9, 17) == 0) { 813 fastboot_tx_write_str("FAILnot implemented"); 814 } else if (strncmp("get_unlock_bootloader_nonce", cmd + 4, 27) == 0) { 815 fastboot_tx_write_str("FAILnot implemented"); 816 } else if (strncmp("unlock_bootloader", cmd + 9, 17) == 0) { 817 fastboot_tx_write_str("FAILnot implemented"); 818 } else if (strncmp("lock_bootloader", cmd + 9, 15) == 0) { 819 fastboot_tx_write_str("FAILnot implemented"); 820 } else { 821 fastboot_tx_write_str("FAILunknown flashing command"); 822 } 823 } 824 825 static void cb_oem(struct usb_ep *ep, struct usb_request *req) 826 { 827 char *cmd = req->buf; 828 829 #ifdef CONFIG_FASTBOOT_FLASH_MMC_DEV 830 if (strncmp("format", cmd + 4, 6) == 0) { 831 char cmdbuf[32]; 832 sprintf(cmdbuf, "gpt write mmc %x $partitions", 833 CONFIG_FASTBOOT_FLASH_MMC_DEV); 834 if (run_command(cmdbuf, 0)) 835 fastboot_tx_write_str("FAIL"); 836 else 837 fastboot_tx_write_str("OKAY"); 838 } else 839 #endif 840 if (strncmp("unlock", cmd + 4, 8) == 0) { 841 fastboot_tx_write_str("FAILnot implemented"); 842 } else if (strncmp("at-get-ca-request", cmd + 4, 17) == 0) { 843 fastboot_tx_write_str("OKAY"); 844 } else if (strncmp("at-set-ca-response", cmd + 4, 18) == 0) { 845 fastboot_tx_write_str("OKAY"); 846 } else if (strncmp("at-lock-vboot", cmd + 4, 13) == 0) { 847 fastboot_tx_write_str("FAILnot implemented"); 848 } else if (strncmp("at-unlock-vboot", cmd + 4, 15) == 0) { 849 fastboot_tx_write_str("FAILnot implemented"); 850 } else if (strncmp("at-disable-unlock-vboot", cmd + 4, 23) == 0) { 851 fastboot_tx_write_str("FAILnot implemented"); 852 } else if (strncmp("fuse at-perm-attr", cmd + 4, 16) == 0) { 853 #ifdef CONFIG_AVB_LIBAVB_USER 854 if (write_permanent_attributes((uint8_t *) 855 CONFIG_FASTBOOT_BUF_ADDR, 856 download_bytes)) 857 fastboot_tx_write_str("FAIL"); 858 else 859 fastboot_tx_write_str("OKAY"); 860 #else 861 fastboot_tx_write_str("FAILnot implemented"); 862 #endif 863 } else { 864 fastboot_tx_write_str("FAILunknown oem command"); 865 } 866 } 867 868 #ifdef CONFIG_FASTBOOT_FLASH 869 static void cb_erase(struct usb_ep *ep, struct usb_request *req) 870 { 871 char *cmd = req->buf; 872 char response[FASTBOOT_RESPONSE_LEN]; 873 874 strsep(&cmd, ":"); 875 if (!cmd) { 876 error("missing partition name"); 877 fastboot_tx_write_str("FAILmissing partition name"); 878 return; 879 } 880 881 fastboot_fail("no flash device defined", response); 882 #ifdef CONFIG_FASTBOOT_FLASH_MMC_DEV 883 fb_mmc_erase(cmd, response); 884 #endif 885 #ifdef CONFIG_FASTBOOT_FLASH_NAND_DEV 886 fb_nand_erase(cmd, response); 887 #endif 888 fastboot_tx_write_str(response); 889 } 890 #endif 891 892 struct cmd_dispatch_info { 893 char *cmd; 894 void (*cb)(struct usb_ep *ep, struct usb_request *req); 895 }; 896 897 static const struct cmd_dispatch_info cmd_dispatch_info[] = { 898 { 899 .cmd = "reboot", 900 .cb = cb_reboot, 901 }, { 902 .cmd = "getvar:", 903 .cb = cb_getvar, 904 }, { 905 .cmd = "download:", 906 .cb = cb_download, 907 }, { 908 .cmd = "upload", 909 .cb = cb_upload, 910 }, { 911 .cmd = "boot", 912 .cb = cb_boot, 913 }, { 914 .cmd = "continue", 915 .cb = cb_continue, 916 }, { 917 .cmd = "set_active", 918 .cb = cb_set_active, 919 }, 920 #ifdef CONFIG_FASTBOOT_FLASH 921 { 922 .cmd = "flashing", 923 .cb = cb_flashing, 924 }, 925 { 926 .cmd = "flash", 927 .cb = cb_flash, 928 }, { 929 .cmd = "erase", 930 .cb = cb_erase, 931 }, 932 #endif 933 { 934 .cmd = "oem", 935 .cb = cb_oem, 936 }, 937 }; 938 939 static void rx_handler_command(struct usb_ep *ep, struct usb_request *req) 940 { 941 char *cmdbuf = req->buf; 942 void (*func_cb)(struct usb_ep *ep, struct usb_request *req) = NULL; 943 int i; 944 945 if (req->status != 0 || req->length == 0) 946 return; 947 948 for (i = 0; i < ARRAY_SIZE(cmd_dispatch_info); i++) { 949 if (!strcmp_l1(cmd_dispatch_info[i].cmd, cmdbuf)) { 950 func_cb = cmd_dispatch_info[i].cb; 951 break; 952 } 953 } 954 955 if (!func_cb) { 956 error("unknown command: %.*s", req->actual, cmdbuf); 957 fastboot_tx_write_str("FAILunknown command"); 958 } else { 959 if (req->actual < req->length) { 960 u8 *buf = (u8 *)req->buf; 961 buf[req->actual] = 0; 962 func_cb(ep, req); 963 } else { 964 error("buffer overflow"); 965 fastboot_tx_write_str("FAILbuffer overflow"); 966 } 967 } 968 969 *cmdbuf = '\0'; 970 req->actual = 0; 971 usb_ep_queue(ep, req, 0); 972 } 973