[T106][ZXW-22]7520V3SCV2.01.01.02P42U09_VEC_V0.8_AP_VEC origin source commit

Change-Id: Ic6e05d89ecd62fc34f82b23dcf306c93764aec4b
diff --git a/boot/common/src/loader/drivers/image.c b/boot/common/src/loader/drivers/image.c
new file mode 100755
index 0000000..8903e14
--- /dev/null
+++ b/boot/common/src/loader/drivers/image.c
@@ -0,0 +1,351 @@
+/*
+ * (C) Copyright 2016 ZXIC Inc.
+ */
+#include <common.h>   
+#include <asm/io.h>
+#include <asm/string.h>
+
+#include <image.h>
+#include <linux/byteorder/generic.h>
+#include <secure_verify.h>
+
+#include "flash.h"
+#include <bbt.h>
+
+
+/*
+ ******************************************************************************
+ * Function:     
+ * Description: 
+ * Parameters:
+ *	 Input:
+ *	 Output:
+ * Returns:
+ * Others:
+ *******************************************************************************
+ */
+uint32_t page_align(uint32_t offset)
+{
+    uint32_t page_size = flash.page_size;
+    if(offset & (page_size - 1))
+    {
+        offset &= (~(page_size - 1));
+        offset += page_size;
+    }
+    return offset;
+}
+
+
+/*
+ ******************************************************************************
+ * Function:     
+ * Description: 
+ * Parameters:
+ *	 Input:
+ *	 Output:
+ * Returns:
+ * Others:
+ *******************************************************************************
+ */
+uint32_t find_partition_para(partition_entry_t *entry, 
+ 									   uint32_t entrys, 
+ 									   uint8_t *name)
+{
+    partition_entry_t *p_entry = entry;
+    uint32_t entry_nums = entrys;
+    while(entry_nums--)
+    {
+        if(memcmp( p_entry->part_name, name, strlen(name)) == 0)
+            return p_entry->part_offset;
+        p_entry++;
+    }
+    return -1;
+}
+
+/*
+ ******************************************************************************
+ * Function:     
+ * Description: 
+ * Parameters:
+ *	 Input:
+ *	 Output:
+ * Returns:
+ * Others:
+ *******************************************************************************
+ */
+int read_image_part_offset(uint8_t *name, uint32_t *offset)
+{
+	int ret = 0;
+	uint32_t part_size = 0;
+
+	if(flash.flash_type == NOR_BOOT)
+	{
+		part_size = 8*flash.page_size;
+	}
+	else
+	{
+		part_size = flash.page_size;	
+	}
+
+	ret = flash.read(0x2000, part_size, CFG_TEMP_ADDR);
+	if(ret != 0)
+	{
+		return -1;
+	}
+            
+	partition_table_t *part = (partition_table_t  *)CFG_TEMP_ADDR;   
+	partition_entry_t *entry = &part->table[0];
+	uint32_t entrys = part->entrys;
+
+	if(part->magic != CFG_PARTITION_MAGIC)
+	{
+		return -1;
+	}
+
+	*offset = find_partition_para(entry, entrys, name);
+	if(*offset == -1 )
+	{
+		return -1;
+	}
+
+	return 0;
+}
+
+//#ifdef CONFIG_ZX297520V3E_MDL_AB
+#if defined(CONFIG_ZX297520V3E_MDL_AB) || defined(CONFIG_ZX297520V3E_VEHICLE_DC)
+int read_flags_image(uint8_t *name)
+{
+    T_BOOT_FOTA_FLAG *fotaFlag;
+	uint32_t uiPageSize = 0;
+    uint32_t flags_offset = 0;
+	uint32_t off = 0;
+	uint32_t flags_size = 0x4E0000;/*flags·ÖÇø*/
+	uint32_t blockNum = 0;
+	int32_t flag_one = 0;
+	uint32_t work_area_offset = 0;
+	uint32_t backup_area_offset = 0;
+	int32_t ret = 0;
+	int32_t fota_size = sizeof(T_BOOT_FOTA_FLAG);
+	int32_t block_size = flash.block_size;
+
+	fota_size = page_align(fota_size);
+
+	ret = read_image_part_offset(name, &flags_offset);
+	if(ret != 0)
+	{
+		printf("flags partition offset fail.\n");
+		return -1;
+	}
+
+	/*È·¶¨¹¤×÷ÇøºÍ±¸·ÝÇøÆ«ÒÆµØÖ·*/
+	for (off = flags_offset; off < flags_offset+flags_size; off += flash.block_size)
+	{
+		if (!(nand_block_isbad(off)))
+		{
+            blockNum += 1;
+		}   
+		
+		if((blockNum == 1) && (flag_one == 0))
+		{
+            work_area_offset = off;
+			flag_one = 1;
+		}
+	
+		else if(blockNum == 2)
+		{
+             backup_area_offset = off;
+			 break;
+		}		
+	}
+
+	if(blockNum < 2)
+	{
+        printf("flags partition have not enough space!\n");
+			
+		return -1;
+	}
+	
+	ret = flash.read(work_area_offset, fota_size, CFG_TEMP_ADDR);
+	if(ret != 0)
+	{
+		printf("read flags work partition err.\n");
+		
+		return -1;
+	}
+
+	fotaFlag = (T_BOOT_FOTA_FLAG *)(CFG_TEMP_ADDR);
+	
+	if(fotaFlag->magic != FLAGS_MAGIC)
+	{
+        ret = flash.read(backup_area_offset, fota_size, CFG_TEMP_ADDR);
+		if(ret != 0)
+		{
+			printf("read flags backup partition err.\n");
+			
+			return -1;
+		}
+		fotaFlag = (T_BOOT_FOTA_FLAG *)(CFG_TEMP_ADDR);
+		if(fotaFlag->magic != FLAGS_MAGIC)
+		{
+            printf("flags magic err.\n");
+		    return -1;
+		}	
+	}
+	
+	return 0;
+    
+}
+#endif
+/*
+ ****************************************************************************
+ * Function:     
+ * Description: 
+ * Parameters:
+ *	 Input:
+ *	 Output:
+ * Returns:
+ * Others:
+ *****************************************************************************
+ */
+int read_uboot_image(uint8_t *name, uint32_t *uboot_entry_point)
+{
+	/*
+	 * +----------------------------------------------------------------+
+	 * |  sImageHeader  |  image_header_t  |    u-boot.bin     |                
+	 * +----------------------------------------------------------------+
+	 * |    384 Bytes      |     64 Bytes         |    xxx Bytes       |
+	 *                                 
+	 */
+
+	image_header_t *psImgHdrOld = NULL;
+
+	uint32_t uiPageSize = 0;
+
+	uint32_t uiImgHdrSizeOld = sizeof(image_header_t);
+	uint32_t uiImgHdrSizeNew = sizeof(sImageHeader);
+
+	uint32_t uiUBootSize = 0;
+	uint32_t uiUBootLoadAddr = 0;
+	uint32_t uiUBootIsReadSize = 0;
+
+	int32_t ret = 0;
+	uint32_t uboot_offset = 0;
+
+
+		
+	if(flash.flash_type == NOR_BOOT)
+	{
+		uiPageSize = 8*flash.page_size;
+	}
+	else 
+	{
+		uiPageSize = flash.page_size;	
+	}
+
+	ret = read_image_part_offset(name, &uboot_offset);
+	if(ret != 0)
+	{
+		printf("offset fail.\n");
+		return -1;
+	}
+	
+	ret = flash.read(uboot_offset, uiPageSize, CFG_TEMP_ADDR);
+	if(ret != 0)
+	{
+		printf("image header err.\n");
+		return -1;
+	}
+
+	psImgHdrOld = (image_header_t *)(CFG_TEMP_ADDR + uiImgHdrSizeNew);
+	uiUBootSize = ___htonl(psImgHdrOld->ih_size);   
+	uiUBootLoadAddr = ___htonl(psImgHdrOld->ih_load);
+	*uboot_entry_point = ___htonl(psImgHdrOld->ih_ep);
+
+	if(___htonl(psImgHdrOld->ih_magic) != IH_MAGIC)
+	{
+		printf("magic err.\n");
+		return -1;
+	}
+
+	uiUBootIsReadSize = uiPageSize - uiImgHdrSizeOld - uiImgHdrSizeNew;
+	uiUBootSize -= uiUBootIsReadSize;			
+	uiUBootSize = page_align(uiUBootSize);   
+
+	memcpy(uiUBootLoadAddr - uiImgHdrSizeOld, 
+			CFG_TEMP_ADDR + uiImgHdrSizeNew, 
+		   	uiUBootIsReadSize + uiImgHdrSizeOld);
+
+	ret = flash.read(uboot_offset + uiPageSize, 
+						uiUBootSize, 
+						uiUBootLoadAddr + uiUBootIsReadSize);
+	if(ret != 0)
+	{
+		printf("image err.\n");
+		return -1;
+	}
+	
+	ret = SecureVerify(CFG_TEMP_ADDR);
+	if(ret != 0)
+	{
+		printf("Secure verify fail!\n");
+		return -1;
+	}
+	
+	return 0;
+}
+
+/*
+ ******************************************************************************
+ * Function:     
+ * Description: 
+ * Parameters:
+ *	 Input:
+ *	 Output:
+ * Returns:
+ * Others:
+ *******************************************************************************
+ */
+ int nand_read_m0(uint32_t *m0_entry_point)
+{
+	int remap = 0;
+	image_header_t *header = NULL;
+	uint32_t image_header_size = sizeof(image_header_t);
+	uint32_t m0_size = 0;
+	uint32_t m0_load_addr = 0;
+	/*
+	 * +---------------------------------------------------------+
+	 * |  image_header_t    |          m0                        |                
+	 * +---------------------------------------------------------+
+                            m0.bin
+	 */
+
+	/*1¡¢µÈ´ýBOOT°áÔËM0°æ±¾µ½CONFIG_SYS_SDRAM_TEMP_BASEÖÐ*/
+	writel(0, M0_IMAGE_READY_FLAG_ADDR);
+	while(!readl(M0_IMAGE_READY_FLAG_ADDR));
+
+	/*2¡¢M0µÄ0µØÖ·ÖØÓ³Éä*/
+	remap = readl(0x140000);
+	remap |= 0x800000;
+	writel(remap,0x140000);
+
+	/*3¡¢½âÎöM0µÄ°æ±¾Í·£¬»ñÈ¡ÔËÐеØÖ·ÒÔ¼°´óС*/
+	header = (image_header_t *)CONFIG_SYS_SDRAM_TEMP_BASE;
+	m0_size = ___htonl(header->ih_size);    /* m0.bin */
+	m0_load_addr = ___htonl(header->ih_load);
+	*m0_entry_point = ___htonl(header->ih_ep);   
+
+	if(___htonl(header->ih_magic) != IH_MAGIC)
+	{
+		return -1;
+	}
+
+	/*4¡¢½«M0µÄ°æ±¾´ÓIRAM0¿½±´µ½load_addr*/
+	memcpy(m0_load_addr, CONFIG_SYS_SDRAM_TEMP_BASE + image_header_size, m0_size); 
+
+	/*5¡¢ÐÞ¸ÄIRAM±ê¼Ç£¬Ê¹BOOT¼ÌÐøÍùÏÂÖ´ÐÐ*/
+	writel(0, M0_IMAGE_READY_FLAG_ADDR);
+
+	return 0;
+}
+
+