| | |
| | | /* |
| | | * Copyright (c) 2020-2021 Shanghai Panchip Microelectronics Co.,Ltd. |
| | | * Copyright (c) 2020-2025 Shanghai Panchip Microelectronics Co.,Ltd. |
| | | * |
| | | * SPDX-License-Identifier: Apache-2.0 |
| | | */ |
| | | |
| | | #include "soc_api.h" |
| | | #include "app_log.h" |
| | | #include "signal_slot_manager.h" |
| | | #include "uart_dfu.h" |
| | | #include "usb_dfu.h" |
| | | #include "flash_manager.h" |
| | | #include "prf_ota.h" |
| | | #include "boot_config.c" |
| | | |
| | | static void on_image_load_enter(void) |
| | | { |
| | | fm_image_move(FLASH_AREA_BACK_UP_START, FLASH_AREA_IMAGE_START); |
| | | APP_LOG_INFO("Try to move image from App Backup Partition to App Partition..\n"); |
| | | |
| | | fm_image_move(FLASH_AREA_BACK_UP_START, FLASH_AREA_IMAGE_START); |
| | | } |
| | | |
| | | void sys_clock_init(void) |
| | | static void boot_cleanup(void) |
| | | { |
| | | /* Unlock protected registers */ |
| | | SYS_UnlockReg(); |
| | | |
| | | ANA->LP_FSYN_LDO |= 0X1; |
| | | /* Mask all IRQs */ |
| | | __disable_irq(); |
| | | |
| | | CLK_XthStartupConfig(); |
| | | CLK->XTH_CTRL |= CLK_XTHCTL_XTH_EN_Msk; |
| | | CLK_WaitClockReady(CLK_SYS_SRCSEL_XTH); |
| | | /* Reset specific hardware modules used in signal.c */ |
| | | sig_hardware_recovery(); |
| | | |
| | | CLK_HCLKConfig(0); |
| | | CLK_SYSCLKConfig(CLK_DPLL_REF_CLKSEL_XTH,CLK_DPLL_OUT_48M); |
| | | CLK_RefClkSrcConfig(CLK_SYS_SRCSEL_DPLL); |
| | | |
| | | SYS_LockReg(); |
| | | /* Reset all hw peripheral modules except eFuse and GPIO */ |
| | | CLK->IPRST0 = 0x1CC; |
| | | CLK->IPRST0 = 0x0; |
| | | CLK->IPRST1 = 0x17FFF; |
| | | CLK->IPRST1 = 0x0; |
| | | |
| | | /* Disable all IRQs and clear all pending IRQs on NVIC before running into app */ |
| | | NVIC->ICER[0U] = 0xFFFFFFFF; |
| | | NVIC->ICPR[0U] = 0xFFFFFFFF; |
| | | |
| | | // Do a short flash read operation here to avoid risk of APP flash x4 mode |
| | | // switch fail in specific scenario (Workaround #5663) |
| | | FMC_ReadByte(FLCTL, 0x0, CMD_DREAD); |
| | | |
| | | // Disable I-cache here, and would enable again in APP SystemInit flow |
| | | CR->X_CACHE_EN = 0x00; |
| | | } |
| | | |
| | | static void jump_to_app(void) |
| | | { |
| | | void (*app_main)(); |
| | | |
| | | uint32_t msp = *(volatile uint32_t*)(FLASH_AREA_IMAGE_START + sizeof(image_header_t)); |
| | | uint32_t addr = *(uint32_t*)(FLASH_AREA_IMAGE_START + sizeof(image_header_t) + 4); |
| | | app_main = (void(*)())(uint32_t*)addr; |
| | | |
| | | FLCTL->X_FL_REMAP_ADDR = FLASH_AREA_IMAGE_START + sizeof(image_header_t); /* fmc remap */ |
| | | |
| | | void (*app_init)(); |
| | | |
| | | uint32_t msp = *(volatile uint32_t*)(FLASH_AREA_IMAGE_START + APP_IMG_HEADER_SIZE); |
| | | uint32_t addr = *(uint32_t*)(FLASH_AREA_IMAGE_START + APP_IMG_HEADER_SIZE + 4); |
| | | app_init = (void(*)())(uint32_t*)addr; |
| | | |
| | | FLCTL->X_FL_REMAP_ADDR = FLASH_AREA_IMAGE_START + APP_IMG_HEADER_SIZE; /* fmc remap */ |
| | | |
| | | __set_MSP(msp); |
| | | |
| | | app_main(); |
| | | |
| | | app_init(); |
| | | } |
| | | |
| | | int main(void) |
| | | { |
| | | sys_clock_init(); |
| | | |
| | | /* when checking backup image is valid, the on_image_load_enter function will be handled */ |
| | | ss_connect(0, sig_back_up_is_completed_image, on_image_load_enter); |
| | | |
| | | #if BOOT_FROM_UART |
| | | /* when detecting key1 down, the on_uart_dfu_enter function will be handled */ |
| | | ss_connect(1, sig_key1_push_down, on_uart_dfu_enter); |
| | | #endif |
| | | |
| | | #if BOOT_FROM_USB |
| | | /* when dectecting key2 down, the on_usb_dfu_enter function will be handled */ |
| | | ss_connect(2, sig_key2_push_down, on_usb_dfu_enter); |
| | | #endif |
| | | |
| | | #if BOOT_FROM_PRF_OTA |
| | | /* when receive a ota start packet, the on_prf_ota_enter function will be handled */ |
| | | ss_connect(3, sig_ota_start_received, on_prf_ota_enter); |
| | | #endif |
| | | |
| | | /* handle all of events related signal fuction*/ |
| | | ss_events_handle(); |
| | | |
| | | /* recovery gpio status that you used to trigger signal */ |
| | | sig_hardware_recovery(); |
| | | |
| | | jump_to_app(); |
| | | |
| | | return 0; |
| | | { |
| | | APP_LOG("\nBootloader in..\n\n"); |
| | | |
| | | /* when checking backup image is valid, the on_image_load_enter function will be handled */ |
| | | ss_connect(0, sig_back_up_is_completed_image, on_image_load_enter); |
| | | |
| | | #if BOOT_ENABLE_UART_DFU |
| | | /* when detecting key1 down, the on_uart_dfu_enter function will be handled */ |
| | | ss_connect(1, sig_key1_push_down, on_uart_dfu_enter); |
| | | #endif |
| | | |
| | | #if BOOT_ENABLE_USB_DFU |
| | | /* when dectecting key2 down, the on_usb_dfu_enter function will be handled */ |
| | | ss_connect(2, sig_key2_push_down, on_usb_dfu_enter); |
| | | #endif |
| | | |
| | | #if BOOT_ENABLE_PRF_OTA |
| | | /* when receive a ota start packet, the on_prf_ota_enter function will be handled */ |
| | | ss_connect(3, sig_ota_start_received, on_prf_ota_enter); |
| | | #endif |
| | | |
| | | /* handle all of events related signal fuction*/ |
| | | ss_events_handle(); |
| | | |
| | | #if APP_LOG_EN |
| | | APP_LOG_INFO("Clean up and try to jump into app image..\n"); |
| | | APP_LOG_INFO("- app partition start addr: 0x%x\n", FLASH_AREA_IMAGE_START); |
| | | APP_LOG_INFO("- app partition size : 0x%x\n", FLASH_IMAGE_MAX_SIZE); |
| | | APP_LOG_INFO("- app image header size : 0x%x\n\n", APP_IMG_HEADER_SIZE); |
| | | soc_busy_wait(10000); // Wait for print done |
| | | #endif |
| | | /* |
| | | * Reset hardware modules possible used in bootloader, and clear other configurations |
| | | * (such as IRQs) before running into app. |
| | | */ |
| | | boot_cleanup(); |
| | | |
| | | /* Now let's try to find app image and jump into the entry of it */ |
| | | jump_to_app(); |
| | | |
| | | return 0; |
| | | } |