forked from xuos/xiuos
Merge pull request 'merge code' (#10) from xidatong-arm32 into prepare_for_master
This commit is contained in:
commit
b825fd7f84
|
@ -5,4 +5,6 @@ source "$KERNEL_DIR/lib/Kconfig"
|
|||
|
||||
source "$KERNEL_DIR/fs/Kconfig"
|
||||
|
||||
source "$KERNEL_DIR/tool/Kconfig"
|
||||
|
||||
source "$KERNEL_DIR/../../APP_Framework/Kconfig"
|
||||
|
|
|
@ -101,7 +101,7 @@ Reset_Handler:
|
|||
strlt r0, [r1], #4
|
||||
blt .LoopCopy1
|
||||
|
||||
ldr r0,=BootLoaderJumpApp
|
||||
ldr r0,=ota_entry
|
||||
blx r0
|
||||
#else /* APP */
|
||||
cpsid i /* Mask interrupts */
|
||||
|
|
|
@ -40,22 +40,6 @@ menu "xidatong-arm32 feature"
|
|||
int "stack size for interrupt"
|
||||
default 4096
|
||||
|
||||
config BSP_USING_OTA
|
||||
bool "xidatong arm32 support OTA function"
|
||||
default n
|
||||
if BSP_USING_OTA
|
||||
choice
|
||||
prompt "compile bootloader bin or application bin."
|
||||
default MCUBOOT_BOOTLOADER
|
||||
|
||||
config MCUBOOT_BOOTLOADER
|
||||
bool "config as bootloader."
|
||||
|
||||
config MCUBOOT_APPLICATION
|
||||
bool "config as application."
|
||||
endchoice
|
||||
endif
|
||||
|
||||
menu "config board peripheral"
|
||||
config MOUNT_SDCARD
|
||||
bool
|
||||
|
|
|
@ -64,8 +64,8 @@ Modification:
|
|||
#include <connect_wdt.h>
|
||||
#endif
|
||||
|
||||
#ifdef BSP_USING_OTA
|
||||
#include <imxrt_ota.h>
|
||||
#ifdef TOOL_USING_OTA
|
||||
#include <ota.h>
|
||||
#endif
|
||||
|
||||
#ifdef BSP_USING_SEMC
|
||||
|
@ -365,49 +365,6 @@ struct InitSequenceDesc _board_init[] =
|
|||
{ " NONE ",NONE },
|
||||
};
|
||||
|
||||
|
||||
#ifdef BSP_USING_OTA
|
||||
static void OtaCmd(void)
|
||||
{
|
||||
int32_t size;
|
||||
ota_info_t ota_info;
|
||||
|
||||
FLASH_Init();
|
||||
UartConfig();
|
||||
|
||||
memcpy(&ota_info, (const void *)FLAG_FLAH_ADDRESS,sizeof(ota_info_t));
|
||||
ota_info.status = OTA_STATUS_DOWNLOADING;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
size = SerialDownload(DOWN_FLAH_ADDRESS);
|
||||
ota_info.status = OTA_STATUS_DOWNLOADED;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
if(size > 0)
|
||||
{
|
||||
ota_info.down.size = size;
|
||||
ota_info.down.crc32= calculate_crc32(DOWN_FLAH_ADDRESS, size);
|
||||
ota_info.down.version = ota_info.os.version + 1;
|
||||
strncpy(ota_info.down.description, "OTA Test!",sizeof(ota_info.down.description));
|
||||
ota_info.status = OTA_STATUS_READY;
|
||||
strncpy(ota_info.error_message, "No error message!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
else
|
||||
{
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "Failed to download firmware to download partition!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
|
||||
FLASH_DeInit();
|
||||
|
||||
__set_FAULTMASK(1);
|
||||
NVIC_SystemReset();
|
||||
}
|
||||
|
||||
SHELL_EXPORT_CMD(SHELL_CMD_PERMISSION(0)|SHELL_CMD_TYPE(SHELL_TYPE_CMD_FUNC)|SHELL_CMD_PARAM_NUM(0),ota, OtaCmd, ota function);
|
||||
|
||||
#endif
|
||||
|
||||
/**
|
||||
* This function will initial imxrt1050 board.
|
||||
*/
|
||||
|
@ -456,9 +413,8 @@ void InitBoardHardware()
|
|||
KPrintf("board init done.\n");
|
||||
KPrintf("start kernel...\n");
|
||||
|
||||
#ifdef BSP_USING_OTA
|
||||
FLASH_Init();
|
||||
//跳转成功将对应跳转失败标志清零
|
||||
FLASH_DeInit();
|
||||
#ifdef TOOL_USING_OTA
|
||||
//跳转成功设置lastjumpflag为JUMP_SUCCESS_FLAG
|
||||
app_clear_jumpflag();
|
||||
#endif
|
||||
}
|
||||
|
|
|
@ -4,8 +4,8 @@ ifeq ($(CONFIG_BSP_USING_SDIO),y)
|
|||
SRC_FILES += fsl_usdhc.c
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_BSP_USING_OTA),y)
|
||||
SRC_FILES += fsl_romapi.c flash.c mcuboot.c common.c ymodem.c imxrt_ota.c
|
||||
ifeq ($(CONFIG_TOOL_USING_OTA),y)
|
||||
SRC_FILES += fsl_romapi.c flash.c mcuboot.c common.c ymodem.c
|
||||
endif
|
||||
|
||||
include $(KERNEL_ROOT)/compiler.mk
|
||||
|
|
|
@ -14,7 +14,6 @@
|
|||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <xs_base.h>
|
||||
#include "flash.h"
|
||||
#include "MIMXRT1052.h"
|
||||
|
||||
|
@ -58,11 +57,11 @@ static const lookuptable_t FlashLookupTable={
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: Flexspi_Nor_Wait_Busy
|
||||
* 功能描述: 等待FlexSPI NOR Flash忙碌状态结束
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
baseAddr:开始读取的Flash地址(32bit)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: Flexspi_Nor_Wait_Busy
|
||||
* 功能描述: 等待FlexSPI NOR Flash忙碌状态结束
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
baseAddr:开始读取的Flash地址(32bit)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static status_t Flexspi_Nor_Wait_Busy(uint32_t instance, uint32_t baseAddr)
|
||||
{
|
||||
|
@ -101,11 +100,11 @@ static status_t Flexspi_Nor_Wait_Busy(uint32_t instance, uint32_t baseAddr)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: Flexspi_Nor_Write_Enable
|
||||
* 功能描述: 使能 FlexSPI NOR Flash的写入操作
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
baseAddr:开始读取的Flash地址(32bit)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: Flexspi_Nor_Write_Enable
|
||||
* 功能描述: 使能 FlexSPI NOR Flash的写入操作
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
baseAddr:开始读取的Flash地址(32bit)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static status_t Flexspi_Nor_Write_Enable(uint32_t instance, uint32_t baseAddr)
|
||||
{
|
||||
|
@ -125,12 +124,12 @@ static status_t Flexspi_Nor_Write_Enable(uint32_t instance, uint32_t baseAddr)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flexspi_clock_config
|
||||
* 功能描述: 配置FlexSPI模块的时钟
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
freq:表示所需的FlexSPI时钟频率
|
||||
sampleClkMode:指定FlexSPI时钟的采样时钟模式,可以选择SDR或DDR模式
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flexspi_clock_config
|
||||
* 功能描述: 配置FlexSPI模块的时钟
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
freq:表示所需的FlexSPI时钟频率
|
||||
sampleClkMode:指定FlexSPI时钟的采样时钟模式,可以选择SDR或DDR模式
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static void flexspi_clock_config(uint32_t instance, uint32_t freq, uint32_t sampleClkMode)
|
||||
{
|
||||
|
@ -210,10 +209,10 @@ static void flexspi_clock_config(uint32_t instance, uint32_t freq, uint32_t samp
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flexspi_clock_gate_enable
|
||||
* 功能描述: 开启FlexSPI模块的时钟门控
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
* 函 数 名: flexspi_clock_gate_enable
|
||||
* 功能描述: 开启FlexSPI模块的时钟门控
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
static void flexspi_clock_gate_enable(void)
|
||||
{
|
||||
|
@ -222,10 +221,10 @@ static void flexspi_clock_gate_enable(void)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flexspi_clock_gate_disable
|
||||
* 功能描述: 关闭FlexSPI模块的时钟门控
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
* 函 数 名: flexspi_clock_gate_disable
|
||||
* 功能描述: 关闭FlexSPI模块的时钟门控
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
static void flexspi_clock_gate_disable(void)
|
||||
{
|
||||
|
@ -234,12 +233,12 @@ static void flexspi_clock_gate_disable(void)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flexspi_get_clock
|
||||
* 功能描述: 获取FlexSPI时钟频率
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
type:所需时钟类型
|
||||
freq:用于存储获取到的时钟频率类型
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flexspi_get_clock
|
||||
* 功能描述: 获取FlexSPI时钟频率
|
||||
* 形 参: instance:FlexSPI实例号
|
||||
type:所需时钟类型
|
||||
freq:用于存储获取到的时钟频率类型
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static status_t flexspi_get_clock(uint32_t instance, flexspi_clock_type_t type, uint32_t *freq)
|
||||
{
|
||||
|
@ -291,13 +290,13 @@ static status_t flexspi_get_clock(uint32_t instance, flexspi_clock_type_t type,
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flexspi_get_ticks
|
||||
* 功能描述: 计算FlexSPI时钟周期数
|
||||
* 形 参: ticks:用于存储计算结果的指针,即所需的时钟周期数;
|
||||
intervalNs:所需的时间间隔,以纳秒(ns)为单位;
|
||||
freq:FlexSPI时钟频率,单位为MHz;
|
||||
unit:时钟周期单位,即计算结果中每个时钟周期代表的时间长度,以ns为单位
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flexspi_get_ticks
|
||||
* 功能描述: 计算FlexSPI时钟周期数
|
||||
* 形 参: ticks:用于存储计算结果的指针,即所需的时钟周期数;
|
||||
intervalNs:所需的时间间隔,以纳秒(ns)为单位;
|
||||
freq:FlexSPI时钟频率,单位为MHz;
|
||||
unit:时钟周期单位,即计算结果中每个时钟周期代表的时间长度,以ns为单位
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static status_t flexspi_get_ticks(uint32_t *ticks, uint32_t intervalNs, uint32_t freq, uint32_t unit)
|
||||
{
|
||||
|
@ -330,11 +329,11 @@ static status_t flexspi_get_ticks(uint32_t *ticks, uint32_t intervalNs, uint32_t
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flexspi_configure_dll
|
||||
* 功能描述: 用来配置FLEXSPI存储器的DLL(延迟锁存器)
|
||||
* 形 参: instance:FLEXSPI实例号
|
||||
config:存储器配置信息,包括读取时钟源、数据有效时间等参数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flexspi_configure_dll
|
||||
* 功能描述: 用来配置FLEXSPI存储器的DLL(延迟锁存器)
|
||||
* 形 参: instance:FLEXSPI实例号
|
||||
config:存储器配置信息,包括读取时钟源、数据有效时间等参数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static status_t flexspi_configure_dll(uint32_t instance, flexspi_mem_config_t *config)
|
||||
{
|
||||
|
@ -473,11 +472,11 @@ static status_t flexspi_configure_dll(uint32_t instance, flexspi_mem_config_t *c
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flexspi_config_mcr1
|
||||
* 功能描述: 配置FlexSPI模块的MCR1寄存器
|
||||
* 形 参: instance:FLEXSPI实例号
|
||||
onfig指向FlexSPI存储器配置结构体的指针
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flexspi_config_mcr1
|
||||
* 功能描述: 配置FlexSPI模块的MCR1寄存器
|
||||
* 形 参: instance:FLEXSPI实例号
|
||||
onfig指向FlexSPI存储器配置结构体的指针
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static status_t flexspi_config_mcr1(uint32_t instance, flexspi_mem_config_t *config)
|
||||
{
|
||||
|
@ -513,10 +512,10 @@ static status_t flexspi_config_mcr1(uint32_t instance, flexspi_mem_config_t *con
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: FLASH_GetSectorSize
|
||||
* 功能描述: 获取扇区大小
|
||||
* 形 参: 无
|
||||
* 返 回 值: 返回扇区大小,HYPER FLASH为64K字节,NOR FLASH为4K字节
|
||||
* 函 数 名: FLASH_GetSectorSize
|
||||
* 功能描述: 获取扇区大小
|
||||
* 形 参: 无
|
||||
* 返 回 值: 返回扇区大小,HYPER FLASH为64K字节,NOR FLASH为4K字节
|
||||
*******************************************************************************/
|
||||
uint32_t FLASH_GetSectorSize(void)
|
||||
{
|
||||
|
@ -529,10 +528,10 @@ uint32_t FLASH_GetSectorSize(void)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: FLASH_GetProgramCmd
|
||||
* 功能描述: 获取页大小
|
||||
* 形 参: 无
|
||||
* 返 回 值: 返回页大小,HYPER FLASH为512字节,NOR FLASH为256字节
|
||||
* 函 数 名: FLASH_GetProgramCmd
|
||||
* 功能描述: 获取页大小
|
||||
* 形 参: 无
|
||||
* 返 回 值: 返回页大小,HYPER FLASH为512字节,NOR FLASH为256字节
|
||||
*******************************************************************************/
|
||||
uint32_t FLASH_GetProgramCmd(void)
|
||||
{
|
||||
|
@ -548,10 +547,10 @@ uint32_t FLASH_GetProgramCmd(void)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: FLASH_Init
|
||||
* 功能描述: Flash接口初始化,需在进行Flash相关操作前进行调用
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
* 函 数 名: FLASH_Init
|
||||
* 功能描述: Flash接口初始化,需在进行Flash相关操作前进行调用
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
void FLASH_Init(void)
|
||||
{
|
||||
|
@ -567,10 +566,10 @@ void FLASH_Init(void)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: FLASH_DeInit
|
||||
* 功能描述: Flash接口反初始化,需在完成Flash相关操作后进行调用
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
* 函 数 名: FLASH_DeInit
|
||||
* 功能描述: Flash接口反初始化,需在完成Flash相关操作后进行调用
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
void FLASH_DeInit(void)
|
||||
{
|
||||
|
@ -583,11 +582,11 @@ void FLASH_DeInit(void)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: FLASH_EraseSector
|
||||
* 功能描述: 擦除一个Flash扇区
|
||||
* 形 参: addr:擦除区域起始地址
|
||||
* 返 回 值: None
|
||||
* 注 释: 擦除一个扇区的最少时间:30ms~200/400ms
|
||||
* 函 数 名: FLASH_EraseSector
|
||||
* 功能描述: 擦除一个Flash扇区
|
||||
* 形 参: addr:擦除区域起始地址
|
||||
* 返 回 值: None
|
||||
* 注 释: 擦除一个扇区的最少时间:30ms~200/400ms
|
||||
*******************************************************************************/
|
||||
uint8_t FLASH_EraseSector(uint32_t addr)
|
||||
{
|
||||
|
@ -613,13 +612,13 @@ uint8_t FLASH_EraseSector(uint32_t addr)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: FLASH_WritePage
|
||||
* 功能描述: 写Flash一个页
|
||||
* 形 参: addr:写入区域起始地址
|
||||
buf:数据存储区
|
||||
len:要写入的字节数(最大256)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 注 释: 在指定地址开始写入最大256字节的数据
|
||||
* 函 数 名: FLASH_WritePage
|
||||
* 功能描述: 写Flash一个页
|
||||
* 形 参: addr:写入区域起始地址
|
||||
buf:数据存储区
|
||||
len:要写入的字节数(最大256)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 注 释: 在指定地址开始写入最大256字节的数据
|
||||
*******************************************************************************/
|
||||
uint8_t FLASH_WritePage(uint32_t addr, const uint32_t *buf, uint32_t len)
|
||||
{
|
||||
|
@ -648,12 +647,12 @@ uint8_t FLASH_WritePage(uint32_t addr, const uint32_t *buf, uint32_t len)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: FLASH_Read
|
||||
* 功能描述: 读Flash内容
|
||||
* 形 参: addr:读取区域起始地址
|
||||
buf:数据存储区
|
||||
len:要读取的字节数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: FLASH_Read
|
||||
* 功能描述: 读Flash内容
|
||||
* 形 参: addr:读取区域起始地址
|
||||
buf:数据存储区
|
||||
len:要读取的字节数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
status_t FLASH_Read(uint32_t addr, uint32_t *buf, uint32_t len)
|
||||
{
|
||||
|
@ -680,12 +679,12 @@ status_t FLASH_Read(uint32_t addr, uint32_t *buf, uint32_t len)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flash_erase
|
||||
* 功能描述: 擦除Flash指定长度的空间
|
||||
* 形 参: addr:擦除区域起始地址
|
||||
byte_cnt:要擦除的字节数,以4k字节为最小擦除单位
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 注 释: 不满4k字节的,也需要擦除掉4k字节
|
||||
* 函 数 名: flash_erase
|
||||
* 功能描述: 擦除Flash指定长度的空间
|
||||
* 形 参: addr:擦除区域起始地址
|
||||
byte_cnt:要擦除的字节数,以4k字节为最小擦除单位
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 注 释: 不满4k字节的,也需要擦除掉4k字节
|
||||
*******************************************************************************/
|
||||
status_t flash_erase(uint32_t start_addr, uint32_t byte_cnt)
|
||||
{
|
||||
|
@ -707,12 +706,12 @@ status_t flash_erase(uint32_t start_addr, uint32_t byte_cnt)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flash_write
|
||||
* 功能描述: 在指定的flash起始地址写入指定长度的数据
|
||||
* 形 参: addr:写入区域起始地址
|
||||
buf:数据存储区
|
||||
byte_cnt:要写入的字节数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flash_write
|
||||
* 功能描述: 在指定的flash起始地址写入指定长度的数据
|
||||
* 形 参: addr:写入区域起始地址
|
||||
buf:数据存储区
|
||||
byte_cnt:要写入的字节数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
status_t flash_write(uint32_t start_addr, uint8_t *buf, uint32_t byte_cnt)
|
||||
{
|
||||
|
@ -736,12 +735,12 @@ status_t flash_write(uint32_t start_addr, uint8_t *buf, uint32_t byte_cnt)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flash_read
|
||||
* 功能描述: 读Flash内容
|
||||
* 形 参: addr:读取区域起始地址
|
||||
buf:数据存储区
|
||||
len:要读取的字节数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flash_read
|
||||
* 功能描述: 读Flash内容
|
||||
* 形 参: addr:读取区域起始地址
|
||||
buf:数据存储区
|
||||
len:要读取的字节数
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
status_t flash_read(uint32_t addr, uint8_t *buf, uint32_t len)
|
||||
{
|
||||
|
@ -768,12 +767,12 @@ status_t flash_read(uint32_t addr, uint8_t *buf, uint32_t len)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: flash_copy
|
||||
* 功能描述: 实现flash数据在分区之间的拷贝
|
||||
* 形 参: srcAddr:源flash的起始地址
|
||||
dstAddr:目标flash的起始地址;
|
||||
imageSize:要拷贝的flash空间大小,单位为字节
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 函 数 名: flash_copy
|
||||
* 功能描述: 实现flash数据在分区之间的拷贝
|
||||
* 形 参: srcAddr:源flash的起始地址
|
||||
dstAddr:目标flash的起始地址;
|
||||
imageSize:要拷贝的flash空间大小,单位为字节
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
status_t flash_copy(uint32_t srcAddr,uint32_t dstAddr, uint32_t imageSize)
|
||||
{
|
||||
|
@ -834,11 +833,11 @@ status_t flash_copy(uint32_t srcAddr,uint32_t dstAddr, uint32_t imageSize)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: NOR_FLASH_Erase
|
||||
* 功能描述: 以扇区为擦除单位擦除Flash指定长度的空间,最终擦除的字节可能大于imageSize
|
||||
* 形 参: addr:擦除区域起始地址
|
||||
imageSize:要擦除的字节数
|
||||
* 返 回 值: None
|
||||
* 函 数 名: NOR_FLASH_Erase
|
||||
* 功能描述: 以扇区为擦除单位擦除Flash指定长度的空间,最终擦除的字节可能大于imageSize
|
||||
* 形 参: addr:擦除区域起始地址
|
||||
imageSize:要擦除的字节数
|
||||
* 返 回 值: None
|
||||
*******************************************************************************/
|
||||
status_t NOR_FLASH_Erase(uint32_t app_base_addr,uint32_t imageSize)
|
||||
{
|
||||
|
@ -860,13 +859,13 @@ status_t NOR_FLASH_Erase(uint32_t app_base_addr,uint32_t imageSize)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: NorFlash_Write_PageProgram
|
||||
* 功能描述: 写入Flash指定长度的数据
|
||||
* 形 参: pBuffer:数据存储区
|
||||
WriteAddr:写入区域起始地址
|
||||
NumByteToWrite:要写入的字节数(最大256)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 注 释: 在指定地址开始写入最大256字节的数据
|
||||
* 函 数 名: NorFlash_Write_PageProgram
|
||||
* 功能描述: 写入Flash指定长度的数据
|
||||
* 形 参: pBuffer:数据存储区
|
||||
WriteAddr:写入区域起始地址
|
||||
NumByteToWrite:要写入的字节数(最大256)
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
* 注 释: 在指定地址开始写入最大256字节的数据
|
||||
*******************************************************************************/
|
||||
void NorFlash_Write_PageProgram(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t NumByteToWrite)
|
||||
{
|
||||
|
@ -883,24 +882,24 @@ void NorFlash_Write_PageProgram(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t Num
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: NorFlash_Write_NoCheck
|
||||
* 功能描述: 无检验写入W25QXX从指定地址开始指定长度的数据
|
||||
* 形 参: pBuffer:数据存储区
|
||||
WriteAddr:开始写入的地址(24bit)
|
||||
NumByteToWrite:要写入的字节数(最大65535)
|
||||
* 返 回 值: 无
|
||||
* 注 释: 必须确保所写的地址范围内的数据全部为0XFF,否则在非0XFF处写入的数据将失败!
|
||||
具有自动换页功能,在指定地址开始写入指定长度的数据,但是要确保地址不越界!
|
||||
* 函 数 名: NorFlash_Write_NoCheck
|
||||
* 功能描述: 无检验写入W25QXX从指定地址开始指定长度的数据
|
||||
* 形 参: pBuffer:数据存储区
|
||||
WriteAddr:开始写入的地址(24bit)
|
||||
NumByteToWrite:要写入的字节数(最大65535)
|
||||
* 返 回 值: 无
|
||||
* 注 释: 必须确保所写的地址范围内的数据全部为0XFF,否则在非0XFF处写入的数据将失败!
|
||||
具有自动换页功能,在指定地址开始写入指定长度的数据,但是要确保地址不越界!
|
||||
*******************************************************************************/
|
||||
void NorFlash_Write_NoCheck(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t NumByteToWrite)
|
||||
{
|
||||
uint16_t pageRemain;
|
||||
|
||||
pageRemain = 256 - WriteAddr%256;//单页剩余的字节数
|
||||
pageRemain = 256 - WriteAddr%256;//单页剩余的字节数
|
||||
|
||||
if(NumByteToWrite <= pageRemain)
|
||||
{
|
||||
pageRemain = NumByteToWrite;//不大于256个字节
|
||||
pageRemain = NumByteToWrite;//不大于256个字节
|
||||
}
|
||||
|
||||
while(1)
|
||||
|
@ -908,21 +907,21 @@ void NorFlash_Write_NoCheck(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t NumByte
|
|||
NorFlash_Write_PageProgram(pBuffer,WriteAddr,pageRemain);
|
||||
if(NumByteToWrite == pageRemain)
|
||||
{
|
||||
break;//写入结束了
|
||||
break;//写入结束了
|
||||
}
|
||||
else //NumByteToWrite>pageRemain
|
||||
{
|
||||
pBuffer += pageRemain;
|
||||
WriteAddr += pageRemain;
|
||||
|
||||
NumByteToWrite -= pageRemain;//减去已经写入了的字节数
|
||||
NumByteToWrite -= pageRemain;//减去已经写入了的字节数
|
||||
if(NumByteToWrite > 256)
|
||||
{
|
||||
pageRemain = 256;//一次可以写入256个字节
|
||||
pageRemain = 256;//一次可以写入256个字节
|
||||
}
|
||||
else
|
||||
{
|
||||
pageRemain = NumByteToWrite;//不够256个字节了
|
||||
pageRemain = NumByteToWrite;//不够256个字节了
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -930,13 +929,13 @@ void NorFlash_Write_NoCheck(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t NumByte
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: NorFlash_Write
|
||||
* 功能描述: 写入W25QXX在指定地址开始写入指定长度的数据
|
||||
* 形 参: pBuffer:数据存储区
|
||||
WriteAddr:开始写入的地址(24bit)
|
||||
NumByteToWrite:要写入的字节数(最大65535)
|
||||
* 返 回 值: None
|
||||
* 注 释: 该函数带擦除操作
|
||||
* 函 数 名: NorFlash_Write
|
||||
* 功能描述: 写入W25QXX在指定地址开始写入指定长度的数据
|
||||
* 形 参: pBuffer:数据存储区
|
||||
WriteAddr:开始写入的地址(24bit)
|
||||
NumByteToWrite:要写入的字节数(最大65535)
|
||||
* 返 回 值: None
|
||||
* 注 释: 该函数带擦除操作
|
||||
*******************************************************************************/
|
||||
void NorFlash_Write(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t NumByteToWrite)
|
||||
{
|
||||
|
@ -946,61 +945,61 @@ void NorFlash_Write(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t NumByteToWrite)
|
|||
uint16_t i;
|
||||
uint8_t *NorFlash_BUF = 0;
|
||||
|
||||
NorFlash_BUF = NorFlash_BUFFER;//RAM缓冲区4K
|
||||
NorFlash_BUF = NorFlash_BUFFER;//RAM缓冲区4K
|
||||
|
||||
WriteAddr &= 0x0FFFFFFF;
|
||||
|
||||
secPos = WriteAddr/SECTOR_SIZE;//扇区地址
|
||||
secOff = WriteAddr%SECTOR_SIZE;//在扇区内的偏移
|
||||
secRemain = SECTOR_SIZE - secOff;//扇区剩余空间大小
|
||||
secPos = WriteAddr/SECTOR_SIZE;//扇区地址
|
||||
secOff = WriteAddr%SECTOR_SIZE;//在扇区内的偏移
|
||||
secRemain = SECTOR_SIZE - secOff;//扇区剩余空间大小
|
||||
|
||||
if(NumByteToWrite <= secRemain)
|
||||
{
|
||||
secRemain = NumByteToWrite;//不大于4096个字节
|
||||
secRemain = NumByteToWrite;//不大于4096个字节
|
||||
}
|
||||
while(1)
|
||||
{
|
||||
FLASH_Read(FLASH_BASE + secPos*SECTOR_SIZE, (void *)NorFlash_BUF, SECTOR_SIZE);//读出整个扇区的内容
|
||||
for(i=0;i<secRemain;i++)//校验数据
|
||||
FLASH_Read(CHIP_FLAH_BASE + secPos*SECTOR_SIZE, (void *)NorFlash_BUF, SECTOR_SIZE);//读出整个扇区的内容
|
||||
for(i=0;i<secRemain;i++)//校验数据
|
||||
{
|
||||
if(NorFlash_BUF[secOff+i] != 0xFF)
|
||||
{
|
||||
break;//需要擦除
|
||||
break;//需要擦除
|
||||
}
|
||||
}
|
||||
if(i < secRemain)//需要擦除
|
||||
if(i < secRemain)//需要擦除
|
||||
{
|
||||
FLASH_EraseSector(FLASH_BASE + secPos*SECTOR_SIZE);
|
||||
for(i=0;i<secRemain;i++)//复制
|
||||
FLASH_EraseSector(CHIP_FLAH_BASE + secPos*SECTOR_SIZE);
|
||||
for(i=0;i<secRemain;i++)//复制
|
||||
{
|
||||
NorFlash_BUF[i+secOff] = pBuffer[i];
|
||||
}
|
||||
NorFlash_Write_NoCheck(NorFlash_BUF,FLASH_BASE + secPos*SECTOR_SIZE,SECTOR_SIZE);//写入整个扇区
|
||||
NorFlash_Write_NoCheck(NorFlash_BUF,CHIP_FLAH_BASE + secPos*SECTOR_SIZE,SECTOR_SIZE);//写入整个扇区
|
||||
}
|
||||
else
|
||||
{
|
||||
NorFlash_Write_NoCheck(pBuffer,FLASH_BASE + WriteAddr,secRemain);//写已经擦除了的,直接写入扇区剩余区间.
|
||||
NorFlash_Write_NoCheck(pBuffer,CHIP_FLAH_BASE + WriteAddr,secRemain);//写已经擦除了的,直接写入扇区剩余区间.
|
||||
}
|
||||
|
||||
if(NumByteToWrite == secRemain)
|
||||
{
|
||||
break;//写入结束了
|
||||
break;//写入结束了
|
||||
}
|
||||
else//写入未结束
|
||||
else//写入未结束
|
||||
{
|
||||
secPos++;//扇区地址增1
|
||||
secOff=0;//偏移位置为0
|
||||
secPos++;//扇区地址增1
|
||||
secOff=0;//偏移位置为0
|
||||
|
||||
pBuffer += secRemain;//指针偏移
|
||||
WriteAddr += secRemain;//写地址偏移
|
||||
NumByteToWrite -= secRemain;//字节数递减
|
||||
pBuffer += secRemain;//指针偏移
|
||||
WriteAddr += secRemain;//写地址偏移
|
||||
NumByteToWrite -= secRemain;//字节数递减
|
||||
if(NumByteToWrite > SECTOR_SIZE)
|
||||
{
|
||||
secRemain = SECTOR_SIZE;//下一个扇区还是写不完
|
||||
secRemain = SECTOR_SIZE;//下一个扇区还是写不完
|
||||
}
|
||||
else
|
||||
{
|
||||
secRemain = NumByteToWrite;//下一个扇区可以写完了
|
||||
secRemain = NumByteToWrite;//下一个扇区可以写完了
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1008,12 +1007,12 @@ void NorFlash_Write(uint8_t* pBuffer,uint32_t WriteAddr,uint16_t NumByteToWrite)
|
|||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: NOR_FLASH_Write
|
||||
* 功能描述: 写入W25QXX在指定地址开始写入指定长度的数据
|
||||
* 形 参: FlashAddress:用于存储当前写入Flash地址的指针,写入过程中会移动
|
||||
Data:要写入数据存储区
|
||||
DataLength:要写入的字节数
|
||||
* 返 回 值: 0
|
||||
* 函 数 名: NOR_FLASH_Write
|
||||
* 功能描述: 写入W25QXX在指定地址开始写入指定长度的数据
|
||||
* 形 参: FlashAddress:用于存储当前写入Flash地址的指针,写入过程中会移动
|
||||
Data:要写入数据存储区
|
||||
DataLength:要写入的字节数
|
||||
* 返 回 值: 0
|
||||
*******************************************************************************/
|
||||
#ifndef USE_HIGHT_SPEED_TRANS
|
||||
uint32_t NOR_FLASH_Write(uint32_t* FlashAddress, uint8_t* Data ,uint16_t DataLength)
|
||||
|
|
|
@ -1,224 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2020 AIIT XUOS Lab
|
||||
* XiUOS is licensed under Mulan PSL v2.
|
||||
* You can use this software according to the terms and conditions of the Mulan PSL v2.
|
||||
* You may obtain a copy of Mulan PSL v2 at:
|
||||
* http://license.coscl.org.cn/MulanPSL2
|
||||
* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
|
||||
* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
|
||||
* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
|
||||
* See the Mulan PSL v2 for more details.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file: imxrt_ota.c
|
||||
* @brief: file imxrt_ota.c
|
||||
* @version: 1.0
|
||||
* @author: AIIT XUOS Lab
|
||||
* @date: 2023/3/24
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <time.h>
|
||||
#include <string.h>
|
||||
#include "flash.h"
|
||||
#include "common.h"
|
||||
#include "imxrt_ota.h"
|
||||
|
||||
|
||||
static const uint32_t crc32tab[] = {
|
||||
0x00000000, 0x77073096, 0xee0e612c, 0x990951ba,
|
||||
0x076dc419, 0x706af48f, 0xe963a535, 0x9e6495a3,
|
||||
0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988,
|
||||
0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91,
|
||||
0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de,
|
||||
0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7,
|
||||
0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec,
|
||||
0x14015c4f, 0x63066cd9, 0xfa0f3d63, 0x8d080df5,
|
||||
0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172,
|
||||
0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b,
|
||||
0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940,
|
||||
0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59,
|
||||
0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116,
|
||||
0x21b4f4b5, 0x56b3c423, 0xcfba9599, 0xb8bda50f,
|
||||
0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924,
|
||||
0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d,
|
||||
0x76dc4190, 0x01db7106, 0x98d220bc, 0xefd5102a,
|
||||
0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433,
|
||||
0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818,
|
||||
0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01,
|
||||
0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e,
|
||||
0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457,
|
||||
0x65b0d9c6, 0x12b7e950, 0x8bbeb8ea, 0xfcb9887c,
|
||||
0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65,
|
||||
0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2,
|
||||
0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb,
|
||||
0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0,
|
||||
0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9,
|
||||
0x5005713c, 0x270241aa, 0xbe0b1010, 0xc90c2086,
|
||||
0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
|
||||
0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4,
|
||||
0x59b33d17, 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad,
|
||||
0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a,
|
||||
0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683,
|
||||
0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8,
|
||||
0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1,
|
||||
0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe,
|
||||
0xf762575d, 0x806567cb, 0x196c3671, 0x6e6b06e7,
|
||||
0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc,
|
||||
0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5,
|
||||
0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252,
|
||||
0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b,
|
||||
0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60,
|
||||
0xdf60efc3, 0xa867df55, 0x316e8eef, 0x4669be79,
|
||||
0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236,
|
||||
0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f,
|
||||
0xc5ba3bbe, 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04,
|
||||
0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d,
|
||||
0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a,
|
||||
0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713,
|
||||
0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38,
|
||||
0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21,
|
||||
0x86d3d2d4, 0xf1d4e242, 0x68ddb3f8, 0x1fda836e,
|
||||
0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777,
|
||||
0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c,
|
||||
0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45,
|
||||
0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2,
|
||||
0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db,
|
||||
0xaed16a4a, 0xd9d65adc, 0x40df0b66, 0x37d83bf0,
|
||||
0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
|
||||
0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6,
|
||||
0xbad03605, 0xcdd70693, 0x54de5729, 0x23d967bf,
|
||||
0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94,
|
||||
0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d
|
||||
};
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: calculate_crc32
|
||||
* 功能描述: 计算给定Flash内存地址范围中数据的CRC32校验和
|
||||
* 形 参: addr:表示Flash地址的起始位置
|
||||
len:表示需要计算CRC32的数据长度
|
||||
* 返 回 值: 计算得到的CRC32值
|
||||
*******************************************************************************/
|
||||
uint32_t calculate_crc32(uint32_t addr, uint32_t len)
|
||||
{
|
||||
uint32_t crc = 0xFFFFFFFF;
|
||||
uint8_t byte = 0xFF;
|
||||
|
||||
for(uint32_t i = 0; i < len; i++)
|
||||
{
|
||||
byte = *((volatile uint8_t *)(addr + i));
|
||||
crc = crc32tab[(crc ^ byte) & 0xff] ^ (crc >> 8);
|
||||
}
|
||||
return crc^0xFFFFFFFF;
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: UpdateOTAFlag
|
||||
* 功能描述: 更新OTA Flag区域的信息,版本完成下载后在app里进行调用
|
||||
* 形 参: ptr:ota_info_t结构体指针,描述OTA升级相关信息
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
status_t UpdateOTAFlag(ota_info_t *ptr)
|
||||
{
|
||||
status_t status;
|
||||
|
||||
status = flash_erase(FLAG_FLAH_ADDRESS,sizeof(ota_info_t));
|
||||
if(status != kStatus_Success)
|
||||
{
|
||||
return status;
|
||||
}
|
||||
status = flash_write(FLAG_FLAH_ADDRESS,(void *)ptr,sizeof(ota_info_t));
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: UpdateApplication
|
||||
* 功能描述: 在bootloader里进行调用,根据Flash中Flag分区中的信息决定是否进行版本更新
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
* 注 释: 该函数调用后无论结果如何都将跳转到app分区
|
||||
*******************************************************************************/
|
||||
void UpdateApplication(void)
|
||||
{
|
||||
status_t status;
|
||||
ota_info_t ota_info; // 定义OTA信息结构体
|
||||
|
||||
// 从Flash中读取OTA信息
|
||||
memcpy(&ota_info, (const void *)FLAG_FLAH_ADDRESS,sizeof(ota_info_t));
|
||||
|
||||
// 如果OTA升级状态为准备状态,且APP分区与download分区版本不同,才可以进行升级
|
||||
if((ota_info.status == OTA_STATUS_READY) && (ota_info.os.crc32 != ota_info.down.crc32))
|
||||
{
|
||||
Serial_PutString("\r\n------Start to update the app!------\r\n");
|
||||
// 校验downlad分区固件CRC
|
||||
if(calculate_crc32(DOWN_FLAH_ADDRESS, ota_info.down.size) == ota_info.down.crc32)
|
||||
{
|
||||
ota_info.status = OTA_STATUS_UPDATING;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
|
||||
// 1.如果CRC校验通过,开始升级,逐字节拷贝Flash,先备份当前XiUOS System分区内容
|
||||
status = flash_copy(XIUOS_FLAH_ADDRESS, BAKUP_FLAH_ADDRESS, ota_info.os.size);
|
||||
if((status == kStatus_Success) &&(calculate_crc32(BAKUP_FLAH_ADDRESS, ota_info.os.size) == ota_info.os.crc32))
|
||||
{
|
||||
Serial_PutString("\r\n------Backup app success!------\r\n");
|
||||
ota_info.bak.size = ota_info.os.size;
|
||||
ota_info.bak.crc32 = ota_info.os.crc32;
|
||||
ota_info.bak.version = ota_info.os.version;
|
||||
strncpy(ota_info.bak.description, ota_info.os.description, sizeof(ota_info.os.description));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
else
|
||||
{
|
||||
Serial_PutString("\r\n------Backup app failed!------\r\n");
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "Backup app failed!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
goto finish;
|
||||
}
|
||||
|
||||
// 2.拷贝download分区到XiUOS System分区
|
||||
status = flash_copy(DOWN_FLAH_ADDRESS, XIUOS_FLAH_ADDRESS, ota_info.down.size);
|
||||
if((status == kStatus_Success) &&(calculate_crc32(XIUOS_FLAH_ADDRESS, ota_info.down.size) == ota_info.down.crc32))
|
||||
{
|
||||
Serial_PutString("\r\n------The download partition is copied successfully!------\r\n");
|
||||
|
||||
ota_info.os.size = ota_info.down.size;
|
||||
ota_info.os.crc32 = ota_info.down.crc32;
|
||||
ota_info.os.version = ota_info.down.version;
|
||||
strncpy(ota_info.os.description, ota_info.down.description, sizeof(ota_info.down.description));
|
||||
ota_info.status == OTA_STATUS_IDLE; // 拷贝download分区到XiUOS System分区成功,将OTA升级状态设置为IDLE
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
else
|
||||
{
|
||||
Serial_PutString("\r\n------The download partition copy failed!------\r\n");
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "The download partition copy failed!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
goto finish;
|
||||
}
|
||||
|
||||
Serial_PutString("\r\n------Update completed!------\r\n");
|
||||
goto finish;
|
||||
}
|
||||
else
|
||||
{
|
||||
// 如果download分区CRC校验失败,升级失败
|
||||
Serial_PutString("\r\n------Download Firmware CRC check failed!------\r\n");
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "Download Firmware CRC check failed!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
goto finish;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Serial_PutString("\r\n------No need to update the app!------\r\n");
|
||||
goto finish;
|
||||
}
|
||||
finish:
|
||||
return;
|
||||
}
|
|
@ -15,112 +15,46 @@
|
|||
|
||||
#include <stdint.h>
|
||||
#include <xs_base.h>
|
||||
#include "imxrt_ota.h"
|
||||
#include "common.h"
|
||||
#include "mcuboot.h"
|
||||
#include "flash.h"
|
||||
|
||||
#ifdef MCUBOOT_BOOTLOADER
|
||||
extern void ImxrtMsDelay(uint32 ms);
|
||||
#ifdef TOOL_USING_OTA
|
||||
|
||||
|
||||
static void InitialVersion(void)
|
||||
void mcuboot_bord_init(void)
|
||||
{
|
||||
int32_t size;
|
||||
ota_info_t ota_info;
|
||||
|
||||
memset(&ota_info, 0, sizeof(ota_info_t));
|
||||
size = SerialDownload(XIUOS_FLAH_ADDRESS);
|
||||
if(size > 0)
|
||||
{
|
||||
ota_info.os.size = size;
|
||||
ota_info.os.crc32 = calculate_crc32(XIUOS_FLAH_ADDRESS, size);
|
||||
ota_info.os.version = 0x1;
|
||||
strncpy(ota_info.os.description, "This is the initial firmware for the device!", sizeof(ota_info.os.description));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void jump_to_application(void)
|
||||
{
|
||||
SCB->VTOR = (uint32_t)XIUOS_FLAH_ADDRESS;
|
||||
|
||||
asm volatile("LDR R0, = 0x60100000");
|
||||
asm volatile("LDR R0, [R0]");
|
||||
asm volatile("MOV SP, R0");
|
||||
|
||||
asm volatile("LDR R0, = 0x60100000+4");
|
||||
asm volatile("LDR R0, [R0]");
|
||||
asm volatile("BX R0");
|
||||
}
|
||||
|
||||
|
||||
void BootLoaderJumpApp(void)
|
||||
{
|
||||
uint8_t ch1, ch2;
|
||||
uint32_t ret;
|
||||
ota_info_t ota_info;
|
||||
uint32_t timeout = 500;
|
||||
|
||||
BOARD_ConfigMPU();
|
||||
BOARD_InitPins();
|
||||
BOARD_BootClockRUN();
|
||||
UartConfig();
|
||||
SysTick_Config(SystemCoreClock / TICK_PER_SECOND);
|
||||
}
|
||||
|
||||
Serial_PutString("Please press 'space' key into menu in 5s !!!\r\n");
|
||||
void mcuboot_reset(void)
|
||||
{
|
||||
__set_FAULTMASK(1);
|
||||
NVIC_SystemReset();
|
||||
}
|
||||
|
||||
void mcuboot_jump(void)
|
||||
{
|
||||
uint32_t addr = XIUOS_FLAH_ADDRESS;
|
||||
|
||||
SCB->VTOR = addr;
|
||||
asm volatile("LDR R0, %0" : : "m"(addr));
|
||||
asm volatile("LDR R0, [R0]");
|
||||
asm volatile("MOV SP, R0");
|
||||
|
||||
while(timeout)
|
||||
{
|
||||
ret = (SerialKeyPressed((uint8_t*)&ch1));
|
||||
if(ret) break;
|
||||
timeout--;
|
||||
ImxrtMsDelay(10);
|
||||
}
|
||||
addr += 4;
|
||||
asm volatile("LDR R0, %0" : : "m"(addr));
|
||||
asm volatile("LDR R0, [R0]");
|
||||
asm volatile("BX R0");
|
||||
}
|
||||
|
||||
while(1)
|
||||
{
|
||||
if((ret)&&(ch1 == 0x20))
|
||||
{
|
||||
Serial_PutString("\r\nPlease slecet:");
|
||||
Serial_PutString("\r\n 1:run app");
|
||||
Serial_PutString("\r\n 2:update app");
|
||||
Serial_PutString("\r\n 3:reboot \r\n");
|
||||
extern void ImxrtMsDelay(uint32 ms);
|
||||
|
||||
ch2 = GetKey();
|
||||
switch(ch2)
|
||||
{
|
||||
case 0x31:
|
||||
jump_to_application();
|
||||
break;
|
||||
|
||||
case 0x32:
|
||||
FLASH_Init();
|
||||
memcpy(&ota_info, (const void *)FLAG_FLAH_ADDRESS,sizeof(ota_info_t));
|
||||
/* 此时APP分区还没有有效的固件,需要在bootloader下通过iap烧写出厂固件 */
|
||||
if((ota_info.os.size > APP_FLASH_SIZE) || (calculate_crc32(XIUOS_FLAH_ADDRESS, ota_info.os.size) != ota_info.os.crc32))
|
||||
{
|
||||
Serial_PutString("\r\nNeed to flash initial firmware!\r\n");
|
||||
InitialVersion();
|
||||
}
|
||||
else
|
||||
{
|
||||
UpdateApplication();
|
||||
}
|
||||
FLASH_DeInit();
|
||||
jump_to_application();
|
||||
break;
|
||||
|
||||
case 0x33:
|
||||
__set_FAULTMASK(1);
|
||||
NVIC_SystemReset();
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
jump_to_application();
|
||||
}
|
||||
}
|
||||
void mcuboot_delay(uint32_t ms)
|
||||
{
|
||||
ImxrtMsDelay(ms);
|
||||
}
|
||||
#endif
|
|
@ -17,7 +17,7 @@
|
|||
* @author: AIIT XUOS Lab
|
||||
* @date: 2023/3/24
|
||||
*/
|
||||
|
||||
#include <xs_base.h>
|
||||
#include "ymodem.h"
|
||||
#include "string.h"
|
||||
#include "flash.h"
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
|
||||
/**
|
||||
* @file fsl_flash.h
|
||||
* @file flash.h
|
||||
* @brief support flexspi norflash function
|
||||
* @version 2.0
|
||||
* @author AIIT XUOS Lab
|
||||
|
@ -16,25 +16,19 @@
|
|||
#ifndef __FLASH_H__
|
||||
#define __FLASH_H__
|
||||
|
||||
#include <xs_base.h>
|
||||
#include <stdint.h>
|
||||
#include "fsl_romapi.h"
|
||||
|
||||
#define USE_HIGHT_SPEED_TRANS 1
|
||||
#define FLASH_BASE 0x60000000
|
||||
#define SECTOR_SIZE 0x1000
|
||||
#define FLASH_PAGE_SIZE 256
|
||||
#define APP_FLASH_SIZE 0x100000 //Application package size is limited to 1M
|
||||
|
||||
#define FLEXSPI_WAIT_TIMEOUT_NS (500000000UL) //FlexSPI timeout value, 500ms
|
||||
#define FLEXSPI_FREQ_1GHz (1000000000UL)
|
||||
#define FREQ_1MHz (1000000UL)
|
||||
#define FLEXSPI_DLLCR_DEFAULT (0x100UL)
|
||||
|
||||
#define XIUOS_FLAH_ADDRESS 0x60100000
|
||||
#define BAKUP_FLAH_ADDRESS 0x60300000
|
||||
#define DOWN_FLAH_ADDRESS 0x60500000
|
||||
#define FLAG_FLAH_ADDRESS 0x60700000
|
||||
|
||||
enum
|
||||
{
|
||||
kFlexSpiDelayCellUnit_Min = 75, // 75ps
|
||||
|
|
|
@ -22,8 +22,12 @@
|
|||
#include "fsl_iomuxc.h"
|
||||
#include "fsl_gpio.h"
|
||||
#include "fsl_lpuart.h"
|
||||
#include "common.h"
|
||||
|
||||
void jump_to_application(void);
|
||||
void mcuboot_bord_init(void);
|
||||
void mcuboot_reset(void);
|
||||
void mcuboot_jump(void);
|
||||
void mcuboot_delay(uint32_t ms);
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -555,6 +555,11 @@ KERNELPATHS +=-I$(KERNEL_ROOT)/tool/shell/letter-shell \
|
|||
-I$(KERNEL_ROOT)/tool/shell/letter-shell/file_ext #
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_TOOL_USING_OTA), y)
|
||||
KERNELPATHS +=-I$(KERNEL_ROOT)/tool/bootloader/flash \
|
||||
-I$(KERNEL_ROOT)/tool/bootloader/ota #
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_FS_LWEXT4),y)
|
||||
KERNELPATHS += -I$(KERNEL_ROOT)/fs/lwext4/lwext4_submodule/blockdev/xiuos #
|
||||
KERNELPATHS += -I$(KERNEL_ROOT)/fs/lwext4/lwext4_submodule/include #
|
||||
|
|
|
@ -0,0 +1,5 @@
|
|||
menu "Tool feature"
|
||||
|
||||
source "$KERNEL_DIR/tool/bootloader/Kconfig"
|
||||
|
||||
endmenu
|
|
@ -4,4 +4,8 @@ ifeq ($(CONFIG_TOOL_SHELL),y)
|
|||
SRC_DIR += shell
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_TOOL_USING_OTA),y)
|
||||
SRC_DIR += bootloader
|
||||
endif
|
||||
|
||||
include $(KERNEL_ROOT)/compiler.mk
|
||||
|
|
|
@ -0,0 +1,48 @@
|
|||
menu "OTA function"
|
||||
|
||||
menuconfig TOOL_USING_OTA
|
||||
bool "Enable support OTA function"
|
||||
default n
|
||||
|
||||
if TOOL_USING_OTA
|
||||
choice
|
||||
prompt "Compile bootloader bin or application bin."
|
||||
default MCUBOOT_BOOTLOADER
|
||||
|
||||
config MCUBOOT_BOOTLOADER
|
||||
bool "Config as bootloader."
|
||||
|
||||
config MCUBOOT_APPLICATION
|
||||
bool "Config as application."
|
||||
endchoice
|
||||
|
||||
|
||||
menu "Flash area address and size configuration."
|
||||
config CHIP_FLAH_BASE
|
||||
hex "Flash base address of the chip."
|
||||
default 0x60000000
|
||||
|
||||
config XIUOS_FLAH_ADDRESS
|
||||
hex "Flash area address of the XiUOS system."
|
||||
default 0x60100000
|
||||
|
||||
config BAKUP_FLAH_ADDRESS
|
||||
hex "Flash area address of the backup firmware."
|
||||
default 0x60300000
|
||||
|
||||
config DOWN_FLAH_ADDRESS
|
||||
hex "Flash area address of the downloaded firmware."
|
||||
default 0x60500000
|
||||
|
||||
config FLAG_FLAH_ADDRESS
|
||||
hex "Flash area address of the OTA information."
|
||||
default 0x60700000
|
||||
|
||||
config APP_FLASH_SIZE
|
||||
hex "Application package size,the default size is limited to 1M."
|
||||
default 0x00100000
|
||||
endmenu
|
||||
|
||||
endif
|
||||
|
||||
endmenu
|
|
@ -0,0 +1,4 @@
|
|||
SRC_DIR :=
|
||||
SRC_DIR += flash ota
|
||||
|
||||
include $(KERNEL_ROOT)/compiler.mk
|
|
@ -0,0 +1,3 @@
|
|||
SRC_FILES := flash_ops.c
|
||||
|
||||
include $(KERNEL_ROOT)/compiler.mk
|
|
@ -0,0 +1,47 @@
|
|||
/*
|
||||
* Copyright 2018-2020 NXP
|
||||
* All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file flash_ops.h
|
||||
* @brief support flash function
|
||||
* @version 2.0
|
||||
* @author AIIT XUOS Lab
|
||||
* @date 2023-04-03
|
||||
*/
|
||||
#ifndef __FLASH_OPS_H__
|
||||
#define __FLASH_OPS_H__
|
||||
|
||||
|
||||
#include <flash.h>
|
||||
|
||||
typedef struct
|
||||
{
|
||||
/* board init function*/
|
||||
void (*board_init)(void);
|
||||
void (*serial_init)(void);
|
||||
void (*print_string)(uint8_t *s);
|
||||
|
||||
/* flash Driver operation */
|
||||
void (*flash_init)(void);
|
||||
void (*flash_deinit)(void);
|
||||
|
||||
/* flash operation */
|
||||
status_t (*op_flash_erase)(uint32_t start_addr, uint32_t byte_cnt);
|
||||
status_t (*op_flash_write)(uint32_t start_addr, uint8_t *buf, uint32_t byte_cnt);
|
||||
status_t (*op_flash_read)(uint32_t addr, uint8_t *buf, uint32_t len);
|
||||
status_t (*op_flash_copy)(uint32_t srcAddr,uint32_t dstAddr, uint32_t imageSize);
|
||||
|
||||
/* Burn the initialization version */
|
||||
int32_t (*download_by_serial)(const uint32_t addr);
|
||||
|
||||
/* system operation */
|
||||
void(*op_reset)(void);
|
||||
void(*op_jump)(void);
|
||||
void(*op_delay)(uint32_t ms);
|
||||
}mcuboot_t;
|
||||
|
||||
#endif
|
|
@ -0,0 +1,3 @@
|
|||
SRC_FILES := ota.c
|
||||
|
||||
include $(KERNEL_ROOT)/compiler.mk
|
|
@ -0,0 +1,441 @@
|
|||
/*
|
||||
* Copyright 2018-2020 NXP
|
||||
* All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file ota.c
|
||||
* @brief file ota.c
|
||||
* @version 2.0
|
||||
* @author AIIT XUOS Lab
|
||||
* @date 2023-04-03
|
||||
*/
|
||||
#include "shell.h"
|
||||
#include "xsconfig.h"
|
||||
#include "mcuboot.h"
|
||||
#include "ymodem.h"
|
||||
#include "ota.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Private Function Prototypes
|
||||
****************************************************************************/
|
||||
static uint32_t calculate_crc32(uint32_t addr, uint32_t len);
|
||||
static void UpdateApplication(void);
|
||||
static void InitialVersion(void);
|
||||
static void BackupVersion(void);
|
||||
static void BootLoaderJumpApp(void);
|
||||
static status_t UpdateOTAFlag(ota_info_t *ptr);
|
||||
|
||||
#ifdef MCUBOOT_APPLICATION
|
||||
static void app_ota(void);
|
||||
#endif
|
||||
|
||||
|
||||
/****************************************************************************
|
||||
* Private Data
|
||||
****************************************************************************/
|
||||
static const mcuboot_t mcuboot =
|
||||
{
|
||||
mcuboot_bord_init,
|
||||
UartConfig,
|
||||
Serial_PutString,
|
||||
FLASH_Init,
|
||||
FLASH_DeInit,
|
||||
flash_erase,
|
||||
flash_write,
|
||||
flash_read,
|
||||
flash_copy,
|
||||
SerialDownload,
|
||||
mcuboot_reset,
|
||||
mcuboot_jump,
|
||||
mcuboot_delay
|
||||
};
|
||||
|
||||
static const uint32_t crc32tab[] = {
|
||||
0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, 0x706af48f, 0xe963a535, 0x9e6495a3,
|
||||
0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988, 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91,
|
||||
0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de, 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7,
|
||||
0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9, 0xfa0f3d63, 0x8d080df5,
|
||||
0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172, 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b,
|
||||
0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59,
|
||||
0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423, 0xcfba9599, 0xb8bda50f,
|
||||
0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924, 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d,
|
||||
0x76dc4190, 0x01db7106, 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433,
|
||||
0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818, 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01,
|
||||
0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e, 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457,
|
||||
0x65b0d9c6, 0x12b7e950, 0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65,
|
||||
0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, 0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb,
|
||||
0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0, 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9,
|
||||
0x5005713c, 0x270241aa, 0xbe0b1010, 0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
|
||||
0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17, 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad,
|
||||
0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a, 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683,
|
||||
0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8, 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1,
|
||||
0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb, 0x196c3671, 0x6e6b06e7,
|
||||
0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc, 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5,
|
||||
0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b,
|
||||
0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55, 0x316e8eef, 0x4669be79,
|
||||
0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236, 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f,
|
||||
0xc5ba3bbe, 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d,
|
||||
0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a, 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713,
|
||||
0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38, 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21,
|
||||
0x86d3d2d4, 0xf1d4e242, 0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777,
|
||||
0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, 0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45,
|
||||
0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2, 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db,
|
||||
0xaed16a4a, 0xd9d65adc, 0x40df0b66, 0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
|
||||
0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605, 0xcdd70693, 0x54de5729, 0x23d967bf,
|
||||
0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94, 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d
|
||||
};
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: calculate_crc32
|
||||
* 功能描述: 计算给定Flash内存地址范围中数据的CRC32校验和
|
||||
* 形 参: addr:表示Flash地址的起始位置
|
||||
len:表示需要计算CRC32的数据长度
|
||||
* 返 回 值: 计算得到的CRC32值
|
||||
*******************************************************************************/
|
||||
static uint32_t calculate_crc32(uint32_t addr, uint32_t len)
|
||||
{
|
||||
uint32_t crc = 0xFFFFFFFF;
|
||||
uint8_t byte = 0xFF;
|
||||
|
||||
for(uint32_t i = 0; i < len; i++)
|
||||
{
|
||||
byte = *((volatile uint8_t *)(addr + i));
|
||||
crc = crc32tab[(crc ^ byte) & 0xff] ^ (crc >> 8);
|
||||
}
|
||||
return crc^0xFFFFFFFF;
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: UpdateApplication
|
||||
* 功能描述: 在bootloader里进行调用,根据Flash中Flag分区中的信息决定是否进行版本更新
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
* 注 释: 该函数调用后无论结果如何都将跳转到app分区
|
||||
*******************************************************************************/
|
||||
static void UpdateApplication(void)
|
||||
{
|
||||
status_t status;
|
||||
ota_info_t ota_info; // 定义OTA信息结构体
|
||||
|
||||
// 从Flash中读取OTA信息
|
||||
mcuboot.op_flash_read(FLAG_FLAH_ADDRESS, (void*)&ota_info, sizeof(ota_info_t));
|
||||
|
||||
// 如果OTA升级状态为准备状态,且APP分区与download分区版本不同,才可以进行升级
|
||||
if((ota_info.status == OTA_STATUS_READY) && (ota_info.os.crc32 != ota_info.down.crc32))
|
||||
{
|
||||
mcuboot.print_string("\r\n------Start to update the app!------\r\n");
|
||||
// 校验downlad分区固件CRC
|
||||
if(calculate_crc32(DOWN_FLAH_ADDRESS, ota_info.down.size) == ota_info.down.crc32)
|
||||
{
|
||||
ota_info.status = OTA_STATUS_UPDATING;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
|
||||
// 1.如果CRC校验通过,开始升级,逐字节拷贝Flash,先备份当前XiUOS System分区内容
|
||||
status = mcuboot.op_flash_copy(XIUOS_FLAH_ADDRESS, BAKUP_FLAH_ADDRESS, ota_info.os.size);
|
||||
if((status == kStatus_Success) &&(calculate_crc32(BAKUP_FLAH_ADDRESS, ota_info.os.size) == ota_info.os.crc32))
|
||||
{
|
||||
mcuboot.print_string("\r\n------Backup app success!------\r\n");
|
||||
ota_info.bak.size = ota_info.os.size;
|
||||
ota_info.bak.crc32 = ota_info.os.crc32;
|
||||
ota_info.bak.version = ota_info.os.version;
|
||||
strncpy(ota_info.bak.description, ota_info.os.description, sizeof(ota_info.os.description));
|
||||
UpdateOTAFlag(&ota_info);;
|
||||
}
|
||||
else
|
||||
{
|
||||
mcuboot.print_string("\r\n------Backup app failed!------\r\n");
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "Backup app failed!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);;
|
||||
goto finish;
|
||||
}
|
||||
|
||||
// 2.拷贝download分区到XiUOS System分区
|
||||
status = mcuboot.op_flash_copy(DOWN_FLAH_ADDRESS, XIUOS_FLAH_ADDRESS, ota_info.down.size);
|
||||
if((status == kStatus_Success) &&(calculate_crc32(XIUOS_FLAH_ADDRESS, ota_info.down.size) == ota_info.down.crc32))
|
||||
{
|
||||
mcuboot.print_string("\r\n------The download partition is copied successfully!------\r\n");
|
||||
|
||||
ota_info.os.size = ota_info.down.size;
|
||||
ota_info.os.crc32 = ota_info.down.crc32;
|
||||
ota_info.os.version = ota_info.down.version;
|
||||
strncpy(ota_info.os.description, ota_info.down.description, sizeof(ota_info.down.description));
|
||||
ota_info.status == OTA_STATUS_IDLE; // 拷贝download分区到XiUOS System分区成功,将OTA升级状态设置为IDLE
|
||||
UpdateOTAFlag(&ota_info);;
|
||||
}
|
||||
else
|
||||
{
|
||||
mcuboot.print_string("\r\n------The download partition copy failed!------\r\n");
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "The download partition copy failed!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);;
|
||||
goto finish;
|
||||
}
|
||||
|
||||
mcuboot.print_string("\r\n------Update completed!------\r\n");
|
||||
goto finish;
|
||||
}
|
||||
else
|
||||
{
|
||||
// 如果download分区CRC校验失败,升级失败
|
||||
mcuboot.print_string("\r\n------Download Firmware CRC check failed!------\r\n");
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "Download Firmware CRC check failed!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);;
|
||||
goto finish;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
mcuboot.print_string("\r\n------No need to update the app!------\r\n");
|
||||
goto finish;
|
||||
}
|
||||
finish:
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: InitialVersion
|
||||
* 功能描述: 该函数可以烧写APP分区的初始化版本,初始化版本的版本号为0x1
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
static void InitialVersion(void)
|
||||
{
|
||||
int32_t size;
|
||||
ota_info_t ota_info;
|
||||
|
||||
memset(&ota_info, 0, sizeof(ota_info_t));
|
||||
size = mcuboot.download_by_serial(XIUOS_FLAH_ADDRESS);
|
||||
if(size > 0)
|
||||
{
|
||||
ota_info.os.size = size;
|
||||
ota_info.os.crc32 = calculate_crc32(XIUOS_FLAH_ADDRESS, size);
|
||||
ota_info.os.version = 0x1;
|
||||
strncpy(ota_info.os.description, "This is the initial firmware for the device!", sizeof(ota_info.os.description));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: BackupVersion
|
||||
* 功能描述: 版本回退函数,如果升级的APP存在bug导致无法跳转需调用此函数进行版本回退
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
static void BackupVersion(void)
|
||||
{
|
||||
status_t status;
|
||||
ota_info_t ota_info;
|
||||
mcuboot.op_flash_read(FLAG_FLAH_ADDRESS, (void*)&ota_info, sizeof(ota_info_t));
|
||||
|
||||
ota_info.status = OTA_STATUS_BACKUP;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
status = mcuboot.op_flash_copy(BAKUP_FLAH_ADDRESS, XIUOS_FLAH_ADDRESS, ota_info.bak.size);
|
||||
if((status == kStatus_Success) &&(calculate_crc32(XIUOS_FLAH_ADDRESS, ota_info.bak.size) == ota_info.bak.crc32))
|
||||
{
|
||||
mcuboot.print_string("\r\n------Backup app version success!------\r\n");
|
||||
ota_info.os.size = ota_info.bak.size;
|
||||
ota_info.os.crc32 = ota_info.bak.crc32;
|
||||
ota_info.os.version = ota_info.bak.version;
|
||||
strncpy(ota_info.os.description, ota_info.bak.description, sizeof(ota_info.bak.description));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
else
|
||||
{
|
||||
mcuboot.print_string("\r\n------Backup app version failed!------\r\n");
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "Backup app version failed!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: BootLoaderJumpApp
|
||||
* 功能描述: 上次跳转若是失败的,先从BAKUP分区进行恢复,然后再进行跳转
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
static void BootLoaderJumpApp(void)
|
||||
{
|
||||
ota_info_t ota_info;
|
||||
mcuboot.flash_init();
|
||||
mcuboot.op_flash_read(FLAG_FLAH_ADDRESS, (void*)&ota_info, sizeof(ota_info_t));
|
||||
|
||||
if(ota_info.lastjumpflag == JUMP_FAILED_FLAG)
|
||||
{
|
||||
mcuboot.print_string("\r\n------Bootloader false, begin backup!------\r\n");
|
||||
BackupVersion();
|
||||
}
|
||||
else
|
||||
{
|
||||
ota_info.lastjumpflag = JUMP_FAILED_FLAG;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
mcuboot.flash_deinit();
|
||||
mcuboot.op_jump();
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: UpdateOTAFlag
|
||||
* 功能描述: 更新OTA Flag区域的信息,版本完成下载后在app里进行调用
|
||||
* 形 参: ptr:ota_info_t结构体指针,描述OTA升级相关信息
|
||||
* 返 回 值: 如果函数执行成功,状态值为 kStatus_Success,否则状态值为其他错误码
|
||||
*******************************************************************************/
|
||||
static status_t UpdateOTAFlag(ota_info_t *ptr)
|
||||
{
|
||||
status_t status;
|
||||
|
||||
status = mcuboot.op_flash_erase(FLAG_FLAH_ADDRESS,sizeof(ota_info_t));
|
||||
if(status != kStatus_Success)
|
||||
{
|
||||
return status;
|
||||
}
|
||||
status = mcuboot.op_flash_write(FLAG_FLAH_ADDRESS,(void *)ptr,sizeof(ota_info_t));
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: app_ota
|
||||
* 功能描述: 在app中通过命令来进行ota升级,该函数与升级的命令关联
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
static void app_ota(void)
|
||||
{
|
||||
int32_t size;
|
||||
ota_info_t ota_info;
|
||||
|
||||
mcuboot.flash_init();
|
||||
mcuboot.serial_init();
|
||||
|
||||
mcuboot.op_flash_read(FLAG_FLAH_ADDRESS, (void*)&ota_info, sizeof(ota_info_t));
|
||||
ota_info.status = OTA_STATUS_DOWNLOADING;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
size = mcuboot.download_by_serial(DOWN_FLAH_ADDRESS);
|
||||
ota_info.status = OTA_STATUS_DOWNLOADED;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
if(size > 0)
|
||||
{
|
||||
ota_info.down.size = size;
|
||||
ota_info.down.crc32= calculate_crc32(DOWN_FLAH_ADDRESS, size);
|
||||
ota_info.down.version = ota_info.os.version + 1;
|
||||
strncpy(ota_info.down.description, "OTA Test!",sizeof(ota_info.down.description));
|
||||
ota_info.status = OTA_STATUS_READY;
|
||||
strncpy(ota_info.error_message, "No error message!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
else
|
||||
{
|
||||
ota_info.status = OTA_STATUS_ERROR;
|
||||
strncpy(ota_info.error_message, "Failed to download firmware to download partition!",sizeof(ota_info.error_message));
|
||||
UpdateOTAFlag(&ota_info);
|
||||
}
|
||||
mcuboot.flash_deinit();
|
||||
mcuboot.op_reset();
|
||||
}
|
||||
SHELL_EXPORT_CMD(SHELL_CMD_PERMISSION(0)|SHELL_CMD_TYPE(SHELL_TYPE_CMD_FUNC)|SHELL_CMD_PARAM_NUM(0),ota, app_ota, ota function);
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: app_clear_jumpflag
|
||||
* 功能描述: 跳转app成功后,在app中调用将lastjumpflag重置为0XCDCDCDCD
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
void app_clear_jumpflag(void)
|
||||
{
|
||||
mcuboot.flash_init();
|
||||
//跳转成功设置lastjumpflag为JUMP_SUCCESS_FLAG
|
||||
ota_info_t ota_info;
|
||||
mcuboot.op_flash_read(FLAG_FLAH_ADDRESS, (void*)&ota_info, sizeof(ota_info_t));
|
||||
ota_info.lastjumpflag = JUMP_SUCCESS_FLAG;
|
||||
UpdateOTAFlag(&ota_info);
|
||||
mcuboot.flash_deinit();
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
* 函 数 名: ota_entry
|
||||
* 功能描述: bootloader的入口函数
|
||||
* 形 参: 无
|
||||
* 返 回 值: 无
|
||||
*******************************************************************************/
|
||||
void ota_entry(void)
|
||||
{
|
||||
uint8_t ch1, ch2;
|
||||
uint32_t ret;
|
||||
ota_info_t ota_info;
|
||||
uint32_t timeout = 1000;
|
||||
|
||||
mcuboot.board_init();
|
||||
|
||||
mcuboot.print_string("Please press 'space' key into menu in 10s !!!\r\n");
|
||||
|
||||
while(timeout)
|
||||
{
|
||||
ret = (SerialKeyPressed((uint8_t*)&ch1));
|
||||
if(ret) break;
|
||||
timeout--;
|
||||
mcuboot.op_delay(10);
|
||||
}
|
||||
|
||||
while(1)
|
||||
{
|
||||
|
||||
if((ret)&&(ch1 == 0x20))
|
||||
{
|
||||
mcuboot.print_string("\r\nPlease slecet:");
|
||||
|
||||
mcuboot.print_string("\r\n 1:run app");
|
||||
mcuboot.print_string("\r\n 2:update app");
|
||||
mcuboot.print_string("\r\n 3:reboot \r\n");
|
||||
|
||||
|
||||
ch2 = GetKey();
|
||||
switch(ch2)
|
||||
{
|
||||
case 0x31:
|
||||
BootLoaderJumpApp();
|
||||
break;
|
||||
|
||||
case 0x32:
|
||||
mcuboot.flash_init();
|
||||
mcuboot.op_flash_read(FLAG_FLAH_ADDRESS, (void*)&ota_info, sizeof(ota_info_t));
|
||||
/* 此时APP分区还没有有效的固件,需要在bootloader下通过iap烧写出厂固件 */
|
||||
if((ota_info.os.size > APP_FLASH_SIZE) || (calculate_crc32(XIUOS_FLAH_ADDRESS, ota_info.os.size) != ota_info.os.crc32))
|
||||
{
|
||||
mcuboot.print_string("\r\nNeed to flash initial firmware!\r\n");
|
||||
InitialVersion();
|
||||
}
|
||||
else
|
||||
{
|
||||
UpdateApplication();
|
||||
}
|
||||
|
||||
mcuboot.flash_deinit();
|
||||
BootLoaderJumpApp();
|
||||
break;
|
||||
|
||||
case 0x33:
|
||||
mcuboot.op_reset();
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
BootLoaderJumpApp();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,38 +1,32 @@
|
|||
/*
|
||||
* Copyright (c) 2020 AIIT XUOS Lab
|
||||
* XiUOS is licensed under Mulan PSL v2.
|
||||
* You can use this software according to the terms and conditions of the Mulan PSL v2.
|
||||
* You may obtain a copy of Mulan PSL v2 at:
|
||||
* http://license.coscl.org.cn/MulanPSL2
|
||||
* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
|
||||
* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
|
||||
* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
|
||||
* See the Mulan PSL v2 for more details.
|
||||
*/
|
||||
|
||||
* Copyright 2018-2020 NXP
|
||||
* All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file: imxrt_ota.h
|
||||
* @brief: file imxrt_ota.h
|
||||
* @version: 1.0
|
||||
* @author: AIIT XUOS Lab
|
||||
* @date: 2023/3/24
|
||||
* @file ota.h
|
||||
* @brief file ota.h
|
||||
* @version 2.0
|
||||
* @author AIIT XUOS Lab
|
||||
* @date 2023-04-03
|
||||
*/
|
||||
#ifndef __OTA_DEF_H__
|
||||
#define __OTA_DEF_H__
|
||||
|
||||
#ifndef __IMXRT_OTA__H__
|
||||
#define __IMXRT_OTA__H__
|
||||
#include "flash_ops.h"
|
||||
|
||||
#include <stdint.h>
|
||||
#include "mcuboot.h"
|
||||
#include "flash.h"
|
||||
#include "ymodem.h"
|
||||
#define JUMP_FAILED_FLAG 0XABABABAB
|
||||
#define JUMP_SUCCESS_FLAG 0XCDCDCDCD
|
||||
|
||||
/* OTA升级过程中的状态描述 */
|
||||
typedef enum {
|
||||
OTA_STATUS_IDLE = 0, // 空闲状态,没有进行OTA升级
|
||||
OTA_STATUS_READY, // 准备状态,可以进行OTA升级
|
||||
OTA_STATUS_DOWNLOADING, // 正在下载固件
|
||||
OTA_STATUS_DOWNLOADED, // 固件下载完成
|
||||
OTA_STATUS_UPDATING, // 正在进行OTA升级
|
||||
OTA_STATUS_BACKUP, // 正在版本回退
|
||||
OTA_STATUS_ERROR, // 出现错误,升级失败
|
||||
} ota_status_t;
|
||||
|
||||
|
@ -53,14 +47,11 @@ typedef struct {
|
|||
firmware_t bak; // Bakup分区属性信息
|
||||
firmware_t down; // Download分区属性信息
|
||||
uint32_t status; // 升级状态,取值来自于ota_status_t类型
|
||||
uint32_t lastjumpflag; // bootloaer跳转失败的标志,bootloader里置0xABABABAB,跳转成功后在应用里置0x00000000
|
||||
uint32_t lastjumpflag; // bootloaer跳转失败的标志,bootloader里置0xABABABAB,跳转成功后在应用里置0xCDCDCDCD
|
||||
uint32_t reserve[2]; // 保留字段
|
||||
uint8_t error_message[128]; // 错误信息,最多128个字符
|
||||
} ota_info_t;
|
||||
|
||||
|
||||
uint32_t calculate_crc32(uint32_t addr, uint32_t len);
|
||||
status_t UpdateOTAFlag(ota_info_t *ptr);
|
||||
void UpdateApplication(void);
|
||||
|
||||
void app_clear_jumpflag(void);
|
||||
void ota_entry(void);
|
||||
#endif
|
Loading…
Reference in New Issue