load_image.c 30 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030
  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/mt_typedefs.h>
  37. #include <platform/boot_mode.h>
  38. #include <platform/mt_reg_base.h>
  39. #include <platform/errno.h>
  40. #include <platform/verified_boot.h>
  41. #include <platform/sec_policy.h>
  42. #include <printf.h>
  43. #include <string.h>
  44. #include <malloc.h>
  45. #include <platform/mt_gpt.h>
  46. #include <platform/sec_status.h>
  47. #include <platform/sec_export.h>
  48. #include <platform/mtk_key.h>
  49. #include <target/cust_key.h>
  50. #include <bootimg.h>
  51. #include <part_interface.h>
  52. #include <block_generic_interface.h> // for mt_part_get_device()
  53. #include <target.h> // for target_get_scratch_address()
  54. #include <verified_boot_common.h>
  55. #include <boot_opt.h>
  56. #define MODULE_NAME "LK_BOOT"
  57. #define BOOTIMG_DEF_PGSIZE (2 * 1024)
  58. // ************************************************************************
  59. #define PUBK_LEN 256
  60. #define BOOT_STATE_GREEN 0x0
  61. #define BOOT_STATE_ORANGE 0x1
  62. #define BOOT_STATE_YELLOW 0x2
  63. #define BOOT_STATE_RED 0x3
  64. #define DEVICE_STATE_UNLOCKED 0x0
  65. #define DEVICE_STATE_LOCKED 0x1
  66. #define UART_EARLY_CONSOLE_LEN 128
  67. //*********
  68. //* Notice : it's kernel start addr (and not include any debug header)
  69. unsigned int g_kmem_off = 0;
  70. //*********
  71. //* Notice : it's rootfs start addr (and not include any debug header)
  72. unsigned int g_rmem_off = 0;
  73. unsigned int g_pg_sz = BOOTIMG_DEF_PGSIZE;
  74. unsigned int g_bimg_sz = 0;
  75. unsigned int g_rcimg_sz = 0;
  76. unsigned int g_fcimg_sz = 0;
  77. int g_kimg_sz = 0;
  78. int g_rimg_sz = 0;
  79. extern struct bootimg_hdr *g_boot_hdr;
  80. extern BOOT_ARGUMENT *g_boot_arg;
  81. extern bool cmdline_append(const char *append_string);
  82. extern void platform_parse_bootopt(u8 *bootopt_str);
  83. #ifdef TRUSTONIC_TEE_SUPPORT
  84. extern void root_status_check(u32 sec_boot_check);
  85. #endif
  86. extern void mtk_wdt_restart(void);
  87. int imgver_not_sync_warning(int v1, int v2)
  88. {
  89. if (v1 == ERR_IMAGE_IMG_VER_NOT_SYNC || v2 == ERR_IMAGE_IMG_VER_NOT_SYNC) {
  90. video_clean_screen();
  91. video_set_cursor(video_get_rows() / 2, 0);
  92. if (v1 == ERR_IMAGE_IMG_VER_NOT_SYNC)
  93. video_printf("prelaoder stage img ver not sync\n\n");
  94. if (v2 == ERR_IMAGE_IMG_VER_NOT_SYNC)
  95. video_printf("lk stage img ver not sync\n\n");
  96. video_printf("OTP counter will not update\n");
  97. video_printf("Your device will boot in 5 seconds\n");
  98. mtk_wdt_restart();
  99. mdelay(5000);
  100. mtk_wdt_restart();
  101. }
  102. return 0;
  103. }
  104. static void append_maxcpus_parameter(void)
  105. {
  106. char buf[16];
  107. sprintf(buf, "maxcpus=%d", g_boot_arg->max_cpus);
  108. cmdline_append(buf);
  109. }
  110. /* the only possible boot state change here is green->red */
  111. int verified_boot_init(char *part_name, char *img_name)
  112. {
  113. int ret = 0;
  114. unsigned int policy_entry_idx = 0;
  115. unsigned int img_auth_required = 0;
  116. unsigned int img_vfy_time = 0;
  117. unsigned int sec_feature_mask = 0;
  118. g_boot_state = BOOT_STATE_GREEN;
  119. #ifdef MTK_SECURITY_SW_SUPPORT
  120. /* please refer to the following website for verified boot flow */
  121. /* http://source.android.com/devices/tech/security/verifiedboot/verified-boot.html */
  122. img_vfy_time = get_timer(0);
  123. policy_entry_idx = get_policy_entry_idx(part_name);
  124. img_auth_required = get_vfy_policy(policy_entry_idx);
  125. if (img_auth_required) {
  126. #ifdef MTK_SECURITY_ANTI_ROLLBACK
  127. sec_feature_mask |= SEC_FEATURE_MASK_ANTIROLLBACK;
  128. #endif
  129. ret = (int)sec_img_auth_init(part_name, img_name, sec_feature_mask);
  130. #ifdef MTK_SECURITY_YELLOW_STATE_SUPPORT
  131. if (ERR_RETRY_WITH_VERIFIED_BOOT == ret)
  132. ret = 0;
  133. #endif
  134. dprintf(INFO, "[SBC] boot cert vfy(%d ms)\n",
  135. (unsigned int)get_timer(img_vfy_time));
  136. if (ret) {
  137. g_boot_state = BOOT_STATE_RED;
  138. ret = -1;
  139. }
  140. #ifdef MTK_SECURITY_ANTI_ROLLBACK
  141. ret = sec_rollback_check(1);
  142. if (ret) {
  143. g_boot_state = BOOT_STATE_RED;
  144. ret = -1;
  145. }
  146. #endif
  147. } else
  148. dprintf(INFO, "[SBC] (%s, %s) cert vfy disabled\n", part_name, img_name);
  149. #endif
  150. ret = print_boot_state();
  151. if (ret)
  152. return ret;
  153. if (img_name == NULL)
  154. ret = show_warning("UNKNOWN");
  155. else
  156. ret = show_warning(img_name);
  157. if (ret)
  158. return ret;
  159. return ret;
  160. }
  161. int verified_boot_flow(char *img_name, unsigned long img_addr, unsigned int img_sz)
  162. {
  163. int ret = 0;
  164. unsigned int policy_entry_idx = 0;
  165. unsigned int img_auth_required = 0;
  166. unsigned int img_vfy_time = 0;
  167. int lock_state = 0;
  168. if (g_boot_state == BOOT_STATE_RED)
  169. goto _end;
  170. g_boot_state = BOOT_STATE_GREEN;
  171. /* loading boot image without verifying boot image header first would not
  172. become a security hole since initial load address is not specified by
  173. boot image header, boot image is loaded to an address specified by lk,
  174. and kernel and ramdisk will be relocated later after boot image
  175. verification is done. Need to consider whether boot image size will be
  176. too big so it overlaps with other important region. */
  177. /* if MTK_SECURITY_SW_SUPPORT is not defined, boot state is always green */
  178. #ifdef MTK_SECURITY_SW_SUPPORT
  179. /* please refer to the following website for verified boot flow */
  180. /* http://source.android.com/devices/tech/security/verifiedboot/verified-boot.html */
  181. ret = sec_query_device_lock(&lock_state);
  182. if (ret) {
  183. g_boot_state = BOOT_STATE_RED;
  184. goto _end;
  185. }
  186. if (DEVICE_STATE_LOCKED == lock_state) {
  187. img_vfy_time = get_timer(0);
  188. policy_entry_idx = get_policy_entry_idx("boot");
  189. img_auth_required = get_vfy_policy(policy_entry_idx);
  190. if (img_auth_required) {
  191. img_vfy_time = get_timer(0);
  192. ret = (int)sec_img_auth((unsigned char *)img_addr, img_sz);
  193. if (ret) {
  194. /* show public key on LCM and requires user confirmation to proceed */
  195. ret = sec_img_auth_custom((unsigned char *)img_addr, img_sz);
  196. if (0 == ret)
  197. g_boot_state = BOOT_STATE_YELLOW;
  198. else
  199. g_boot_state = BOOT_STATE_RED;
  200. }
  201. dprintf(INFO, "[SBC] img vfy(%d ms)\n", (unsigned int)get_timer(img_vfy_time));
  202. #if defined(TRUSTONIC_TEE_SUPPORT) && defined(RDA_STATUS_SUPPORT)
  203. if (g_boot_state == BOOT_STATE_GREEN)
  204. root_status_check(1); /* boot image verification succeeds */
  205. else
  206. root_status_check(0); /* boot image verification fails */
  207. #endif //TRUSTONIC_TEE_SUPPORT && RDA_STATUS_SUPPORT
  208. } else
  209. dprintf(CRITICAL, "[SBC] img vfy disabled\n");
  210. } else if (DEVICE_STATE_UNLOCKED == lock_state)
  211. g_boot_state = BOOT_STATE_ORANGE;
  212. else /* unknown lock state*/
  213. g_boot_state = BOOT_STATE_RED;
  214. #endif //MTK_SECURITY_SW_SUPPORT
  215. _end:
  216. ret = print_boot_state();
  217. if (ret)
  218. return ret;
  219. if (img_name == NULL)
  220. ret = show_warning("UNKNOWN");
  221. else
  222. ret = show_warning(img_name);
  223. if (ret)
  224. return ret;
  225. ret = set_boot_state_to_cmdline();
  226. if (ret)
  227. return ret;
  228. return ret;
  229. }
  230. static int mboot_common_load_part_info(char *part_name,
  231. char *img_name, part_hdr_t *part_hdr, unsigned long long *img_start_addr)
  232. {
  233. long len;
  234. u64 offset, part_size;
  235. part_size = partition_get_size_by_name(part_name);
  236. offset = 0;
  237. //***************
  238. //* read partition header
  239. //*
  240. while (1) {
  241. len = partition_read(part_name, offset, (uchar *)part_hdr, sizeof(part_hdr_t));
  242. if (len < 0) {
  243. dprintf(CRITICAL, "[%s] %s partition read error. LINE: %d\n", MODULE_NAME,
  244. part_name, __LINE__);
  245. break;
  246. }
  247. dprintf(CRITICAL, "\n=========================================\n");
  248. dprintf(CRITICAL, "[%s] %s magic number : 0x%x\n", MODULE_NAME, part_name,
  249. part_hdr->info.magic);
  250. part_hdr->info.name[31] = '\0'; //append end char
  251. dprintf(CRITICAL, "[%s] %s name : %s\n", MODULE_NAME, part_name,
  252. part_hdr->info.name);
  253. dprintf(CRITICAL, "[%s] %s size : %d\n", MODULE_NAME, part_name,
  254. part_hdr->info.dsize);
  255. dprintf(CRITICAL, "=========================================\n");
  256. //***************
  257. //* check partition magic
  258. //*
  259. if (part_hdr->info.magic != PART_MAGIC) {
  260. dprintf(CRITICAL, "[%s] %s partition magic error\n", MODULE_NAME, part_name);
  261. len = -1;
  262. break;
  263. }
  264. offset += sizeof(part_hdr_t);
  265. //***************
  266. //* check partition data size
  267. //*
  268. if ((offset + part_hdr->info.dsize) > part_size) {
  269. dprintf(CRITICAL, "[%s] %s partition size error 0x%llx, 0x%llx\n", MODULE_NAME,
  270. part_name, offset + part_hdr->info.dsize, part_size);
  271. len = -1;
  272. break;
  273. }
  274. //***************
  275. //* check image name
  276. //*
  277. if (!strncasecmp(part_hdr->info.name, img_name, sizeof(part_hdr->info.name))) {
  278. dprintf(INFO, "[%s] %s image name found\n", MODULE_NAME, img_name);
  279. break;
  280. }
  281. //***************
  282. //* find next image
  283. //* image with new layout will align to a specific size
  284. //*
  285. if (part_hdr->info.ext_magic == PART_EXT_MAGIC)
  286. offset += ROUNDUP(part_hdr->info.dsize, part_hdr->info.align_size);
  287. else
  288. offset += part_hdr->info.dsize;
  289. }
  290. if (len > 0)
  291. *img_start_addr = offset;
  292. return len;
  293. }
  294. /**********************************************************
  295. * Routine: mboot_common_load_part
  296. *
  297. * Description: common function for loading image from nand flash
  298. * this function is called by
  299. * (1) 'mboot_common_load_logo' to display logo
  300. *
  301. **********************************************************/
  302. int mboot_common_load_part(char *part_name, char *img_name, unsigned long addr)
  303. {
  304. long len;
  305. unsigned long long start_addr = 0;
  306. part_hdr_t *part_hdr;
  307. part_hdr = (part_hdr_t *)malloc(sizeof(part_hdr_t));
  308. if (!part_hdr)
  309. return -ENOMEM;
  310. len = mboot_common_load_part_info(part_name, img_name, part_hdr,
  311. &start_addr);
  312. if (len < 0) {
  313. len = -EINVAL;
  314. goto exit;
  315. }
  316. //****************
  317. //* read image data
  318. //*
  319. dprintf(INFO, "read the data of %s\n", part_name);
  320. len = partition_read(part_name, start_addr, (uchar *)addr,
  321. (size_t)part_hdr->info.dsize);
  322. if (len < 0) {
  323. len = -EIO;
  324. goto exit;
  325. }
  326. exit:
  327. if (part_hdr)
  328. free(part_hdr);
  329. return len;
  330. }
  331. /**********************************************************
  332. * Routine: mboot_common_load_logo
  333. *
  334. * Description: function to load logo to display
  335. *
  336. **********************************************************/
  337. int mboot_common_load_logo(unsigned long logo_addr, char *filename)
  338. {
  339. int ret;
  340. #if (CONFIG_COMMANDS & CFG_CMD_FAT)
  341. long len;
  342. #endif
  343. #if (CONFIG_COMMANDS & CFG_CMD_FAT)
  344. len = file_fat_read(filename, (unsigned char *)logo_addr, 0);
  345. if (len > 0)
  346. return (int)len;
  347. #endif
  348. ret = mboot_common_load_part("logo", "logo", logo_addr);
  349. return ret;
  350. }
  351. /**********************************************************
  352. * Routine: mboot_android_check_img_info
  353. *
  354. * Description: this function is called to
  355. * (1) check the header of kernel / rootfs
  356. *
  357. * Notice : this function will be called by 'mboot_android_check_bootimg_hdr'
  358. *
  359. **********************************************************/
  360. int mboot_android_check_img_info(char *part_name, part_hdr_t *part_hdr)
  361. {
  362. //***************
  363. //* check partition magic
  364. //*
  365. if (part_hdr->info.magic != PART_MAGIC) {
  366. dprintf(CRITICAL, "[%s] %s partition magic not match\n", MODULE_NAME,
  367. part_name);
  368. return -1;
  369. }
  370. //***************
  371. //* check partition name
  372. //*
  373. if (strncasecmp(part_hdr->info.name, part_name, sizeof(part_hdr->info.name))) {
  374. dprintf(CRITICAL, "[%s] %s partition name not match\n", MODULE_NAME, part_name);
  375. return -1;
  376. }
  377. dprintf(CRITICAL, "\n=========================================\n");
  378. dprintf(CRITICAL, "[%s] %s magic number : 0x%x\n", MODULE_NAME, part_name,
  379. part_hdr->info.magic);
  380. dprintf(CRITICAL, "[%s] %s size : 0x%x\n", MODULE_NAME, part_name,
  381. part_hdr->info.dsize);
  382. dprintf(CRITICAL, "=========================================\n");
  383. //***************
  384. //* return the image size
  385. //*
  386. return part_hdr->info.dsize;
  387. }
  388. /**********************************************************
  389. * Routine: mboot_android_check_bootimg_hdr
  390. *
  391. * Description: this function is called to
  392. * (1) 'read' the header of boot image from nand flash
  393. * (2) 'parse' the header of boot image to obtain
  394. * - (a) kernel image size
  395. * - (b) rootfs image size
  396. * - (c) rootfs offset
  397. *
  398. * Notice : this function must be read first when doing nand / msdc boot
  399. *
  400. **********************************************************/
  401. static int mboot_android_check_bootimg_hdr(char *part_name,
  402. struct bootimg_hdr *boot_hdr)
  403. {
  404. long len;
  405. int ret = 0;
  406. u64 addr;
  407. unsigned int k_pg_cnt = 0;
  408. unsigned int r_pg_cnt = 0;
  409. unsigned int dt_pg_cnt = 0;
  410. //**********************************
  411. // TODO : fix pg_sz assignment
  412. //**********************************
  413. unsigned int pg_sz = 2 * 1024 ;
  414. addr = partition_get_offset_by_name(part_name);
  415. //***************
  416. //* read partition header
  417. //*
  418. dprintf(CRITICAL, "part page addr is 0x%llx\n", addr);
  419. len = partition_read(part_name, 0, (uchar *) boot_hdr,
  420. sizeof(struct bootimg_hdr));
  421. if (len < 0) {
  422. dprintf(CRITICAL, "[%s] %s boot image header read error. LINE: %d\n",
  423. MODULE_NAME, part_name, __LINE__);
  424. return -1;
  425. }
  426. dprintf(CRITICAL,
  427. "\n============================================================\n");
  428. dprintf(CRITICAL, "[%s] Android Partition Name : %s\n",
  429. MODULE_NAME, part_name);
  430. dprintf(CRITICAL, "[%s] Android Boot IMG Hdr - Kernel Size : 0x%08X\n",
  431. MODULE_NAME, boot_hdr->kernel_sz);
  432. dprintf(CRITICAL, "[%s] Android Boot IMG Hdr - Kernel Address : 0x%08X\n",
  433. MODULE_NAME, boot_hdr->kernel_addr);
  434. dprintf(CRITICAL, "[%s] Android Boot IMG Hdr - Rootfs Size : 0x%08X\n",
  435. MODULE_NAME, boot_hdr->ramdisk_sz);
  436. dprintf(CRITICAL, "[%s] Android Boot IMG Hdr - Rootfs Address : 0x%08X\n",
  437. MODULE_NAME, boot_hdr->ramdisk_addr);
  438. dprintf(CRITICAL, "[%s] Android Boot IMG Hdr - Tags Address : 0x%08X\n",
  439. MODULE_NAME, boot_hdr->tags_addr);
  440. dprintf(CRITICAL, "[%s] Android Boot IMG Hdr - Page Size : 0x%08X\n",
  441. MODULE_NAME, boot_hdr->page_sz);
  442. dprintf(CRITICAL, "[%s] Android Boot IMG Hdr - Command Line : %s\n",
  443. MODULE_NAME, boot_hdr->cmdline);
  444. dprintf(CRITICAL,
  445. "============================================================\n");
  446. //***************
  447. //* check partition magic
  448. //*
  449. if (strncmp((char const *)boot_hdr->magic, BOOTIMG_MAGIC,
  450. BOOTIMG_MAGIC_SZ) != 0) {
  451. dprintf(CRITICAL, "[%s] boot image header magic error\n", MODULE_NAME);
  452. return -1;
  453. }
  454. pg_sz = boot_hdr->page_sz;
  455. g_pg_sz = boot_hdr->page_sz;
  456. //***************
  457. //* follow bootimg.h to calculate the location of rootfs
  458. //*
  459. if (len != -1) {
  460. unsigned int k_pg_cnt = 0;
  461. unsigned int r_pg_cnt = 0;
  462. unsigned int dtbo_pg_cnt = 0;
  463. unsigned int dt_pg_cnt = 0;
  464. if (g_is_64bit_kernel)
  465. g_kmem_off = (unsigned int)target_get_scratch_address();
  466. else
  467. g_kmem_off = boot_hdr->kernel_addr;
  468. if (boot_hdr->kernel_sz % pg_sz == 0)
  469. k_pg_cnt = boot_hdr->kernel_sz / pg_sz;
  470. else
  471. k_pg_cnt = (boot_hdr->kernel_sz / pg_sz) + 1;
  472. if (boot_hdr->ramdisk_sz % pg_sz == 0)
  473. r_pg_cnt = boot_hdr->ramdisk_sz / pg_sz;
  474. else
  475. r_pg_cnt = (boot_hdr->ramdisk_sz / pg_sz) + 1;
  476. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_ONE)
  477. dtbo_pg_cnt = (boot_hdr->recovery_dtbo_size + (pg_sz - 1)) / pg_sz;
  478. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_TWO)
  479. dt_pg_cnt = (boot_hdr->dtb_size + (pg_sz - 1)) / pg_sz;
  480. dprintf(INFO, " > page count of kernel image = %d\n", k_pg_cnt);
  481. g_rmem_off = g_kmem_off + k_pg_cnt * pg_sz;
  482. dprintf(INFO, " > kernel mem offset = 0x%x\n", g_kmem_off);
  483. dprintf(INFO, " > rootfs mem offset = 0x%x\n", g_rmem_off);
  484. //***************
  485. //* specify boot image size
  486. //*
  487. g_bimg_sz = (k_pg_cnt + r_pg_cnt + dtbo_pg_cnt + dt_pg_cnt + 1) * pg_sz;
  488. dprintf(INFO, " > boot image size = 0x%x\n", g_bimg_sz);
  489. }
  490. ret = verified_boot_init("boot", "boot");
  491. if (ret)
  492. return ret;
  493. return 0;
  494. }
  495. /**********************************************************
  496. * Routine: mboot_android_check_recoveryimg_hdr
  497. *
  498. * Description: this function is called to
  499. * (1) 'read' the header of boot image from nand flash
  500. * (2) 'parse' the header of boot image to obtain
  501. * - (a) kernel image size
  502. * - (b) rootfs image size
  503. * - (c) rootfs offset
  504. *
  505. * Notice : this function must be read first when doing nand / msdc boot
  506. *
  507. **********************************************************/
  508. static int mboot_android_check_recoveryimg_hdr(char *part_name,
  509. struct bootimg_hdr *boot_hdr)
  510. {
  511. int ret = 0;
  512. long len;
  513. unsigned int k_pg_cnt = 0;
  514. unsigned int r_pg_cnt = 0;
  515. unsigned int dt_pg_cnt = 0;
  516. //**********************************
  517. // TODO : fix pg_sz assignment
  518. //**********************************
  519. unsigned int pg_sz = 2 * 1024 ;
  520. //***************
  521. //* read partition header
  522. //*
  523. len = partition_read(part_name, 0, (uchar *) boot_hdr,
  524. sizeof(struct bootimg_hdr));
  525. if (len < 0) {
  526. dprintf(CRITICAL, "[%s] %s Recovery image header read error. LINE: %d\n",
  527. MODULE_NAME, part_name, __LINE__);
  528. return -1;
  529. }
  530. dprintf(CRITICAL,
  531. "\n============================================================\n");
  532. dprintf(CRITICAL, "[%s] Android Recovery IMG Hdr - Kernel Size : 0x%08X\n",
  533. MODULE_NAME, boot_hdr->kernel_sz);
  534. dprintf(CRITICAL, "[%s] Android Recovery IMG Hdr - Kernel Address : 0x%08X\n",
  535. MODULE_NAME, boot_hdr->kernel_addr);
  536. dprintf(CRITICAL, "[%s] Android Recovery IMG Hdr - Rootfs Size : 0x%08X\n",
  537. MODULE_NAME, boot_hdr->ramdisk_sz);
  538. dprintf(CRITICAL, "[%s] Android Recovery IMG Hdr - Rootfs Address : 0x%08X\n",
  539. MODULE_NAME, boot_hdr->ramdisk_addr);
  540. dprintf(CRITICAL, "[%s] Android Recovery IMG Hdr - Tags Address : 0x%08X\n",
  541. MODULE_NAME, boot_hdr->tags_addr);
  542. dprintf(CRITICAL, "[%s] Android Recovery IMG Hdr - Page Size : 0x%08X\n",
  543. MODULE_NAME, boot_hdr->page_sz);
  544. dprintf(CRITICAL, "[%s] Android Recovery IMG Hdr - Command Line : %s\n",
  545. MODULE_NAME, boot_hdr->cmdline);
  546. dprintf(CRITICAL,
  547. "============================================================\n");
  548. //***************
  549. //* check partition magic
  550. //*
  551. if (strncmp((char const *)boot_hdr->magic, BOOTIMG_MAGIC,
  552. BOOTIMG_MAGIC_SZ) != 0) {
  553. dprintf(CRITICAL, "[%s] Recovery image header magic error\n", MODULE_NAME);
  554. return -1;
  555. }
  556. pg_sz = boot_hdr->page_sz;
  557. g_pg_sz = boot_hdr->page_sz;
  558. //***************
  559. //* follow bootimg.h to calculate the location of rootfs
  560. //*
  561. if (len != -1) {
  562. unsigned int k_pg_cnt = 0;
  563. unsigned int r_pg_cnt = 0;
  564. unsigned int dtbo_pg_cnt = 0;
  565. unsigned int dt_pg_cnt = 0;
  566. if (g_is_64bit_kernel)
  567. g_kmem_off = target_get_scratch_address();
  568. else
  569. g_kmem_off = boot_hdr->kernel_addr;
  570. if (boot_hdr->kernel_sz % pg_sz == 0)
  571. k_pg_cnt = boot_hdr->kernel_sz / pg_sz;
  572. else
  573. k_pg_cnt = (boot_hdr->kernel_sz / pg_sz) + 1;
  574. if (boot_hdr->ramdisk_sz % pg_sz == 0)
  575. r_pg_cnt = boot_hdr->ramdisk_sz / pg_sz;
  576. else
  577. r_pg_cnt = (boot_hdr->ramdisk_sz / pg_sz) + 1;
  578. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_ONE)
  579. dtbo_pg_cnt = (boot_hdr->recovery_dtbo_size + (pg_sz - 1)) / pg_sz;
  580. if (boot_hdr->header_version >= BOOT_HEADER_VERSION_TWO)
  581. dt_pg_cnt = (boot_hdr->dtb_size+ (pg_sz - 1)) / pg_sz;
  582. dprintf(INFO, " > page count of kernel image = %d\n", k_pg_cnt);
  583. g_rmem_off = g_kmem_off + k_pg_cnt * pg_sz;
  584. dprintf(INFO, " > kernel mem offset = 0x%x\n", g_kmem_off);
  585. dprintf(INFO, " > rootfs mem offset = 0x%x\n", g_rmem_off);
  586. //***************
  587. //* specify boot image size
  588. //*
  589. g_rcimg_sz = (k_pg_cnt + r_pg_cnt + dtbo_pg_cnt + dt_pg_cnt + 1) * pg_sz;
  590. dprintf(INFO, " > Recovery image size = 0x%x\n", g_rcimg_sz);
  591. }
  592. ret = verified_boot_init("recovery", "boot");
  593. if (ret)
  594. return ret;
  595. return 0;
  596. }
  597. /**********************************************************
  598. * Routine: mboot_android_load_bootimg_hdr
  599. *
  600. * Description: this is the entry function to handle boot image header
  601. *
  602. **********************************************************/
  603. int mboot_android_load_bootimg_hdr(char *part_name, unsigned long addr)
  604. {
  605. long len;
  606. part_t *part;
  607. struct bootimg_hdr *boot_hdr;
  608. append_maxcpus_parameter();
  609. boot_hdr = (struct bootimg_hdr *)malloc(sizeof(struct bootimg_hdr));
  610. if (!boot_hdr) {
  611. dprintf(CRITICAL, "mboot_android_load_bootimg_hdr, boot_hdr = NULL\n");
  612. return -ENOMEM;
  613. }
  614. g_boot_hdr = boot_hdr;
  615. len = mboot_android_check_bootimg_hdr(part_name, boot_hdr);
  616. platform_parse_bootopt(boot_hdr->cmdline);
  617. #ifndef USER_BUILD
  618. char cmdline[UART_EARLY_CONSOLE_LEN];
  619. if (g_is_64bit_kernel == 1)
  620. snprintf(cmdline, UART_EARLY_CONSOLE_LEN, " earlycon=uartmtk,mmio32,0x%x,",
  621. AP_UART0_BASE);
  622. else
  623. snprintf(cmdline, UART_EARLY_CONSOLE_LEN, " earlyprintk=mt6757,0x%x ",
  624. AP_UART0_BASE);
  625. cmdline_append(cmdline);
  626. #endif
  627. return len;
  628. }
  629. /**********************************************************
  630. * Routine: mboot_android_load_recoveryimg_hdr
  631. *
  632. * Description: this is the entry function to handle Recovery image header
  633. *
  634. **********************************************************/
  635. int mboot_android_load_recoveryimg_hdr(char *part_name, unsigned long addr)
  636. {
  637. long len;
  638. struct bootimg_hdr *boot_hdr;
  639. boot_hdr = (struct bootimg_hdr *)malloc(sizeof(struct bootimg_hdr));
  640. if (!boot_hdr) {
  641. dprintf(CRITICAL, "mboot_android_load_bootimg_hdr, boot_hdr = NULL\n");
  642. return -ENOMEM;
  643. }
  644. g_boot_hdr = boot_hdr;
  645. len = mboot_android_check_recoveryimg_hdr(part_name, boot_hdr);
  646. return len;
  647. }
  648. /**********************************************************
  649. * Routine: mboot_android_load_bootimg
  650. *
  651. * Description: main function to load Android Boot Image
  652. *
  653. **********************************************************/
  654. int mboot_android_load_bootimg(char *part_name, unsigned long addr)
  655. {
  656. int ret = 0;
  657. long len;
  658. unsigned long long start_addr;
  659. //***************
  660. //* not to include unused header
  661. //*
  662. start_addr = partition_get_offset_by_name(part_name) + g_boot_hdr->page_sz;
  663. /*
  664. * check mkimg header
  665. */
  666. dprintf(INFO, "check mkimg header\n");
  667. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  668. MKIMG_HEADER_SZ);
  669. if (len < 0) {
  670. dprintf(CRITICAL, "[%s] %s partition read error. LINE: %d\n", MODULE_NAME,
  671. part_name, __LINE__);
  672. return -EIO;
  673. }
  674. // check kernel header
  675. g_kimg_sz = mboot_android_check_img_info(PART_KERNEL, (part_hdr_t *)addr);
  676. if (g_kimg_sz == -1)
  677. dprintf(INFO, "no mkimg header in kernel image\n");
  678. else {
  679. dprintf(INFO, "mkimg header exist in kernel image\n");
  680. addr = addr - MKIMG_HEADER_SZ;
  681. g_rmem_off = g_rmem_off - MKIMG_HEADER_SZ;
  682. }
  683. //***************
  684. //* read image data
  685. //*
  686. dprintf(INFO, "\nread the data of %s (size = 0x%x)\n", part_name, g_bimg_sz);
  687. dprintf(INFO, " > from - 0x%016llx (skip boot img hdr)\n", start_addr);
  688. dprintf(INFO, " > to - 0x%x (starts with kernel img hdr)\n",
  689. (unsigned int)addr);
  690. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  691. (size_t)g_bimg_sz);
  692. // check ramdisk/rootfs header
  693. g_rimg_sz = mboot_android_check_img_info(PART_ROOTFS, (part_hdr_t *)g_rmem_off);
  694. if (g_rimg_sz == -1) {
  695. dprintf(INFO, "no mkimg header in ramdisk image\n");
  696. g_rimg_sz = g_boot_hdr->ramdisk_sz;
  697. } else {
  698. dprintf(INFO, "mkimg header exist in ramdisk image\n");
  699. g_rmem_off = g_rmem_off + MKIMG_HEADER_SZ;
  700. }
  701. if (len < 0) {
  702. len = -EIO;
  703. return len;
  704. }
  705. ret = verified_boot_flow("boot", addr, g_bimg_sz - g_pg_sz);
  706. if (ret)
  707. len = -EIO;
  708. return len;
  709. }
  710. /**********************************************************
  711. * Routine: mboot_android_load_recoveryimg
  712. *
  713. * Description: main function to load Android Recovery Image
  714. *
  715. **********************************************************/
  716. int mboot_android_load_recoveryimg(char *part_name, unsigned long addr)
  717. {
  718. int ret = 0;
  719. long len;
  720. unsigned long long start_addr;
  721. //***************
  722. //* not to include unused header
  723. //*
  724. start_addr = partition_get_offset_by_name(part_name)+ g_boot_hdr->page_sz;
  725. /*
  726. * check mkimg header
  727. */
  728. dprintf(INFO, "check mkimg header\n");
  729. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  730. MKIMG_HEADER_SZ);
  731. if (len < 0) {
  732. dprintf(CRITICAL, "[%s] %s partition read error. LINE: %d\n", MODULE_NAME,
  733. part_name, __LINE__);
  734. return -EIO;
  735. }
  736. // check kernel header
  737. g_kimg_sz = mboot_android_check_img_info(PART_KERNEL, (part_hdr_t *)addr);
  738. if (g_kimg_sz == -1)
  739. dprintf(INFO, "no mkimg header in kernel image\n");
  740. else {
  741. dprintf(INFO, "mkimg header exist in kernel image\n");
  742. addr = addr - MKIMG_HEADER_SZ;
  743. g_rmem_off = g_rmem_off - MKIMG_HEADER_SZ;
  744. }
  745. //***************
  746. //* read image data
  747. //*
  748. dprintf(INFO, "\nread the data of %s (size = 0x%x)\n", part_name, g_rcimg_sz);
  749. dprintf(INFO, " > from - 0x%016llx (skip recovery img hdr)\n", start_addr);
  750. dprintf(INFO, " > to - 0x%x (starts with kernel img hdr)\n",
  751. (unsigned int)addr);
  752. len = partition_read(part_name, g_boot_hdr->page_sz, (uchar *)addr,
  753. (size_t)g_rcimg_sz);
  754. // check ramdisk/rootfs header
  755. g_rimg_sz = mboot_android_check_img_info("recovery", (part_hdr_t *)g_rmem_off);
  756. if (g_rimg_sz == -1) {
  757. dprintf(INFO, "no mkimg header in recovery image\n");
  758. g_rimg_sz = g_boot_hdr->ramdisk_sz;
  759. } else {
  760. dprintf(INFO, "mkimg header exist in recovery image\n");
  761. g_rmem_off = g_rmem_off + MKIMG_HEADER_SZ;
  762. }
  763. if (len < 0) {
  764. len = -EIO;
  765. return len;
  766. }
  767. ret = verified_boot_flow("recovery", addr, g_rcimg_sz - g_pg_sz);
  768. if (ret)
  769. len = -EIO;
  770. return len;
  771. }
  772. /**********************************************************
  773. * Routine: mboot_recovery_load_raw_part
  774. *
  775. * Description: load raw data for recovery mode support
  776. *
  777. **********************************************************/
  778. int mboot_recovery_load_raw_part(char *part_name, unsigned long *addr,
  779. unsigned int size)
  780. {
  781. long len;
  782. unsigned long begin;
  783. begin = get_timer(0);
  784. len = partition_read(part_name, 0, (uchar *)addr, (size_t)size);
  785. if (len < 0) {
  786. len = -EIO;
  787. goto exit;
  788. }
  789. dprintf(CRITICAL, "[%s] Load '%s' partition to 0x%08lX (%d bytes in %ld ms)\n",
  790. MODULE_NAME, part_name, (unsigned long)addr, size, get_timer(begin));
  791. exit:
  792. return len;
  793. }
  794. /**********************************************************
  795. * Routine: mboot_recovery_load_misc
  796. *
  797. * Description: load recovery command
  798. *
  799. **********************************************************/
  800. int mboot_recovery_load_misc(unsigned long *misc_addr, unsigned int size)
  801. {
  802. int ret;
  803. dprintf(INFO, "[mboot_recovery_load_misc]: size is %u\n", size);
  804. dprintf(INFO, "[mboot_recovery_load_misc]: misc_addr is 0x%x\n",
  805. (unsigned int)misc_addr);
  806. ret = mboot_recovery_load_raw_part("para", misc_addr, size);
  807. if (ret < 0)
  808. return ret;
  809. return ret;
  810. }
  811. unsigned int mboot_get_img_size(char *part_name, unsigned int *size)
  812. {
  813. int ret = 0;
  814. long len = 0;
  815. struct bootimg_hdr boot_hdr;
  816. unsigned page_sz = 0x800;
  817. *size = 0;
  818. len = partition_read(part_name, (off_t)0, (uchar *)&boot_hdr,
  819. sizeof(struct bootimg_hdr));
  820. if (len < 0) {
  821. dprintf(CRITICAL, "[%s] %s boot image header read error. LINE: %d\n",
  822. MODULE_NAME, part_name, __LINE__);
  823. return -1;
  824. }
  825. boot_hdr.magic[7] = '\0';
  826. dprintf(CRITICAL,
  827. "\n============================================================\n");
  828. dprintf(CRITICAL, "[%s] Android Partition Name : %s\n", MODULE_NAME,
  829. part_name);
  830. dprintf(CRITICAL, "[%s] Android IMG Hdr - Magic : %s\n", MODULE_NAME,
  831. boot_hdr.magic);
  832. dprintf(CRITICAL, "[%s] Android IMG Hdr - Kernel Size : 0x%08X\n",
  833. MODULE_NAME, boot_hdr.kernel_sz);
  834. dprintf(CRITICAL, "[%s] Android IMG Hdr - Kernel Address : 0x%08X\n",
  835. MODULE_NAME, boot_hdr.kernel_addr);
  836. dprintf(CRITICAL, "[%s] Android IMG Hdr - Rootfs Size : 0x%08X\n",
  837. MODULE_NAME, boot_hdr.ramdisk_sz);
  838. dprintf(CRITICAL, "[%s] Android IMG Hdr - Rootfs Address : 0x%08X\n",
  839. MODULE_NAME, boot_hdr.ramdisk_addr);
  840. dprintf(CRITICAL, "[%s] Android IMG Hdr - Tags Address : 0x%08X\n",
  841. MODULE_NAME, boot_hdr.tags_addr);
  842. dprintf(CRITICAL, "[%s] Android IMG Hdr - Page Size : 0x%08X\n",
  843. MODULE_NAME, boot_hdr.page_sz);
  844. dprintf(CRITICAL, "[%s] Android IMG Hdr - Command Line : %s\n", MODULE_NAME,
  845. boot_hdr.cmdline);
  846. dprintf(CRITICAL,
  847. "============================================================\n");
  848. page_sz = boot_hdr.page_sz;
  849. *size += page_sz; /* boot header size is 1 page*/
  850. *size += (((boot_hdr.kernel_sz + page_sz - 1) / page_sz) * page_sz);
  851. *size += (((boot_hdr.ramdisk_sz + page_sz - 1) / page_sz) * page_sz);
  852. *size += (((boot_hdr.second_sz + page_sz - 1) / page_sz) * page_sz);
  853. if (boot_hdr.header_version >= BOOT_HEADER_VERSION_ONE)
  854. *size += (((boot_hdr.recovery_dtbo_size + page_sz - 1) / page_sz) * page_sz);
  855. if (boot_hdr.header_version >= BOOT_HEADER_VERSION_TWO)
  856. *size += (((boot_hdr.dtb_size + page_sz - 1) / page_sz) * page_sz);
  857. return ret;
  858. }