load_image.c 30 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053
  1. /* Copyright Statement:
  2. *
  3. * This software/firmware and related documentation ("MediaTek Software") are
  4. * protected under relevant copyright laws. The information contained herein
  5. * is confidential and proprietary to MediaTek Inc. and/or its licensors.
  6. * Without the prior written permission of MediaTek inc. and/or its licensors,
  7. * any reproduction, modification, use or disclosure of MediaTek Software,
  8. * and information contained herein, in whole or in part, shall be strictly prohibited.
  9. */
  10. /* MediaTek Inc. (C) 2015. All rights reserved.
  11. *
  12. * BY OPENING THIS FILE, RECEIVER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
  13. * THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
  14. * RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO RECEIVER ON
  15. * AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES,
  16. * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
  17. * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT.
  18. * NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE
  19. * SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR
  20. * SUPPLIED WITH THE MEDIATEK SOFTWARE, AND RECEIVER AGREES TO LOOK ONLY TO SUCH
  21. * THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. RECEIVER EXPRESSLY ACKNOWLEDGES
  22. * THAT IT IS RECEIVER'S SOLE RESPONSIBILITY TO OBTAIN FROM ANY THIRD PARTY ALL PROPER LICENSES
  23. * CONTAINED IN MEDIATEK SOFTWARE. MEDIATEK SHALL ALSO NOT BE RESPONSIBLE FOR ANY MEDIATEK
  24. * SOFTWARE RELEASES MADE TO RECEIVER'S SPECIFICATION OR TO CONFORM TO A PARTICULAR
  25. * STANDARD OR OPEN FORUM. RECEIVER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND
  26. * CUMULATIVE LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE,
  27. * AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE,
  28. * OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY RECEIVER TO
  29. * MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
  30. */
  31. #include <stdlib.h>
  32. #include <sys/types.h>
  33. #include <stdint.h>
  34. #include <video.h>
  35. #include <platform/partition.h>
  36. #include <platform/boot_mode.h>
  37. #include <platform/mt_reg_base.h>
  38. #include <platform/errno.h>
  39. #include <platform/verified_boot.h>
  40. #include <platform/sec_policy.h>
  41. #include <printf.h>
  42. #include <string.h>
  43. #include <malloc.h>
  44. #include <platform/mt_gpt.h>
  45. #include <platform/sec_status.h>
  46. #include <platform/sec_export.h>
  47. #include <platform/mtk_key.h>
  48. #include <target/cust_key.h>
  49. #include <bootimg.h>
  50. #include <part_interface.h>
  51. #include <part_status.h>
  52. #include <block_generic_interface.h>
  53. #include <target.h> // for target_get_scratch_address()
  54. #include <platform/sec_devinfo.h>
  55. #include <verified_boot_common.h>
  56. #include <boot_opt.h>
  57. #include <storage_api.h>
  58. #include <pal_typedefs.h>
  59. #include <pal_log.h>
  60. #define MODULE_NAME "LK_BOOT"
  61. #define BOOTIMG_DEF_PGSIZE (2 * 1024)
  62. #define UART_EARLY_CONSOLE_LEN 128
  63. //*********
  64. //* Notice : it's kernel start addr (and not include any debug header)
  65. uint32_t g_kmem_off = 0;
  66. //*********
  67. //* Notice : it's rootfs start addr (and not include any debug header)
  68. uint32_t g_rmem_off = 0;
  69. uint32_t g_pg_sz = BOOTIMG_DEF_PGSIZE;
  70. uint32_t g_bimg_sz = 0;
  71. uint32_t g_rcimg_sz = 0;
  72. uint32_t g_fcimg_sz = 0;
  73. int g_kimg_sz = 0;
  74. int g_rimg_sz = 0;
  75. extern BOOT_ARGUMENT *g_boot_arg;
  76. static struct bootimg_hdr *g_boot_hdr = NULL;
  77. extern bool cmdline_append(const char *append_string);
  78. extern void mtk_wdt_restart(void);
  79. static void append_maxcpus_parameter(void)
  80. {
  81. #if 1
  82. // This function is needed only when it is necessary to limit the
  83. // number of CPU cores during boot up for thermal reasons.
  84. char buf[16];
  85. int ret;
  86. dprintf(INFO,"[CPU SMP] Check eFuse value : 0x%x\n", get_devinfo_with_index(120));
  87. if (((get_devinfo_with_index(120)) & (0x1)) == 0)
  88. ret = sprintf(buf, "maxcpus=%d", 8);
  89. else
  90. ret = sprintf(buf, "maxcpus=%d", 4);
  91. if (ret < 0)
  92. dprintf(CRITICAL, "[%s] sprintf error %d\n", __func__, ret);
  93. cmdline_append(buf);
  94. #endif
  95. }
  96. /* the only possible boot state change here is green->red */
  97. int verified_boot_init(char *part_name, char *img_name)
  98. {
  99. int ret = 0;
  100. #ifdef MTK_SECURITY_SW_SUPPORT
  101. uint32_t policy_entry_idx = 0;
  102. uint32_t img_auth_required = 0;
  103. uint32_t img_vfy_time = 0;
  104. uint32_t bypass_ver_check = 0;
  105. #endif
  106. g_boot_state = BOOT_STATE_GREEN;
  107. #ifdef MTK_SECURITY_SW_SUPPORT
  108. /* please refer to the following website for verified boot flow */
  109. /* http://source.android.com/devices/tech/security/verifiedboot/verified-boot.html */
  110. img_vfy_time = get_timer(0);
  111. policy_entry_idx = get_policy_entry_idx(part_name);
  112. img_auth_required = get_vfy_policy(policy_entry_idx);
  113. if (img_auth_required) {
  114. mtk_wdt_restart();
  115. #ifdef MTK_SECURITY_OEM_WITH_DMCERT_ONLY_SUPPORT
  116. ret = (int)sec_img_auth_init(part_name, img_name, BYPASS_CERT_CHAIN_VERIFY);
  117. #else
  118. ret = (int)sec_img_auth_init(part_name, img_name, 0);
  119. #endif
  120. #ifdef MTK_SECURITY_YELLOW_STATE_SUPPORT
  121. if (ERR_RETRY_WITH_VERIFIED_BOOT == ret) {
  122. ret = 0;
  123. bypass_ver_check = 1;
  124. }
  125. #endif
  126. pal_log_info("[SBC] boot cert vfy(%d ms)\n",
  127. (uint32_t)get_timer(img_vfy_time));
  128. if (ret) {
  129. g_boot_state = BOOT_STATE_RED;
  130. ret = -1;
  131. goto end;
  132. }
  133. if (bypass_ver_check == 0) {
  134. #ifdef MTK_SECURITY_ANTI_ROLLBACK
  135. #ifdef MTK_SECURITY_OEM_WITH_DMCERT_ONLY_SUPPORT
  136. pal_log_info("[SBC] DMCERT: No anti-rollback support\n");
  137. #else
  138. ret = sec_rollback_check(1);
  139. if (ret) {
  140. g_boot_state = BOOT_STATE_RED;
  141. ret = -1;
  142. goto end;
  143. }
  144. #endif
  145. #endif
  146. }
  147. } else
  148. pal_log_info("[SBC] (%s, %s) cert vfy disabled\n", part_name, img_name);
  149. #endif
  150. end:
  151. ret = print_boot_state();
  152. if (ret)
  153. return ret;
  154. if (img_name == NULL)
  155. ret = show_warning("UNKNOWN");
  156. else
  157. ret = show_warning(img_name);
  158. if (ret)
  159. return ret;
  160. return ret;
  161. }
  162. int verified_boot_flow(char *img_name, uint32_t img_addr, uint32_t img_sz)
  163. {
  164. int ret = 0;
  165. #ifdef MTK_SECURITY_SW_SUPPORT
  166. uint32_t policy_entry_idx = 0;
  167. uint32_t img_auth_required = 0;
  168. uint32_t img_vfy_time = 0;
  169. int lock_state = 0;
  170. #endif
  171. if (g_boot_state == BOOT_STATE_RED)
  172. goto end;
  173. g_boot_state = BOOT_STATE_GREEN;
  174. /* loading boot image without verifying boot image header first would not
  175. become a security hole since initial load address is not specified by
  176. boot image header, boot image is loaded to an address specified by lk,
  177. and kernel and ramdisk will be relocated later after boot image
  178. verification is done. Need to consider whether boot image size will be
  179. too big so it overlaps with other important region. */
  180. /* if MTK_SECURITY_SW_SUPPORT is not defined, boot state is always green */
  181. #ifdef MTK_SECURITY_SW_SUPPORT
  182. /* please refer to the following website for verified boot flow */
  183. /* http://source.android.com/devices/tech/security/verifiedboot/verified-boot.html */
  184. ret = sec_query_device_lock(&lock_state);
  185. if (ret) {
  186. g_boot_state = BOOT_STATE_RED;
  187. goto end;
  188. }
  189. if (DEVICE_STATE_LOCKED == lock_state) {
  190. img_vfy_time = get_timer(0);
  191. policy_entry_idx = get_policy_entry_idx("boot");
  192. img_auth_required = get_vfy_policy(policy_entry_idx);
  193. if (img_auth_required) {
  194. mtk_wdt_restart();
  195. img_vfy_time = get_timer(0);
  196. #ifdef MTK_SECURITY_OEM_WITH_DMCERT_ONLY_SUPPORT
  197. ret = sec_img_auth_custom(img_addr, img_sz);
  198. if (ret)
  199. g_boot_state = BOOT_STATE_RED;
  200. else {
  201. ret = sec_oemkey_compare();
  202. if (ret)
  203. g_boot_state = BOOT_STATE_YELLOW;
  204. else
  205. g_boot_state = BOOT_STATE_GREEN;
  206. }
  207. #else
  208. ret = (int)sec_img_auth((uint8_t *)img_addr, img_sz);
  209. if (ret) {
  210. /* show public key on LCM and requires user confirmation to proceed */
  211. ret = sec_img_auth_custom((uint8_t *)img_addr, img_sz);
  212. if (0 == ret)
  213. g_boot_state = BOOT_STATE_YELLOW;
  214. else
  215. g_boot_state = BOOT_STATE_RED;
  216. }
  217. #endif
  218. pal_log_info("[SBC] img vfy(%d ms)\n", (uint32_t)get_timer(img_vfy_time));
  219. } else
  220. pal_log_err("[SBC] img vfy disabled\n");
  221. } else if (DEVICE_STATE_UNLOCKED == lock_state)
  222. g_boot_state = BOOT_STATE_ORANGE;
  223. else /* unknown lock state*/
  224. g_boot_state = BOOT_STATE_RED;
  225. #endif //MTK_SECURITY_SW_SUPPORT
  226. end:
  227. ret = print_boot_state();
  228. if (ret)
  229. return ret;
  230. if (img_name == NULL)
  231. ret = show_warning("UNKNOWN");
  232. else
  233. ret = show_warning(img_name);
  234. if (ret)
  235. return ret;
  236. ret = set_boot_state_to_cmdline();
  237. if (ret)
  238. return ret;
  239. return ret;
  240. }
  241. static int mboot_common_load_part_info(char *part_name,
  242. char *img_name, part_hdr_t *part_hdr, uint64_t *img_start_addr)
  243. {
  244. long len;
  245. u64 offset, part_size;
  246. if (partition_exists(part_name) == PART_NOT_EXIST)
  247. return -ENOENT;
  248. part_size = partition_get_size_by_name(part_name);
  249. offset = 0;
  250. //***************
  251. //* read partition header
  252. //*
  253. while (1) {
  254. len = partition_read(part_name, offset, (uchar *)part_hdr, sizeof(part_hdr_t));
  255. if (len < 0) {
  256. pal_log_err("[%s] %s partition read error. LINE: %d\n", MODULE_NAME,
  257. part_name, __LINE__);
  258. break;
  259. }
  260. pal_log_err("\n=========================================\n");
  261. pal_log_err("[%s] %s magic number : 0x%x\n", MODULE_NAME, part_name,
  262. part_hdr->info.magic);
  263. part_hdr->info.name[31] = '\0'; //append end char
  264. pal_log_err("[%s] %s name : %s\n", MODULE_NAME, part_name,
  265. part_hdr->info.name);
  266. pal_log_err("[%s] %s size : %d\n", MODULE_NAME, part_name,
  267. part_hdr->info.dsize);
  268. pal_log_err("=========================================\n");
  269. //***************
  270. //* check partition magic
  271. //*
  272. if (part_hdr->info.magic != PART_MAGIC) {
  273. pal_log_err("[%s] %s partition magic error\n", MODULE_NAME, part_name);
  274. len = -1;
  275. break;
  276. }
  277. offset += sizeof(part_hdr_t);
  278. //***************
  279. //* check partition data size
  280. //*
  281. if ((offset + part_hdr->info.dsize) > part_size) {
  282. pal_log_err("[%s] %s partition size error 0x%llx, 0x%llx\n", MODULE_NAME,
  283. part_name, offset + part_hdr->info.dsize, part_size);
  284. len = -1;
  285. break;
  286. }
  287. //***************
  288. //* check image name
  289. //*
  290. if (!strncasecmp(part_hdr->info.name, img_name, sizeof(part_hdr->info.name))) {
  291. pal_log_info("[%s] %s image name found\n", MODULE_NAME, img_name);
  292. break;
  293. }
  294. //***************
  295. //* find next image
  296. //* image with new layout will align to a specific size
  297. //*
  298. if (part_hdr->info.ext_magic == PART_EXT_MAGIC)
  299. offset += ROUNDUP(part_hdr->info.dsize, part_hdr->info.align_size);
  300. else
  301. offset += part_hdr->info.dsize;
  302. }
  303. if (len > 0)
  304. *img_start_addr = offset;
  305. return len;
  306. }
  307. /**********************************************************
  308. * Routine: mboot_common_load_part
  309. *
  310. * Description: common function for loading image from nand flash
  311. * this function is called by
  312. * (1) 'mboot_common_load_logo' to display logo
  313. *
  314. **********************************************************/
  315. int mboot_common_load_part(char *part_name, char *img_name, uint32_t addr)
  316. {
  317. long len;
  318. uint64_t start_addr = 0;
  319. part_hdr_t *part_hdr;
  320. if (partition_exists(part_name) == PART_NOT_EXIST)
  321. return -ENOENT;
  322. part_hdr = (part_hdr_t *)malloc(sizeof(part_hdr_t));
  323. if (!part_hdr)
  324. return -ENOMEM;
  325. len = mboot_common_load_part_info(part_name, img_name, part_hdr,
  326. &start_addr);
  327. if (len < 0) {
  328. len = -EINVAL;
  329. goto exit;
  330. }
  331. //****************
  332. //* read image data
  333. //*
  334. pal_log_info("read the data of %s\n", part_name);
  335. len = partition_read(part_name, start_addr, (uchar *)addr,
  336. (size_t)part_hdr->info.dsize);
  337. if (len < 0) {
  338. len = -EIO;
  339. goto exit;
  340. }
  341. exit:
  342. if (part_hdr)
  343. free(part_hdr);
  344. return len;
  345. }
  346. /**********************************************************
  347. * Routine: mboot_common_load_logo
  348. *
  349. * Description: function to load logo to display
  350. *
  351. **********************************************************/
  352. int mboot_common_load_logo(uint32_t logo_addr, char *filename)
  353. {
  354. int ret;
  355. #if (CONFIG_COMMANDS & CFG_CMD_FAT)
  356. long len;
  357. #endif
  358. #if (CONFIG_COMMANDS & CFG_CMD_FAT)
  359. len = file_fat_read(filename, (uint8_t *)logo_addr, 0);
  360. if (len > 0)
  361. return (int)len;
  362. #endif
  363. ret = mboot_common_load_part("logo", "logo", logo_addr);
  364. return ret;
  365. }
  366. /**********************************************************
  367. * Routine: mboot_android_check_img_info
  368. *
  369. * Description: this function is called to
  370. * (1) check the header of kernel / rootfs
  371. *
  372. * Notice : this function will be called by 'mboot_android_check_bootimg_hdr'
  373. *
  374. **********************************************************/
  375. int mboot_android_check_img_info(char *part_name, part_hdr_t *part_hdr)
  376. {
  377. //***************
  378. //* check partition magic
  379. //*
  380. if (part_hdr->info.magic != PART_MAGIC) {
  381. pal_log_err("[%s] %s partition magic not match\n", MODULE_NAME,
  382. part_name);
  383. return -1;
  384. }
  385. //***************
  386. //* check partition name
  387. //*
  388. if (strncasecmp(part_hdr->info.name, part_name, sizeof(part_hdr->info.name))) {
  389. pal_log_err("[%s] %s partition name not match\n", MODULE_NAME, part_name);
  390. return -1;
  391. }
  392. pal_log_err("\n=========================================\n");
  393. pal_log_err("[%s] %s magic number : 0x%x\n", MODULE_NAME, part_name,
  394. part_hdr->info.magic);
  395. pal_log_err("[%s] %s size : 0x%x\n", MODULE_NAME, part_name,
  396. part_hdr->info.dsize);
  397. pal_log_err("=========================================\n");
  398. //***************
  399. //* return the image size
  400. //*
  401. return part_hdr->info.dsize;
  402. }
  403. /**********************************************************
  404. * Routine: mboot_android_check_bootimg_hdr
  405. *
  406. * Description: this function is called to
  407. * (1) 'read' the header of boot image from nand flash
  408. * (2) 'parse' the header of boot image to obtain
  409. * - (a) kernel image size
  410. * - (b) rootfs image size
  411. * - (c) rootfs offset
  412. *
  413. * Notice : this function must be read first when doing nand / msdc boot
  414. *
  415. **********************************************************/
  416. static int mboot_android_check_bootimg_hdr(char *part_name,
  417. struct bootimg_hdr *boot_hdr)
  418. {
  419. long len;
  420. int ret = 0;
  421. u64 addr;
  422. uint32_t k_pg_cnt = 0;
  423. uint32_t r_pg_cnt = 0;
  424. uint32_t dtbo_pg_cnt = 0;
  425. uint32_t dt_pg_cnt = 0;
  426. uint32_t pg_sz;
  427. if (partition_exists(part_name) == PART_NOT_EXIST)
  428. return -1;
  429. addr = partition_get_offset_by_name(part_name);
  430. //***************
  431. //* read partition header
  432. //*
  433. pal_log_err("part page addr is 0x%llx\n", addr);
  434. len = partition_read(part_name, 0, (uchar *) boot_hdr,
  435. sizeof(struct bootimg_hdr));
  436. if (len < 0) {
  437. pal_log_err("[%s] %s boot image header read error. LINE: %d\n",
  438. MODULE_NAME, part_name, __LINE__);
  439. return -1;
  440. }
  441. pal_log_err("\n============================================================\n");
  442. pal_log_err("[%s] Android Partition Name : %s\n",
  443. MODULE_NAME, part_name);
  444. pal_log_err("[%s] Android Boot IMG Hdr - Kernel Size : 0x%08X\n",
  445. MODULE_NAME, boot_hdr->kernel_sz);
  446. pal_log_err("[%s] Android Boot IMG Hdr - Kernel Address : 0x%08X\n",
  447. MODULE_NAME, boot_hdr->kernel_addr);
  448. pal_log_err("[%s] Android Boot IMG Hdr - Rootfs Size : 0x%08X\n",
  449. MODULE_NAME, boot_hdr->ramdisk_sz);
  450. pal_log_err("[%s] Android Boot IMG Hdr - Rootfs Address : 0x%08X\n",
  451. MODULE_NAME, boot_hdr->ramdisk_addr);
  452. pal_log_err("[%s] Android Boot IMG Hdr - Tags Address : 0x%08X\n",
  453. MODULE_NAME, boot_hdr->tags_addr);
  454. pal_log_err("[%s] Android Boot IMG Hdr - Page Size : 0x%08X\n",
  455. MODULE_NAME, boot_hdr->page_sz);
  456. pal_log_err("[%s] Android Boot IMG Hdr - Command Line : %s\n",
  457. MODULE_NAME, boot_hdr->cmdline);
  458. pal_log_err("\n============================================================\n");
  459. //***************
  460. //* check partition magic
  461. //*
  462. if (strncmp((char const *)boot_hdr->magic, BOOTIMG_MAGIC,
  463. BOOTIMG_MAGIC_SZ) != 0) {
  464. pal_log_err("[%s] boot image header magic error\n", MODULE_NAME);
  465. return -1;
  466. }
  467. pg_sz = boot_hdr->page_sz;
  468. g_pg_sz = boot_hdr->page_sz;
  469. //***************
  470. //* follow bootimg.h to calculate the location of rootfs
  471. //*
  472. if (len != -1) {
  473. if (g_is_64bit_kernel)
  474. g_kmem_off = (uint32_t)target_get_scratch_address();
  475. else
  476. g_kmem_off = boot_hdr->kernel_addr;
  477. k_pg_cnt = (boot_hdr->kernel_sz + (pg_sz - 1)) / pg_sz;
  478. r_pg_cnt = (boot_hdr->ramdisk_sz + (pg_sz - 1)) / pg_sz;
  479. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_ONE)
  480. dtbo_pg_cnt = (boot_hdr->recovery_dtbo_size + (pg_sz - 1)) / pg_sz;
  481. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_TWO)
  482. dt_pg_cnt = (boot_hdr->dtb_size + (pg_sz - 1)) / pg_sz;
  483. pal_log_info(" > page count of kernel image = %d\n", k_pg_cnt);
  484. g_rmem_off = g_kmem_off + k_pg_cnt * pg_sz;
  485. pal_log_info(" > kernel mem offset = 0x%x\n", g_kmem_off);
  486. pal_log_info(" > rootfs mem offset = 0x%x\n", g_rmem_off);
  487. //***************
  488. //* specify boot image size
  489. //*
  490. g_bimg_sz = (k_pg_cnt + r_pg_cnt + dtbo_pg_cnt + dt_pg_cnt + 1) * pg_sz;
  491. pal_log_info(" > boot image size = 0x%x\n", g_bimg_sz);
  492. }
  493. ret = verified_boot_init("boot", "boot");
  494. if (ret)
  495. return ret;
  496. return 0;
  497. }
  498. /**********************************************************
  499. * Routine: mboot_android_check_recoveryimg_hdr
  500. *
  501. * Description: this function is called to
  502. * (1) 'read' the header of boot image from nand flash
  503. * (2) 'parse' the header of boot image to obtain
  504. * - (a) kernel image size
  505. * - (b) rootfs image size
  506. * - (c) rootfs offset
  507. *
  508. * Notice : this function must be read first when doing nand / msdc boot
  509. *
  510. **********************************************************/
  511. static int mboot_android_check_recoveryimg_hdr(char *part_name,
  512. struct bootimg_hdr *boot_hdr)
  513. {
  514. int ret = 0;
  515. long len;
  516. uint32_t k_pg_cnt = 0;
  517. uint32_t r_pg_cnt = 0;
  518. uint32_t dtbo_pg_cnt = 0;
  519. uint32_t dt_pg_cnt = 0;
  520. uint32_t pg_sz;
  521. if (partition_exists(part_name) == PART_NOT_EXIST)
  522. return -1;
  523. //***************
  524. //* read partition header
  525. //*
  526. len = partition_read(part_name, 0, (uchar *) boot_hdr,
  527. sizeof(struct bootimg_hdr));
  528. if (len < 0) {
  529. pal_log_err("[%s] %s Recovery image header read error. LINE: %d\n",
  530. MODULE_NAME, part_name, __LINE__);
  531. return -1;
  532. }
  533. pal_log_err("\n============================================================\n");
  534. pal_log_err("[%s] Android Recovery IMG Hdr - Kernel Size : 0x%08X\n",
  535. MODULE_NAME, boot_hdr->kernel_sz);
  536. pal_log_err("[%s] Android Recovery IMG Hdr - Kernel Address : 0x%08X\n",
  537. MODULE_NAME, boot_hdr->kernel_addr);
  538. pal_log_err("[%s] Android Recovery IMG Hdr - Rootfs Size : 0x%08X\n",
  539. MODULE_NAME, boot_hdr->ramdisk_sz);
  540. pal_log_err("[%s] Android Recovery IMG Hdr - Rootfs Address : 0x%08X\n",
  541. MODULE_NAME, boot_hdr->ramdisk_addr);
  542. pal_log_err("[%s] Android Recovery IMG Hdr - Tags Address : 0x%08X\n",
  543. MODULE_NAME, boot_hdr->tags_addr);
  544. pal_log_err("[%s] Android Recovery IMG Hdr - Page Size : 0x%08X\n",
  545. MODULE_NAME, boot_hdr->page_sz);
  546. pal_log_err("[%s] Android Recovery IMG Hdr - Command Line : %s\n",
  547. MODULE_NAME, boot_hdr->cmdline);
  548. pal_log_err("\n============================================================\n");
  549. //***************
  550. //* check partition magic
  551. //*
  552. if (strncmp((char const *)boot_hdr->magic, BOOTIMG_MAGIC,
  553. BOOTIMG_MAGIC_SZ) != 0) {
  554. pal_log_err("[%s] Recovery image header magic error\n", MODULE_NAME);
  555. return -1;
  556. }
  557. pg_sz = boot_hdr->page_sz;
  558. g_pg_sz = boot_hdr->page_sz;
  559. //***************
  560. //* follow bootimg.h to calculate the location of rootfs
  561. //*
  562. if (len != -1) {
  563. if (g_is_64bit_kernel)
  564. g_kmem_off = (uint32_t)target_get_scratch_address();
  565. else
  566. g_kmem_off = boot_hdr->kernel_addr;
  567. k_pg_cnt = (boot_hdr->kernel_sz + (pg_sz - 1)) / pg_sz;
  568. r_pg_cnt = (boot_hdr->ramdisk_sz + (pg_sz - 1)) / pg_sz;
  569. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_ONE)
  570. dtbo_pg_cnt = (boot_hdr->recovery_dtbo_size + (pg_sz - 1)) / pg_sz;
  571. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_TWO)
  572. dt_pg_cnt = (boot_hdr->dtb_size+ (pg_sz - 1)) / pg_sz;
  573. pal_log_info(" > page count of kernel image = %d\n", k_pg_cnt);
  574. g_rmem_off = g_kmem_off + k_pg_cnt * pg_sz;
  575. pal_log_info(" > kernel mem offset = 0x%x\n", g_kmem_off);
  576. pal_log_info(" > rootfs mem offset = 0x%x\n", g_rmem_off);
  577. //***************
  578. //* specify boot image size
  579. //*
  580. //g_rcimg_sz = part->start_sect * dev->blkdev->blksz;
  581. g_rcimg_sz = (k_pg_cnt + r_pg_cnt + dtbo_pg_cnt + dt_pg_cnt + 1) * pg_sz;
  582. pal_log_info(" > Recovery image size = 0x%x\n", g_rcimg_sz);
  583. }
  584. ret = verified_boot_init("recovery", "recovery");
  585. if (ret)
  586. return ret;
  587. return 0;
  588. }
  589. /**********************************************************
  590. * Routine: mboot_android_load_bootimg_hdr
  591. *
  592. * Description: this is the entry function to handle boot image header
  593. *
  594. **********************************************************/
  595. int mboot_android_load_bootimg_hdr(char *part_name, uint32_t addr)
  596. {
  597. long len;
  598. struct bootimg_hdr *boot_hdr;
  599. append_maxcpus_parameter();
  600. if (partition_exists(part_name) == PART_NOT_EXIST) {
  601. pal_log_err("mboot_android_load_bootimg_hdr (%s), part = NULL\n",
  602. part_name);
  603. return -ENOENT;
  604. }
  605. boot_hdr = (struct bootimg_hdr *)malloc(sizeof(struct bootimg_hdr));
  606. if (!boot_hdr) {
  607. pal_log_err("mboot_android_load_bootimg_hdr, boot_hdr = NULL\n");
  608. return -ENOMEM;
  609. }
  610. g_boot_hdr = boot_hdr;
  611. len = mboot_android_check_bootimg_hdr(part_name, boot_hdr);
  612. platform_parse_bootopt(boot_hdr->cmdline);
  613. return len;
  614. }
  615. /**********************************************************
  616. * Routine: mboot_android_load_recoveryimg_hdr
  617. *
  618. * Description: this is the entry function to handle Recovery image header
  619. *
  620. **********************************************************/
  621. int mboot_android_load_recoveryimg_hdr(char *part_name, uint32_t addr)
  622. {
  623. long len;
  624. struct bootimg_hdr *boot_hdr;
  625. if (partition_exists(part_name) == PART_NOT_EXIST) {
  626. pal_log_err("mboot_android_load_recoveryimg_hdr (%s), part = NULL\n",
  627. part_name);
  628. return -ENOENT;
  629. }
  630. boot_hdr = (struct bootimg_hdr *)malloc(sizeof(struct bootimg_hdr));
  631. if (!boot_hdr) {
  632. pal_log_err("mboot_android_load_bootimg_hdr, boot_hdr = NULL\n");
  633. return -ENOMEM;
  634. }
  635. g_boot_hdr = boot_hdr;
  636. len = mboot_android_check_recoveryimg_hdr(part_name, boot_hdr);
  637. return len;
  638. }
  639. /**********************************************************
  640. * Routine: mboot_android_load_bootimg
  641. *
  642. * Description: main function to load Android Boot Image
  643. *
  644. **********************************************************/
  645. int mboot_android_load_bootimg(char *part_name, uint32_t addr)
  646. {
  647. int ret = 0;
  648. long len;
  649. uint64_t start_addr;
  650. if (partition_exists(part_name) == PART_NOT_EXIST) {
  651. pal_log_err("mboot_android_load_bootimg , part = NULL\n");
  652. return -ENOENT;
  653. }
  654. //***************
  655. //* not to include unused header
  656. //*
  657. start_addr = partition_get_offset_by_name(part_name);
  658. /*
  659. * check mkimg header
  660. */
  661. pal_log_info("check mkimg header\n");
  662. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  663. MKIMG_HEADER_SZ);
  664. if (len < 0) {
  665. pal_log_err("[%s] %s partition read error. LINE: %d\n", MODULE_NAME,
  666. part_name, __LINE__);
  667. return -EIO;
  668. }
  669. // check kernel header
  670. g_kimg_sz = mboot_android_check_img_info(PART_KERNEL, (part_hdr_t *)addr);
  671. if (g_kimg_sz == -1)
  672. pal_log_info("no mkimg header in kernel image\n");
  673. else {
  674. pal_log_info("mkimg header exist in kernel image\n");
  675. addr = addr - MKIMG_HEADER_SZ;
  676. g_rmem_off = g_rmem_off - MKIMG_HEADER_SZ;
  677. }
  678. //***************
  679. //* read image data
  680. //*
  681. pal_log_info("read the data of %s (size = 0x%x)\n", part_name, g_bimg_sz);
  682. pal_log_info(" > from - 0x%016llx (skip boot img hdr)\n", start_addr);
  683. pal_log_info(" > to - 0x%x (starts with kernel img hdr)\n",
  684. (uint32_t)addr);
  685. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  686. (size_t)g_bimg_sz);
  687. // check ramdisk/rootfs header
  688. g_rimg_sz = mboot_android_check_img_info(PART_ROOTFS, (part_hdr_t *)g_rmem_off);
  689. if (g_rimg_sz == -1) {
  690. pal_log_info("no mkimg header in ramdisk image\n");
  691. g_rimg_sz = g_boot_hdr->ramdisk_sz;
  692. } else {
  693. pal_log_info("mkimg header exist in ramdisk image\n");
  694. g_rmem_off = g_rmem_off + MKIMG_HEADER_SZ;
  695. }
  696. if (len < 0) {
  697. len = -EIO;
  698. return len;
  699. }
  700. ret = verified_boot_flow("boot", addr, g_bimg_sz - g_pg_sz);
  701. if (ret)
  702. len = -EIO;
  703. return len;
  704. }
  705. /**********************************************************
  706. * Routine: mboot_android_load_recoveryimg
  707. *
  708. * Description: main function to load Android Recovery Image
  709. *
  710. **********************************************************/
  711. int mboot_android_load_recoveryimg(char *part_name, uint32_t addr)
  712. {
  713. int ret = 0;
  714. long len;
  715. uint64_t start_addr;
  716. if (partition_exists(part_name) == PART_NOT_EXIST) {
  717. pal_log_err("mboot_android_load_bootimg , part = NULL\n");
  718. return -ENOENT;
  719. }
  720. //***************
  721. //* not to include unused header
  722. //*
  723. start_addr = partition_get_offset_by_name(part_name);
  724. /*
  725. * check mkimg header
  726. */
  727. pal_log_info("check mkimg header\n");
  728. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  729. MKIMG_HEADER_SZ);
  730. if (len < 0) {
  731. pal_log_err("[%s] %s partition read error. LINE: %d\n", MODULE_NAME,
  732. part_name, __LINE__);
  733. return -EIO;
  734. }
  735. // check kernel header
  736. g_kimg_sz = mboot_android_check_img_info(PART_KERNEL, (part_hdr_t *)addr);
  737. if (g_kimg_sz == -1)
  738. pal_log_info("no mkimg header in kernel image\n");
  739. else {
  740. pal_log_info("mkimg header exist in kernel image\n");
  741. addr = addr - MKIMG_HEADER_SZ;
  742. g_rmem_off = g_rmem_off - MKIMG_HEADER_SZ;
  743. }
  744. //***************
  745. //* read image data
  746. //*
  747. pal_log_info("\nread the data of %s (size = 0x%x)\n", part_name, g_rcimg_sz);
  748. pal_log_info(" > from - 0x%016llx (skip recovery img hdr)\n", start_addr);
  749. pal_log_info(" > to - 0x%x (starts with kernel img hdr)\n",
  750. (uint32_t)addr);
  751. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  752. (size_t)g_rcimg_sz);
  753. // check ramdisk/rootfs header
  754. g_rimg_sz = mboot_android_check_img_info("recovery", (part_hdr_t *)g_rmem_off);
  755. if (g_rimg_sz == -1) {
  756. pal_log_info("no mkimg header in recovery image\n");
  757. g_rimg_sz = g_boot_hdr->ramdisk_sz;
  758. } else {
  759. pal_log_info("mkimg header exist in recovery image\n");
  760. g_rmem_off = g_rmem_off + MKIMG_HEADER_SZ;
  761. }
  762. if (len < 0) {
  763. len = -EIO;
  764. return len;
  765. }
  766. ret = verified_boot_flow("recovery", addr, g_rcimg_sz - g_pg_sz);
  767. if (ret)
  768. len = -EIO;
  769. return len;
  770. }
  771. /**********************************************************
  772. * Routine: mboot_recovery_load_raw_part
  773. *
  774. * Description: load raw data for recovery mode support
  775. *
  776. **********************************************************/
  777. int mboot_recovery_load_raw_part(char *part_name, uint32_t *addr,
  778. uint32_t size)
  779. {
  780. long len;
  781. uint32_t begin;
  782. if (partition_exists(part_name) == PART_NOT_EXIST)
  783. return -ENOENT;
  784. begin = get_timer(0);
  785. len = partition_read(part_name, 0, (uchar *)addr, (size_t)size);
  786. if (len < 0) {
  787. len = -EIO;
  788. goto exit;
  789. }
  790. pal_log_err("[%s] Load '%s' partition to 0x%08x (%d bytes in %ld ms)\n",
  791. MODULE_NAME, part_name, (uint32_t)addr, size, get_timer(begin));
  792. exit:
  793. return len;
  794. }
  795. /**********************************************************
  796. * Routine: mboot_recovery_load_raw_part_offset
  797. *
  798. * Description: load partition raw data with offset
  799. *
  800. **********************************************************/
  801. int mboot_recovery_load_raw_part_offset(char *part_name, uint32_t *addr,
  802. uint32_t offset, uint32_t size)
  803. {
  804. long len;
  805. uint32_t begin;
  806. begin = get_timer(0);
  807. len = partition_read(part_name, offset, (uchar *)addr, (size_t)size);
  808. if (len < 0) {
  809. len = -EIO;
  810. goto exit;
  811. }
  812. pal_log_info("[%s] Load '%s' partition to 0x%08x (%d bytes in %ld ms)\n",
  813. MODULE_NAME, part_name, (uint32_t)addr, size, get_timer(begin));
  814. exit:
  815. return len;
  816. }
  817. /**********************************************************
  818. * Routine: mboot_recovery_load_misc
  819. *
  820. * Description: load recovery command
  821. *
  822. **********************************************************/
  823. int mboot_recovery_load_misc(uint32_t *misc_addr, uint32_t size)
  824. {
  825. int ret;
  826. pal_log_info("[mboot_recovery_load_misc]: size is %u\n", size);
  827. pal_log_info("[mboot_recovery_load_misc]: misc_addr is 0x%x\n",
  828. (uint32_t)misc_addr);
  829. ret = mboot_recovery_load_raw_part("para", misc_addr, size);
  830. if (ret < 0)
  831. return ret;
  832. return ret;
  833. }
  834. uint32_t mboot_get_img_size(char *part_name, uint32_t *size)
  835. {
  836. int ret = 0;
  837. long len = 0;
  838. struct bootimg_hdr boot_hdr;
  839. uint16_t page_sz;
  840. *size = 0;
  841. if (partition_exists(part_name) == PART_NOT_EXIST) {
  842. pal_log_err("mboot_android_load_img_hdr (%s), part = NULL\n", part_name);
  843. return -ENOENT;
  844. }
  845. len = partition_read(part_name, (off_t)0, (uchar *)&boot_hdr,
  846. sizeof(struct bootimg_hdr));
  847. if (len < 0) {
  848. pal_log_err("[%s] %s boot image header read error. LINE: %d\n",
  849. MODULE_NAME, part_name, __LINE__);
  850. return -1;
  851. }
  852. boot_hdr.magic[7] = '\0';
  853. pal_log_err("\n============================================================\n");
  854. pal_log_err("[%s] Android Partition Name : %s\n", MODULE_NAME,
  855. part_name);
  856. pal_log_err("[%s] Android IMG Hdr - Magic : %s\n", MODULE_NAME,
  857. boot_hdr.magic);
  858. pal_log_err("[%s] Android IMG Hdr - Kernel Size : 0x%08X\n",
  859. MODULE_NAME, boot_hdr.kernel_sz);
  860. pal_log_err("[%s] Android IMG Hdr - Kernel Address : 0x%08X\n",
  861. MODULE_NAME, boot_hdr.kernel_addr);
  862. pal_log_err("[%s] Android IMG Hdr - Rootfs Size : 0x%08X\n",
  863. MODULE_NAME, boot_hdr.ramdisk_sz);
  864. pal_log_err("[%s] Android IMG Hdr - Rootfs Address : 0x%08X\n",
  865. MODULE_NAME, boot_hdr.ramdisk_addr);
  866. pal_log_err("[%s] Android IMG Hdr - Tags Address : 0x%08X\n",
  867. MODULE_NAME, boot_hdr.tags_addr);
  868. pal_log_err("[%s] Android IMG Hdr - Page Size : 0x%08X\n",
  869. MODULE_NAME, boot_hdr.page_sz);
  870. pal_log_err("[%s] Android IMG Hdr - Command Line : %s\n", MODULE_NAME,
  871. boot_hdr.cmdline);
  872. pal_log_err("\n============================================================\n");
  873. page_sz = boot_hdr.page_sz;
  874. *size += page_sz; /* boot header size is 1 page*/
  875. *size += (((boot_hdr.kernel_sz + page_sz - 1) / page_sz) * page_sz);
  876. *size += (((boot_hdr.ramdisk_sz + page_sz - 1) / page_sz) * page_sz);
  877. *size += (((boot_hdr.second_sz + page_sz - 1) / page_sz) * page_sz);
  878. if (boot_hdr.header_version >= BOOT_HEADER_VERSION_ONE)
  879. *size += (((boot_hdr.recovery_dtbo_size + page_sz - 1) / page_sz) * page_sz);
  880. if (boot_hdr.header_version >= BOOT_HEADER_VERSION_TWO)
  881. *size += (((boot_hdr.dtb_size + page_sz - 1) / page_sz) * page_sz);
  882. return ret;
  883. }