1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * SPDX-License-Identifier: BSD-2-Clause 5 */ 6 7 #include <android_bootloader.h> 8 #include <android_bootloader_message.h> 9 #include <android_avb/avb_slot_verify.h> 10 #include <android_avb/avb_ops_user.h> 11 #include <android_avb/rk_avb_ops_user.h> 12 #include <android_image.h> 13 #include <asm/arch/hotkey.h> 14 #include <cli.h> 15 #include <common.h> 16 #include <dt_table.h> 17 #include <image-android-dt.h> 18 #include <malloc.h> 19 #include <fdt_support.h> 20 #include <fs.h> 21 #include <boot_rkimg.h> 22 #include <attestation_key.h> 23 #include <keymaster.h> 24 #include <linux/libfdt_env.h> 25 #include <optee_include/OpteeClientInterface.h> 26 #include <bidram.h> 27 #include <console.h> 28 #include <sysmem.h> 29 30 DECLARE_GLOBAL_DATA_PTR; 31 32 #define ANDROID_PARTITION_BOOT "boot" 33 #define ANDROID_PARTITION_MISC "misc" 34 #define ANDROID_PARTITION_OEM "oem" 35 #define ANDROID_PARTITION_RECOVERY "recovery" 36 #define ANDROID_PARTITION_SYSTEM "system" 37 #define ANDROID_PARTITION_VBMETA "vbmeta" 38 39 #define ANDROID_ARG_SLOT_SUFFIX "androidboot.slot_suffix=" 40 #define ANDROID_ARG_ROOT "root=" 41 #define ANDROID_ARG_SERIALNO "androidboot.serialno=" 42 #define ANDROID_VERIFY_STATE "androidboot.verifiedbootstate=" 43 #ifdef CONFIG_ROCKCHIP_RESOURCE_IMAGE 44 #define ANDROID_ARG_FDT_FILENAME "rk-kernel.dtb" 45 #define BOOTLOADER_MESSAGE_OFFSET_IN_MISC (16 * 1024) 46 #define BOOTLOADER_MESSAGE_BLK_OFFSET (BOOTLOADER_MESSAGE_OFFSET_IN_MISC >> 9) 47 #else 48 #define ANDROID_ARG_FDT_FILENAME "kernel.dtb" 49 #endif 50 #define OEM_UNLOCK_ARG_SIZE 30 51 #define UUID_SIZE 37 52 53 #ifdef CONFIG_ANDROID_AB 54 static int get_partition_unique_uuid(char *partition, 55 char *guid_buf, 56 size_t guid_buf_size) 57 { 58 struct blk_desc *dev_desc; 59 disk_partition_t part_info; 60 61 dev_desc = rockchip_get_bootdev(); 62 if (!dev_desc) { 63 printf("%s: Could not find device\n", __func__); 64 return -1; 65 } 66 67 if (part_get_info_by_name(dev_desc, partition, &part_info) < 0) { 68 printf("Could not find \"%s\" partition\n", partition); 69 return -1; 70 } 71 72 if (guid_buf && guid_buf_size > 0) 73 memcpy(guid_buf, part_info.uuid, guid_buf_size); 74 75 return 0; 76 } 77 #endif 78 79 char *android_str_append(char *base_name, char *slot_suffix) 80 { 81 char *part_name; 82 size_t part_name_len; 83 84 part_name_len = strlen(base_name) + 1; 85 if (slot_suffix) 86 part_name_len += strlen(slot_suffix); 87 part_name = malloc(part_name_len); 88 if (!part_name) 89 return NULL; 90 strcpy(part_name, base_name); 91 if (slot_suffix && (slot_suffix[0] != '\0')) 92 strcat(part_name, slot_suffix); 93 94 return part_name; 95 } 96 97 int android_bootloader_message_load( 98 struct blk_desc *dev_desc, 99 const disk_partition_t *part_info, 100 struct android_bootloader_message *message) 101 { 102 ulong message_blocks = sizeof(struct android_bootloader_message) / 103 part_info->blksz; 104 if (message_blocks > part_info->size) { 105 printf("misc partition too small.\n"); 106 return -1; 107 } 108 109 #ifdef CONFIG_RKIMG_BOOTLOADER 110 if (blk_dread(dev_desc, part_info->start + BOOTLOADER_MESSAGE_BLK_OFFSET, 111 message_blocks, message) != 112 #else 113 if (blk_dread(dev_desc, part_info->start, message_blocks, message) != 114 #endif 115 message_blocks) { 116 printf("Could not read from misc partition\n"); 117 return -1; 118 } 119 debug("ANDROID: Loaded BCB, %lu blocks.\n", message_blocks); 120 return 0; 121 } 122 123 static int android_bootloader_message_write( 124 struct blk_desc *dev_desc, 125 const disk_partition_t *part_info, 126 struct android_bootloader_message *message) 127 { 128 #ifdef CONFIG_RKIMG_BOOTLOADER 129 ulong message_blocks = sizeof(struct android_bootloader_message) / 130 part_info->blksz + BOOTLOADER_MESSAGE_BLK_OFFSET; 131 #else 132 ulong message_blocks = sizeof(struct android_bootloader_message) / 133 part_info->blksz; 134 #endif 135 if (message_blocks > part_info->size) { 136 printf("misc partition too small.\n"); 137 return -1; 138 } 139 140 if (blk_dwrite(dev_desc, part_info->start, message_blocks, message) != 141 message_blocks) { 142 printf("Could not write to misc partition\n"); 143 return -1; 144 } 145 debug("ANDROID: Wrote new BCB, %lu blocks.\n", message_blocks); 146 return 0; 147 } 148 149 static enum android_boot_mode android_bootloader_load_and_clear_mode( 150 struct blk_desc *dev_desc, 151 const disk_partition_t *misc_part_info) 152 { 153 struct android_bootloader_message bcb; 154 155 #ifdef CONFIG_FASTBOOT 156 char *bootloader_str; 157 158 /* Check for message from bootloader stored in RAM from a previous boot. 159 */ 160 bootloader_str = (char *)CONFIG_FASTBOOT_BUF_ADDR; 161 if (!strcmp("reboot-bootloader", bootloader_str)) { 162 bootloader_str[0] = '\0'; 163 return ANDROID_BOOT_MODE_BOOTLOADER; 164 } 165 #endif 166 167 /* Check and update the BCB message if needed. */ 168 if (android_bootloader_message_load(dev_desc, misc_part_info, &bcb) < 169 0) { 170 printf("WARNING: Unable to load the BCB.\n"); 171 return ANDROID_BOOT_MODE_NORMAL; 172 } 173 174 if (!strcmp("bootonce-bootloader", bcb.command)) { 175 /* Erase the message in the BCB since this value should be used 176 * only once. 177 */ 178 memset(bcb.command, 0, sizeof(bcb.command)); 179 android_bootloader_message_write(dev_desc, misc_part_info, 180 &bcb); 181 return ANDROID_BOOT_MODE_BOOTLOADER; 182 } 183 184 if (!strcmp("boot-recovery", bcb.command)) 185 return ANDROID_BOOT_MODE_RECOVERY; 186 187 return ANDROID_BOOT_MODE_NORMAL; 188 } 189 190 /** 191 * Return the reboot reason string for the passed boot mode. 192 * 193 * @param mode The Android Boot mode. 194 * @return a pointer to the reboot reason string for mode. 195 */ 196 static const char *android_boot_mode_str(enum android_boot_mode mode) 197 { 198 switch (mode) { 199 case ANDROID_BOOT_MODE_NORMAL: 200 return "(none)"; 201 case ANDROID_BOOT_MODE_RECOVERY: 202 return "recovery"; 203 case ANDROID_BOOT_MODE_BOOTLOADER: 204 return "bootloader"; 205 } 206 return NULL; 207 } 208 209 static int android_part_get_info_by_name_suffix(struct blk_desc *dev_desc, 210 const char *base_name, 211 const char *slot_suffix, 212 disk_partition_t *part_info) 213 { 214 char *part_name; 215 int part_num; 216 size_t part_name_len; 217 218 part_name_len = strlen(base_name) + 1; 219 if (slot_suffix) 220 part_name_len += strlen(slot_suffix); 221 part_name = malloc(part_name_len); 222 if (!part_name) 223 return -1; 224 strcpy(part_name, base_name); 225 if (slot_suffix && (slot_suffix[0] != '\0')) 226 strcat(part_name, slot_suffix); 227 228 part_num = part_get_info_by_name(dev_desc, part_name, part_info); 229 if (part_num < 0) { 230 debug("ANDROID: Could not find partition \"%s\"\n", part_name); 231 part_num = -1; 232 } 233 234 free(part_name); 235 return part_num; 236 } 237 238 static int android_bootloader_boot_bootloader(void) 239 { 240 const char *fastboot_cmd = env_get("fastbootcmd"); 241 242 if (fastboot_cmd == NULL) { 243 printf("fastboot_cmd is null, run default fastboot_cmd!\n"); 244 fastboot_cmd = "fastboot usb 0"; 245 } 246 247 return run_command(fastboot_cmd, CMD_FLAG_ENV); 248 } 249 250 #ifdef CONFIG_SUPPORT_OEM_DTB 251 static int android_bootloader_get_fdt(const char *part_name, 252 const char *load_file_name) 253 { 254 struct blk_desc *dev_desc; 255 disk_partition_t boot_part_info; 256 char *fdt_addr = NULL; 257 char slot_suffix[5] = {0}; 258 char dev_part[3] = {0}; 259 loff_t bytes = 0; 260 loff_t pos = 0; 261 loff_t len_read; 262 unsigned long addr = 0; 263 int part_num = -1; 264 int ret; 265 266 dev_desc = rockchip_get_bootdev(); 267 if (!dev_desc) { 268 printf("%s: dev_desc is NULL!\n", __func__); 269 return -1; 270 } 271 272 memset(&boot_part_info, 0, sizeof(boot_part_info)); 273 274 #ifdef CONFIG_RK_AVB_LIBAVB_USER 275 if (rk_avb_get_current_slot(slot_suffix)) { 276 printf("ANDROID: Get Current Slot error.\n"); 277 return -1; 278 } 279 280 part_num = android_part_get_info_by_name_suffix(dev_desc, 281 part_name, 282 slot_suffix, &boot_part_info); 283 #else 284 part_num = part_get_info_by_name(dev_desc, part_name, &boot_part_info); 285 if (part_num < 0) { 286 printf("ANDROID: Could not find partition \"%s\"\n", part_name); 287 return -1; 288 } 289 #endif 290 291 snprintf(dev_part, ARRAY_SIZE(dev_part), ":%x", part_num); 292 if (fs_set_blk_dev_with_part(dev_desc, part_num)) 293 return -1; 294 295 fdt_addr = env_get("fdt_addr_r"); 296 if (!fdt_addr) { 297 printf("ANDROID: No Found FDT Load Address.\n"); 298 return -1; 299 } 300 addr = simple_strtoul(fdt_addr, NULL, 16); 301 302 ret = fs_read(load_file_name, addr, pos, bytes, &len_read); 303 if (ret < 0) 304 return -1; 305 306 return 0; 307 } 308 #endif 309 310 /* 311 * Test on RK3308 AARCH64 mode (Cortex A35 816 MHZ) boot with eMMC: 312 * 313 * |-------------------------------------------------------------------| 314 * | Format | Size(Byte) | Ratio | Decomp time(ms) | Boot time(ms) | 315 * |-------------------------------------------------------------------| 316 * | Image | 7720968 | | | 488 | 317 * |-------------------------------------------------------------------| 318 * | Image.lz4 | 4119448 | 53% | 59 | 455 | 319 * |-------------------------------------------------------------------| 320 * | Image.lzo | 3858322 | 49% | 141 | 536 | 321 * |-------------------------------------------------------------------| 322 * | Image.gz | 3529108 | 45% | 222 | 609 | 323 * |-------------------------------------------------------------------| 324 * | Image.bz2 | 3295914 | 42% | 2940 | | 325 * |-------------------------------------------------------------------| 326 * | Image.lzma| 2683750 | 34% | | | 327 * |-------------------------------------------------------------------| 328 */ 329 static int sysmem_alloc_uncomp_kernel(ulong andr_hdr, 330 ulong uncomp_kaddr, u32 comp) 331 { 332 struct andr_img_hdr *hdr = (struct andr_img_hdr *)andr_hdr; 333 ulong ksize, kaddr; 334 335 if (comp != IH_COMP_NONE) { 336 /* Release compressed sysmem */ 337 kaddr = env_get_hex("kernel_addr_c", 0); 338 if (!kaddr) 339 kaddr = env_get_hex("kernel_addr_r", 0); 340 kaddr -= hdr->page_size; 341 if (sysmem_free((phys_addr_t)kaddr)) 342 return -EINVAL; 343 344 /* 345 * Use smaller Ratio to get larger estimated uncompress 346 * kernel size. 347 */ 348 if (comp == IH_COMP_ZIMAGE) 349 ksize = hdr->kernel_size * 100 / 45; 350 else if (comp == IH_COMP_LZ4) 351 ksize = hdr->kernel_size * 100 / 50; 352 else if (comp == IH_COMP_LZO) 353 ksize = hdr->kernel_size * 100 / 45; 354 else if (comp == IH_COMP_GZIP) 355 ksize = hdr->kernel_size * 100 / 40; 356 else if (comp == IH_COMP_BZIP2) 357 ksize = hdr->kernel_size * 100 / 40; 358 else if (comp == IH_COMP_LZMA) 359 ksize = hdr->kernel_size * 100 / 30; 360 else 361 ksize = hdr->kernel_size; 362 363 kaddr = uncomp_kaddr; 364 ksize = ALIGN(ksize, 512); 365 if (!sysmem_alloc_base(MEMBLK_ID_UNCOMP_KERNEL, 366 (phys_addr_t)kaddr, ksize)) 367 return -ENOMEM; 368 369 hotkey_run(HK_SYSMEM); 370 } 371 372 return 0; 373 } 374 375 int android_bootloader_boot_kernel(unsigned long kernel_address) 376 { 377 char *kernel_addr_r = env_get("kernel_addr_r"); 378 char *kernel_addr_c = env_get("kernel_addr_c"); 379 char *fdt_addr = env_get("fdt_addr"); 380 char kernel_addr_str[12]; 381 char comp_str[32] = {0}; 382 ulong comp_type; 383 const char *comp_name[] = { 384 [IH_COMP_NONE] = "IMAGE", 385 [IH_COMP_GZIP] = "GZIP", 386 [IH_COMP_BZIP2] = "BZIP2", 387 [IH_COMP_LZMA] = "LZMA", 388 [IH_COMP_LZO] = "LZO", 389 [IH_COMP_LZ4] = "LZ4", 390 [IH_COMP_ZIMAGE]= "ZIMAGE", 391 }; 392 char *bootm_args[] = { 393 "bootm", kernel_addr_str, kernel_addr_str, fdt_addr, NULL }; 394 395 comp_type = env_get_ulong("os_comp", 10, 0); 396 sprintf(kernel_addr_str, "0x%08lx", kernel_address); 397 398 if (comp_type != IH_COMP_NONE) { 399 if (comp_type == IH_COMP_ZIMAGE && 400 kernel_addr_r && !kernel_addr_c) { 401 kernel_addr_c = kernel_addr_r; 402 kernel_addr_r = __stringify(CONFIG_SYS_SDRAM_BASE); 403 } 404 snprintf(comp_str, 32, "%s%s%s", 405 "(Uncompress to ", kernel_addr_r, ")"); 406 } 407 408 printf("Booting %s kernel at %s%s with fdt at %s...\n\n\n", 409 comp_name[comp_type], 410 comp_type != IH_COMP_NONE ? kernel_addr_c : kernel_addr_r, 411 comp_str, fdt_addr); 412 413 hotkey_run(HK_SYSMEM); 414 415 /* 416 * Check whether there is enough space for uncompress kernel, 417 * Actually, here only gives a sysmem warning message when failed 418 * but never return -1. 419 */ 420 if (sysmem_alloc_uncomp_kernel(kernel_address, 421 simple_strtoul(kernel_addr_r, NULL, 16), 422 comp_type)) 423 return -1; 424 425 /* Check sysmem overflow */ 426 sysmem_overflow_check(); 427 428 do_bootm(NULL, 0, 4, bootm_args); 429 430 return -1; 431 } 432 433 static char *strjoin(const char **chunks, char separator) 434 { 435 int len, joined_len = 0; 436 char *ret, *current; 437 const char **p; 438 439 for (p = chunks; *p; p++) 440 joined_len += strlen(*p) + 1; 441 442 if (!joined_len) { 443 ret = malloc(1); 444 if (ret) 445 ret[0] = '\0'; 446 return ret; 447 } 448 449 ret = malloc(joined_len); 450 current = ret; 451 if (!ret) 452 return ret; 453 454 for (p = chunks; *p; p++) { 455 len = strlen(*p); 456 memcpy(current, *p, len); 457 current += len; 458 *current = separator; 459 current++; 460 } 461 /* Replace the last separator by a \0. */ 462 current[-1] = '\0'; 463 return ret; 464 } 465 466 /** android_assemble_cmdline - Assemble the command line to pass to the kernel 467 * @return a newly allocated string 468 */ 469 char *android_assemble_cmdline(const char *slot_suffix, 470 const char *extra_args) 471 { 472 const char *cmdline_chunks[16]; 473 const char **current_chunk = cmdline_chunks; 474 char *env_cmdline, *cmdline, *rootdev_input, *serialno; 475 char *allocated_suffix = NULL; 476 char *allocated_serialno = NULL; 477 char *allocated_rootdev = NULL; 478 unsigned long rootdev_len; 479 480 env_cmdline = env_get("bootargs"); 481 if (env_cmdline) 482 *(current_chunk++) = env_cmdline; 483 484 /* The |slot_suffix| needs to be passed to the kernel to know what 485 * slot to boot from. 486 */ 487 if (slot_suffix) { 488 allocated_suffix = malloc(strlen(ANDROID_ARG_SLOT_SUFFIX) + 489 strlen(slot_suffix) + 1); 490 memset(allocated_suffix, 0, strlen(ANDROID_ARG_SLOT_SUFFIX) 491 + strlen(slot_suffix) + 1); 492 strcpy(allocated_suffix, ANDROID_ARG_SLOT_SUFFIX); 493 strcat(allocated_suffix, slot_suffix); 494 *(current_chunk++) = allocated_suffix; 495 } 496 497 serialno = env_get("serial#"); 498 if (serialno) { 499 allocated_serialno = malloc(strlen(ANDROID_ARG_SERIALNO) + 500 strlen(serialno) + 1); 501 memset(allocated_serialno, 0, strlen(ANDROID_ARG_SERIALNO) + 502 strlen(serialno) + 1); 503 strcpy(allocated_serialno, ANDROID_ARG_SERIALNO); 504 strcat(allocated_serialno, serialno); 505 *(current_chunk++) = allocated_serialno; 506 } 507 508 rootdev_input = env_get("android_rootdev"); 509 if (rootdev_input) { 510 rootdev_len = strlen(ANDROID_ARG_ROOT) + CONFIG_SYS_CBSIZE + 1; 511 allocated_rootdev = malloc(rootdev_len); 512 strcpy(allocated_rootdev, ANDROID_ARG_ROOT); 513 cli_simple_process_macros(rootdev_input, 514 allocated_rootdev + 515 strlen(ANDROID_ARG_ROOT)); 516 /* Make sure that the string is null-terminated since the 517 * previous could not copy to the end of the input string if it 518 * is too big. 519 */ 520 allocated_rootdev[rootdev_len - 1] = '\0'; 521 *(current_chunk++) = allocated_rootdev; 522 } 523 524 if (extra_args) 525 *(current_chunk++) = extra_args; 526 527 *(current_chunk++) = NULL; 528 cmdline = strjoin(cmdline_chunks, ' '); 529 free(allocated_suffix); 530 free(allocated_rootdev); 531 return cmdline; 532 } 533 534 #ifdef CONFIG_ANDROID_AVB 535 static void slot_set_unbootable(AvbABSlotData* slot) 536 { 537 slot->priority = 0; 538 slot->tries_remaining = 0; 539 slot->successful_boot = 0; 540 } 541 542 static AvbSlotVerifyResult android_slot_verify(char *boot_partname, 543 unsigned long *android_load_address, 544 char *slot_suffix) 545 { 546 const char *requested_partitions[1] = {NULL}; 547 uint8_t unlocked = true; 548 AvbOps *ops; 549 AvbSlotVerifyFlags flags; 550 AvbSlotVerifyData *slot_data[1] = {NULL}; 551 AvbSlotVerifyResult verify_result; 552 AvbABData ab_data, ab_data_orig; 553 size_t slot_index_to_boot = 0; 554 char verify_state[38] = {0}; 555 char can_boot = 1; 556 unsigned long load_address = *android_load_address; 557 struct andr_img_hdr *hdr; 558 559 requested_partitions[0] = boot_partname; 560 ops = avb_ops_user_new(); 561 if (ops == NULL) { 562 printf("avb_ops_user_new() failed!\n"); 563 return AVB_SLOT_VERIFY_RESULT_ERROR_OOM; 564 } 565 566 if (ops->read_is_device_unlocked(ops, (bool *)&unlocked) != AVB_IO_RESULT_OK) 567 printf("Error determining whether device is unlocked.\n"); 568 569 printf("read_is_device_unlocked() ops returned that device is %s\n", 570 (unlocked & LOCK_MASK)? "UNLOCKED" : "LOCKED"); 571 572 flags = AVB_SLOT_VERIFY_FLAGS_NONE; 573 if (unlocked & LOCK_MASK) 574 flags |= AVB_SLOT_VERIFY_FLAGS_ALLOW_VERIFICATION_ERROR; 575 576 if(load_metadata(ops->ab_ops, &ab_data, &ab_data_orig)) { 577 printf("Can not load metadata\n"); 578 return AVB_SLOT_VERIFY_RESULT_ERROR_IO; 579 } 580 581 if (!strncmp(slot_suffix, "_a", 2)) 582 slot_index_to_boot = 0; 583 else if (!strncmp(slot_suffix, "_b", 2)) 584 slot_index_to_boot = 1; 585 else 586 slot_index_to_boot = 0; 587 588 verify_result = 589 avb_slot_verify(ops, 590 requested_partitions, 591 slot_suffix, 592 flags, 593 AVB_HASHTREE_ERROR_MODE_RESTART_AND_INVALIDATE, 594 &slot_data[0]); 595 596 strcat(verify_state, ANDROID_VERIFY_STATE); 597 switch (verify_result) { 598 case AVB_SLOT_VERIFY_RESULT_OK: 599 if (unlocked & LOCK_MASK) 600 strcat(verify_state, "orange"); 601 else 602 strcat(verify_state, "green"); 603 break; 604 case AVB_SLOT_VERIFY_RESULT_ERROR_PUBLIC_KEY_REJECTED: 605 if (unlocked & LOCK_MASK) 606 strcat(verify_state, "orange"); 607 else 608 strcat(verify_state, "yellow"); 609 break; 610 case AVB_SLOT_VERIFY_RESULT_ERROR_OOM: 611 case AVB_SLOT_VERIFY_RESULT_ERROR_IO: 612 case AVB_SLOT_VERIFY_RESULT_ERROR_INVALID_METADATA: 613 case AVB_SLOT_VERIFY_RESULT_ERROR_UNSUPPORTED_VERSION: 614 case AVB_SLOT_VERIFY_RESULT_ERROR_VERIFICATION: 615 case AVB_SLOT_VERIFY_RESULT_ERROR_ROLLBACK_INDEX: 616 default: 617 if (unlocked & LOCK_MASK) 618 strcat(verify_state, "orange"); 619 else 620 strcat(verify_state, "red"); 621 break; 622 } 623 624 if (!slot_data[0]) { 625 can_boot = 0; 626 goto out; 627 } 628 629 if (verify_result == AVB_SLOT_VERIFY_RESULT_OK || 630 verify_result == AVB_SLOT_VERIFY_RESULT_ERROR_PUBLIC_KEY_REJECTED || 631 (unlocked & LOCK_MASK)) { 632 int len = 0; 633 char *bootargs, *newbootargs; 634 635 if (*slot_data[0]->cmdline) { 636 debug("Kernel command line: %s\n", slot_data[0]->cmdline); 637 len += strlen(slot_data[0]->cmdline); 638 } 639 640 bootargs = env_get("bootargs"); 641 if (bootargs) 642 len += strlen(bootargs); 643 644 newbootargs = malloc(len + 2); 645 646 if (!newbootargs) { 647 puts("Error: malloc in android_slot_verify failed!\n"); 648 return AVB_SLOT_VERIFY_RESULT_ERROR_OOM; 649 } 650 *newbootargs = '\0'; 651 652 if (bootargs) { 653 strcpy(newbootargs, bootargs); 654 strcat(newbootargs, " "); 655 } 656 if (*slot_data[0]->cmdline) 657 strcat(newbootargs, slot_data[0]->cmdline); 658 env_set("bootargs", newbootargs); 659 660 /* Reserve page_size */ 661 hdr = (void *)slot_data[0]->loaded_partitions->data; 662 load_address -= hdr->page_size; 663 *android_load_address = load_address; 664 665 #ifdef CONFIG_ANDROID_BOOT_IMAGE_SEPARATE 666 android_image_memcpy_separate(hdr, (void *)load_address); 667 #else 668 memcpy((uint8_t *)load_address, 669 slot_data[0]->loaded_partitions->data, 670 slot_data[0]->loaded_partitions->data_size); 671 #endif 672 } else { 673 slot_set_unbootable(&ab_data.slots[slot_index_to_boot]); 674 } 675 676 out: 677 #if defined(CONFIG_ANDROID_AB) && !defined(CONFIG_ANDROID_AVB) 678 /* 679 * In ab & avb process, the tries_remaining minus one in function 680 * android_slot_verify, shield this function here. 681 */ 682 /* ... and decrement tries remaining, if applicable. */ 683 if (!ab_data.slots[slot_index_to_boot].successful_boot && 684 ab_data.slots[slot_index_to_boot].tries_remaining > 0) { 685 ab_data.slots[slot_index_to_boot].tries_remaining -= 1; 686 } 687 #endif 688 env_update("bootargs", verify_state); 689 if (save_metadata_if_changed(ops->ab_ops, &ab_data, &ab_data_orig)) { 690 printf("Can not save metadata\n"); 691 verify_result = AVB_SLOT_VERIFY_RESULT_ERROR_IO; 692 } 693 694 if (slot_data[0] != NULL) 695 avb_slot_verify_data_free(slot_data[0]); 696 697 if ((unlocked & LOCK_MASK) && can_boot) 698 return 0; 699 else 700 return verify_result; 701 } 702 #endif 703 704 #if defined(CONFIG_CMD_DTIMG) && defined(CONFIG_OF_LIBFDT_OVERLAY) 705 706 /* 707 * Default return index 0. 708 */ 709 __weak int board_select_fdt_index(ulong dt_table_hdr) 710 { 711 /* 712 * User can use "dt_for_each_entry(entry, hdr, idx)" to iterate 713 * over all dt entry of DT image and pick up which they want. 714 * 715 * Example: 716 * struct dt_table_entry *entry; 717 * int index; 718 * 719 * dt_for_each_entry(entry, dt_table_hdr, index) { 720 * 721 * .... (use entry) 722 * } 723 * 724 * return index; 725 */ 726 return 0; 727 } 728 729 static int android_get_dtbo(ulong *fdt_dtbo, 730 const struct andr_img_hdr *hdr, 731 int *index) 732 { 733 struct dt_table_header *dt_hdr = NULL; 734 struct blk_desc *dev_desc; 735 const char *part_name; 736 disk_partition_t part_info; 737 u32 blk_offset, blk_cnt; 738 void *buf; 739 ulong e_addr; 740 u32 e_size; 741 int e_idx; 742 int ret; 743 744 /* Get partition according to boot mode */ 745 if (rockchip_get_boot_mode() == BOOT_MODE_RECOVERY) 746 part_name = PART_RECOVERY; 747 else 748 part_name = PART_DTBO; 749 750 /* Get partition info */ 751 dev_desc = rockchip_get_bootdev(); 752 if (!dev_desc) { 753 printf("%s: dev_desc is NULL!\n", __func__); 754 return -ENODEV; 755 } 756 757 ret = part_get_info_by_name(dev_desc, part_name, &part_info); 758 if (ret < 0) { 759 printf("%s: failed to get %s part info, ret=%d\n", 760 __func__, part_name, ret); 761 return ret; 762 } 763 764 /* Check dt table header */ 765 if (!strcmp(part_name, PART_RECOVERY)) 766 blk_offset = part_info.start + 767 (hdr->recovery_dtbo_offset / part_info.blksz); 768 else 769 blk_offset = part_info.start; 770 771 dt_hdr = memalign(ARCH_DMA_MINALIGN, part_info.blksz); 772 if (!dt_hdr) { 773 printf("%s: out of memory for dt header!\n", __func__); 774 return -ENOMEM; 775 } 776 777 ret = blk_dread(dev_desc, blk_offset, 1, dt_hdr); 778 if (ret != 1) { 779 printf("%s: failed to read dt table header\n", 780 __func__); 781 goto out1; 782 } 783 784 if (!android_dt_check_header((ulong)dt_hdr)) { 785 printf("%s: Error: invalid dt table header: 0x%x\n", 786 __func__, dt_hdr->magic); 787 ret = -EINVAL; 788 goto out1; 789 } 790 791 #ifdef DEBUG 792 android_dt_print_contents((ulong)dt_hdr); 793 #endif 794 795 blk_cnt = DIV_ROUND_UP(fdt32_to_cpu(dt_hdr->total_size), 796 part_info.blksz); 797 /* Read all DT Image */ 798 buf = memalign(ARCH_DMA_MINALIGN, part_info.blksz * blk_cnt); 799 if (!buf) { 800 printf("%s: out of memory for %s part!\n", __func__, part_name); 801 ret = -ENOMEM; 802 goto out1; 803 } 804 805 ret = blk_dread(dev_desc, blk_offset, blk_cnt, buf); 806 if (ret != blk_cnt) { 807 printf("%s: failed to read dtbo, blk_cnt=%d, ret=%d\n", 808 __func__, blk_cnt, ret); 809 goto out2; 810 } 811 812 e_idx = board_select_fdt_index((ulong)buf); 813 if (e_idx < 0) { 814 printf("%s: failed to select board fdt index\n", __func__); 815 ret = -EINVAL; 816 goto out2; 817 } 818 819 ret = android_dt_get_fdt_by_index((ulong)buf, e_idx, &e_addr, &e_size); 820 if (!ret) { 821 printf("%s: failed to get fdt, index=%d\n", __func__, e_idx); 822 ret = -EINVAL; 823 goto out2; 824 } 825 826 if (fdt_dtbo) 827 *fdt_dtbo = e_addr; 828 if (index) 829 *index = e_idx; 830 831 free(dt_hdr); 832 debug("ANDROID: Loading dt entry to 0x%lx size 0x%x idx %d from \"%s\" part\n", 833 e_addr, e_size, e_idx, part_name); 834 835 return 0; 836 837 out2: 838 free(buf); 839 out1: 840 free(dt_hdr); 841 842 return ret; 843 } 844 845 int android_fdt_overlay_apply(void *fdt_addr) 846 { 847 struct andr_img_hdr *hdr; 848 struct blk_desc *dev_desc; 849 const char *part_name; 850 disk_partition_t part_info; 851 char buf[32] = {0}; 852 u32 blk_cnt; 853 ulong fdt_dtbo = -1; 854 int index = -1; 855 int ret; 856 857 /* Get partition according to boot mode */ 858 if (rockchip_get_boot_mode() == BOOT_MODE_RECOVERY) 859 part_name = PART_RECOVERY; 860 else 861 part_name = PART_BOOT; 862 863 /* Get partition info */ 864 dev_desc = rockchip_get_bootdev(); 865 if (!dev_desc) { 866 printf("%s: dev_desc is NULL!\n", __func__); 867 return -ENODEV; 868 } 869 870 ret = part_get_info_by_name(dev_desc, part_name, &part_info); 871 if (ret < 0) { 872 printf("%s: failed to get %s part info, ret=%d\n", 873 __func__, part_name, ret); 874 return ret; 875 } 876 877 blk_cnt = DIV_ROUND_UP(sizeof(*hdr), part_info.blksz); 878 hdr = memalign(ARCH_DMA_MINALIGN, part_info.blksz * blk_cnt); 879 if (!hdr) { 880 printf("%s: out of memory!\n", __func__); 881 return -ENOMEM; 882 } 883 884 ret = blk_dread(dev_desc, part_info.start, blk_cnt, hdr); 885 if (ret != blk_cnt) { 886 printf("%s: failed to read %s hdr!\n", __func__, part_name); 887 goto out; 888 } 889 890 #ifdef DEBUG 891 android_print_contents(hdr); 892 #endif 893 894 if (android_image_check_header(hdr)) 895 return -EINVAL; 896 897 /* Check header version */ 898 if (!hdr->header_version) { 899 printf("Android header version 0\n"); 900 ret = -EINVAL; 901 goto out; 902 } 903 904 ret = android_get_dtbo(&fdt_dtbo, (void *)hdr, &index); 905 if (!ret) { 906 phys_size_t fdt_size; 907 /* Must incease size before overlay */ 908 fdt_size = fdt_totalsize((void *)fdt_addr) + 909 fdt_totalsize((void *)fdt_dtbo); 910 if (sysmem_free((phys_addr_t)fdt_addr)) 911 goto out; 912 913 if (!sysmem_alloc_base(MEMBLK_ID_FDT_DTBO, 914 (phys_addr_t)fdt_addr, 915 fdt_size + CONFIG_SYS_FDT_PAD)) 916 goto out; 917 fdt_increase_size(fdt_addr, fdt_totalsize((void *)fdt_dtbo)); 918 ret = fdt_overlay_apply(fdt_addr, (void *)fdt_dtbo); 919 if (!ret) { 920 snprintf(buf, 32, "%s%d", "androidboot.dtbo_idx=", index); 921 env_update("bootargs", buf); 922 printf("ANDROID: fdt overlay OK\n"); 923 } else { 924 printf("ANDROID: fdt overlay failed, ret=%d\n", ret); 925 } 926 } 927 928 out: 929 free(hdr); 930 931 return 0; 932 } 933 #endif 934 935 static int load_android_image(struct blk_desc *dev_desc, 936 char *boot_partname, 937 char *slot_suffix, 938 unsigned long *load_address) 939 { 940 disk_partition_t boot_part; 941 int ret, part_num; 942 943 part_num = android_part_get_info_by_name_suffix(dev_desc, 944 boot_partname, 945 slot_suffix, 946 &boot_part); 947 if (part_num < 0) { 948 printf("%s: Can't find part: %s\n", __func__, boot_partname); 949 return -1; 950 } 951 debug("ANDROID: Loading kernel from \"%s\", partition %d.\n", 952 boot_part.name, part_num); 953 954 ret = android_image_load(dev_desc, &boot_part, *load_address, -1UL); 955 if (ret < 0) { 956 debug("%s: %s part load fail, ret=%d\n", 957 __func__, boot_part.name, ret); 958 return ret; 959 } 960 *load_address = ret; 961 962 return 0; 963 } 964 965 int android_bootloader_boot_flow(struct blk_desc *dev_desc, 966 unsigned long load_address) 967 { 968 enum android_boot_mode mode = ANDROID_BOOT_MODE_NORMAL; 969 disk_partition_t misc_part_info; 970 int part_num; 971 int ret; 972 char *command_line; 973 char slot_suffix[3] = {0}; 974 const char *mode_cmdline = NULL; 975 char *boot_partname = ANDROID_PARTITION_BOOT; 976 ulong fdt_addr; 977 978 /* 979 * 1. Load MISC partition and determine the boot mode 980 * clear its value for the next boot if needed. 981 */ 982 part_num = part_get_info_by_name(dev_desc, ANDROID_PARTITION_MISC, 983 &misc_part_info); 984 if (part_num < 0) { 985 printf("Could not find misc partition\n"); 986 } else { 987 #ifdef CONFIG_ANDROID_KEYMASTER_CA 988 /* load attestation key from misc partition. */ 989 load_attestation_key(dev_desc, &misc_part_info); 990 #endif 991 992 mode = android_bootloader_load_and_clear_mode(dev_desc, 993 &misc_part_info); 994 #ifdef CONFIG_RKIMG_BOOTLOADER 995 if (mode == ANDROID_BOOT_MODE_NORMAL) { 996 if (rockchip_get_boot_mode() == BOOT_MODE_RECOVERY) 997 mode = ANDROID_BOOT_MODE_RECOVERY; 998 } 999 #endif 1000 } 1001 1002 printf("ANDROID: reboot reason: \"%s\"\n", android_boot_mode_str(mode)); 1003 1004 #ifdef CONFIG_ANDROID_AB 1005 /*TODO: get from pre-loader or misc partition*/ 1006 if (rk_avb_get_current_slot(slot_suffix)) { 1007 printf("rk_avb_get_current_slot() failed\n"); 1008 return -1; 1009 } 1010 1011 AvbOps *ops; 1012 AvbABData ab_data; 1013 AvbABData ab_data_orig; 1014 size_t slot_index_to_boot = 0; 1015 1016 if (!strncmp(slot_suffix, "_a", 2)) 1017 slot_index_to_boot = 0; 1018 else if (!strncmp(slot_suffix, "_b", 2)) 1019 slot_index_to_boot = 1; 1020 else 1021 slot_index_to_boot = 0; 1022 ops = avb_ops_user_new(); 1023 if (ops == NULL) { 1024 printf("avb_ops_user_new() failed!\n"); 1025 return -1; 1026 } 1027 1028 if(load_metadata(ops->ab_ops, &ab_data, &ab_data_orig)) { 1029 printf("Can not load metadata\n"); 1030 return -1; 1031 } 1032 1033 /* ... and decrement tries remaining, if applicable. */ 1034 if (!ab_data.slots[slot_index_to_boot].successful_boot && 1035 ab_data.slots[slot_index_to_boot].tries_remaining > 0) { 1036 ab_data.slots[slot_index_to_boot].tries_remaining -= 1; 1037 } 1038 1039 if (save_metadata_if_changed(ops->ab_ops, &ab_data, &ab_data_orig)) { 1040 printf("Can not save metadata\n"); 1041 return -1; 1042 } 1043 1044 if (slot_suffix[0] != '_') { 1045 #ifndef CONFIG_ANDROID_AVB 1046 printf("###There is no bootable slot, bring up lastboot!###\n"); 1047 if (rk_get_lastboot() == 1) 1048 memcpy(slot_suffix, "_b", 2); 1049 else if(rk_get_lastboot() == 0) 1050 memcpy(slot_suffix, "_a", 2); 1051 else 1052 #endif 1053 return -1; 1054 } 1055 #endif 1056 1057 switch (mode) { 1058 case ANDROID_BOOT_MODE_NORMAL: 1059 /* In normal mode, we load the kernel from "boot" but append 1060 * "skip_initramfs" to the cmdline to make it ignore the 1061 * recovery initramfs in the boot partition. 1062 */ 1063 #ifdef CONFIG_ANDROID_AB 1064 mode_cmdline = "skip_initramfs"; 1065 #endif 1066 break; 1067 case ANDROID_BOOT_MODE_RECOVERY: 1068 /* In recovery mode we still boot the kernel from "boot" but 1069 * don't skip the initramfs so it boots to recovery. 1070 */ 1071 #ifndef CONFIG_ANDROID_AB 1072 boot_partname = ANDROID_PARTITION_RECOVERY; 1073 #endif 1074 break; 1075 case ANDROID_BOOT_MODE_BOOTLOADER: 1076 /* Bootloader mode enters fastboot. If this operation fails we 1077 * simply return since we can't recover from this situation by 1078 * switching to another slot. 1079 */ 1080 return android_bootloader_boot_bootloader(); 1081 } 1082 1083 #ifdef CONFIG_ANDROID_AVB 1084 uint8_t vboot_flag = 0; 1085 char vbmeta_partition[9] = {0}; 1086 disk_partition_t vbmeta_part_info; 1087 1088 if (trusty_read_vbootkey_enable_flag(&vboot_flag)) { 1089 printf("Can't read vboot flag\n"); 1090 return -1; 1091 } 1092 1093 if (vboot_flag) { 1094 printf("Vboot=1, SecureBoot enabled, AVB verify\n"); 1095 if (android_slot_verify(boot_partname, &load_address, 1096 slot_suffix)) { 1097 printf("AVB verify failed\n"); 1098 #ifdef CONFIG_ANDROID_AB 1099 printf("Reset in AB system.\n"); 1100 flushc(); 1101 /* 1102 * Since we use the retry-count in ab system, then can 1103 * try reboot if verify fail until the retry-count is 1104 * equal to zero. 1105 */ 1106 reset_cpu(0); 1107 #endif 1108 return -1; 1109 } 1110 } else { 1111 strcat(vbmeta_partition, ANDROID_PARTITION_VBMETA); 1112 strcat(vbmeta_partition, slot_suffix); 1113 part_num = part_get_info_by_name(dev_desc, vbmeta_partition, 1114 &vbmeta_part_info); 1115 if (part_num < 0) { 1116 printf("Not AVB images, AVB skip\n"); 1117 env_update("bootargs", 1118 "androidboot.verifiedbootstate=orange"); 1119 if (load_android_image(dev_desc, boot_partname, 1120 slot_suffix, &load_address)) { 1121 printf("Android image load failed\n"); 1122 return -1; 1123 } 1124 } else { 1125 printf("Vboot=0, AVB images, AVB verify\n"); 1126 if (android_slot_verify(boot_partname, &load_address, 1127 slot_suffix)) { 1128 printf("AVB verify failed\n"); 1129 #ifdef CONFIG_ANDROID_AB 1130 printf("Reset in AB system.\n"); 1131 flushc(); 1132 /* 1133 * Since we use the retry-count in ab system, 1134 * then can try reboot if verify fail until 1135 * the retry-count is equal to zero. 1136 */ 1137 reset_cpu(0); 1138 #endif 1139 return -1; 1140 } 1141 } 1142 } 1143 #else 1144 /* 1145 * 2. Load the boot/recovery from the desired "boot" partition. 1146 * Determine if this is an AOSP image. 1147 */ 1148 if (load_android_image(dev_desc, boot_partname, 1149 slot_suffix, &load_address)) { 1150 printf("Android image load failed\n"); 1151 return -1; 1152 } 1153 #endif 1154 1155 #ifdef CONFIG_ANDROID_AB 1156 /* In android a/b & avb process, the "root=" will be add which parameter 1157 * is in vbmeta.In linux a/b & avb process, the "root=" must be add by 1158 * follow code. To be compatible with the above two processes, test it 1159 * is necessary to add "root=". 1160 */ 1161 char root_partition[20] = {0}; 1162 char guid_buf[UUID_SIZE] = {0}; 1163 char root_partuuid[70] = "root=PARTUUID="; 1164 char *boot_args = env_get("bootargs"); 1165 1166 if (!strstr(boot_args, "root=")) { 1167 strcat(root_partition, ANDROID_PARTITION_SYSTEM); 1168 strcat(root_partition, slot_suffix); 1169 get_partition_unique_uuid(root_partition, guid_buf, UUID_SIZE); 1170 strcat(root_partuuid, guid_buf); 1171 env_update("bootargs", root_partuuid); 1172 } 1173 #endif 1174 1175 /* Set Android root variables. */ 1176 env_set_ulong("android_root_devnum", dev_desc->devnum); 1177 env_set("android_slotsufix", slot_suffix); 1178 1179 #ifdef CONFIG_FASTBOOT_OEM_UNLOCK 1180 /* read oem unlock status and attach to bootargs */ 1181 uint8_t unlock = 0; 1182 TEEC_Result result; 1183 char oem_unlock[OEM_UNLOCK_ARG_SIZE] = {0}; 1184 result = trusty_read_oem_unlock(&unlock); 1185 if (result) { 1186 printf("read oem unlock status with error : 0x%x\n", result); 1187 } else { 1188 snprintf(oem_unlock, OEM_UNLOCK_ARG_SIZE, "androidboot.oem_unlocked=%d", unlock); 1189 env_update("bootargs", oem_unlock); 1190 } 1191 #endif 1192 1193 /* Assemble the command line */ 1194 command_line = android_assemble_cmdline(slot_suffix, mode_cmdline); 1195 env_update("bootargs", command_line); 1196 1197 debug("ANDROID: bootargs: \"%s\"\n", command_line); 1198 1199 #ifdef CONFIG_SUPPORT_OEM_DTB 1200 if (android_bootloader_get_fdt(ANDROID_PARTITION_OEM, 1201 ANDROID_ARG_FDT_FILENAME)) { 1202 printf("Can not get the fdt data from oem!\n"); 1203 } 1204 #else 1205 ret = android_image_get_fdt((void *)load_address, &fdt_addr); 1206 if (!ret) 1207 env_set_hex("fdt_addr", fdt_addr); 1208 #endif 1209 android_bootloader_boot_kernel(load_address); 1210 1211 /* TODO: If the kernel doesn't boot mark the selected slot as bad. */ 1212 return -1; 1213 } 1214 1215 int android_avb_boot_flow(char *slot_suffix, unsigned long kernel_address) 1216 { 1217 struct blk_desc *dev_desc; 1218 disk_partition_t boot_part_info; 1219 int ret; 1220 dev_desc = rockchip_get_bootdev(); 1221 if (!dev_desc) { 1222 printf("%s: dev_desc is NULL!\n", __func__); 1223 return -1; 1224 } 1225 /* Load the kernel from the desired "boot" partition. */ 1226 android_part_get_info_by_name_suffix(dev_desc, 1227 ANDROID_PARTITION_BOOT, 1228 slot_suffix, &boot_part_info); 1229 ret = android_image_load(dev_desc, &boot_part_info, kernel_address, 1230 -1UL); 1231 if (ret < 0) 1232 return ret; 1233 android_bootloader_boot_kernel(kernel_address); 1234 1235 /* TODO: If the kernel doesn't boot mark the selected slot as bad. */ 1236 return -1; 1237 } 1238 1239 int android_boot_flow(unsigned long kernel_address) 1240 { 1241 struct blk_desc *dev_desc; 1242 disk_partition_t boot_part_info; 1243 int ret; 1244 dev_desc = rockchip_get_bootdev(); 1245 if (!dev_desc) { 1246 printf("%s: dev_desc is NULL!\n", __func__); 1247 return -1; 1248 } 1249 /* Load the kernel from the desired "boot" partition. */ 1250 part_get_info_by_name(dev_desc, ANDROID_PARTITION_BOOT, &boot_part_info); 1251 ret = android_image_load(dev_desc, &boot_part_info, kernel_address, 1252 -1UL); 1253 if (ret < 0) 1254 return ret; 1255 android_bootloader_boot_kernel(kernel_address); 1256 1257 /* TODO: If the kernel doesn't boot mark the selected slot as bad. */ 1258 return -1; 1259 } 1260