feat(esp8266): Refactor startup function

This commit is contained in:
Dong Heng
2018-05-23 15:47:32 +08:00
parent 1e294d1102
commit 19f9a8221d
7 changed files with 251 additions and 14 deletions

View File

@ -97,8 +97,9 @@ typedef enum {
FLASH_SIZE_32M_MAP_2048_2048, /**< attention: don't support now ,just compatible for nodemcu; FLASH_SIZE_32M_MAP_2048_2048, /**< attention: don't support now ,just compatible for nodemcu;
Flash size : 32Mbits. Map : 2048KBytes + 2048KBytes */ Flash size : 32Mbits. Map : 2048KBytes + 2048KBytes */
FLASH_SIZE_64M_MAP_1024_1024, /**< Flash size : 64Mbits. Map : 1024KBytes + 1024KBytes */ FLASH_SIZE_64M_MAP_1024_1024, /**< Flash size : 64Mbits. Map : 1024KBytes + 1024KBytes */
FLASH_SIZE_128M_MAP_1024_1024 /**< Flash size : 128Mbits. Map : 1024KBytes + 1024KBytes */ FLASH_SIZE_128M_MAP_1024_1024, /**< Flash size : 128Mbits. Map : 1024KBytes + 1024KBytes */
FALSH_SIZE_MAP_MAX
} flash_size_map; } flash_size_map;
/** /**

View File

@ -20,8 +20,8 @@ MEMORY
{ {
dport0_0_seg : org = 0x3FF00000, len = 0x10 dport0_0_seg : org = 0x3FF00000, len = 0x10
/* All .data/.bss/heap are in this segment. */ /* All .data/.bss/heap are in this segment. 1024 bytes is for system start and interrupt*/
dram0_0_seg : org = 0x3FFE8000, len = 0x18000 dram0_0_seg : org = 0x3FFE8000, len = 0x18000 - 1024
/* Functions which are critical should be put in this segment. */ /* Functions which are critical should be put in this segment. */
iram1_0_seg : org = 0x40100000, len = 0x8000 iram1_0_seg : org = 0x40100000, len = 0x8000

View File

@ -1,7 +1,7 @@
gwen: gwen:
crypto: 137694e crypto: 137694e
espnow: 137694e espnow: 137694e
core: a6ca7a1 core: bc4803f
net80211: 34c6b8d net80211: 34c6b8d
pp: 137694e pp: 137694e
pwm: 0181338 pwm: 0181338

Binary file not shown.

View File

@ -0,0 +1,160 @@
// Copyright 2018-2019 Espressif Systems (Shanghai) PTE LTD
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#include "sdkconfig.h"
#include "esp_attr.h"
#include "spi_flash.h"
#include "esp_log.h"
#include "esp_system.h"
#include "esp8266/eagle_soc.h"
#define PERIPHS_SPI_FLASH_USRREG (0x60000200 + 0x1c)
#define PERIPHS_SPI_FLASH_CTRL (0x60000200 + 0x08)
#define PERIPHS_IO_MUX_CONF_U (0x60000800)
#define SPI0_CLK_EQU_SYSCLK BIT8
#define SPI_FLASH_CLK_EQU_SYSCLK BIT12
typedef struct flash_hdr {
uint8_t magic;
uint8_t blocks;
uint8_t spi_mode;
uint8_t spi_speed : 4;
uint8_t spi_size_map : 4;
uint32_t entry_addr;
} flash_hdr_t;
typedef struct boot_hdr {
uint8_t user_bin : 2;
uint8_t boot_status : 1;
uint8_t to_qio : 1;
uint8_t reserve : 4;
uint8_t version : 5;
uint8_t test_pass_flag : 1;
uint8_t test_start_flag : 1;
uint8_t enhance_boot_flag : 1;
uint8_t test_bin_addr[3];
uint8_t user_bin_addr[3];
} boot_hdr_t;
extern int ets_printf(const char *fmt, ...);
static const char *TAG = "chip_boot";
/*
* @brief initialize the chip including flash I/O and chip cache according to
* boot parameters which are stored at the flash
*/
void chip_boot(void)
{
int ret;
int usebin;
uint32_t freqdiv, flash_size, sect_size;
uint32_t freqbits;
uint32_t cache_map;
flash_hdr_t fhdr;
boot_hdr_t bhdr;
uint32_t flash_map_table[FALSH_SIZE_MAP_MAX] = {
1 * 1024 * 1024,
2 * 1024 * 1024,
4 * 1024 * 1024,
8 * 1024 * 1024,
16 * 1024 * 1024
};
uint32_t flash_map_table_size = sizeof(flash_map_table) / sizeof(flash_map_table[0]);
extern void phy_get_bb_evm(void);
extern void cache_init(uint32_t , uint32_t, uint32_t);
extern void user_spi_flash_dio_to_qio_pre_init(void);
extern int esp_get_boot_param(uint32_t, uint32_t, void *, uint32_t);
phy_get_bb_evm();
SET_PERI_REG_MASK(PERIPHS_SPI_FLASH_USRREG, BIT5);
ret = spi_flash_read(CONFIG_PARTITION_TABLE_CUSTOM_APP_BIN_OFFSET, &fhdr, sizeof(flash_hdr_t));
if (ret) {
ESP_LOGE(TAG, "SPI flash read result %d\n", ret);
}
if (3 > fhdr.spi_speed)
freqdiv = fhdr.spi_speed + 2;
else if (0x0F == fhdr.spi_speed)
freqdiv = 1;
else
freqdiv = 2;
if (fhdr.spi_size_map < flash_map_table_size) {
flash_size = flash_map_table[fhdr.spi_size_map];
} else {
flash_size = 0;
ESP_LOGE(TAG, "SPI size error is %d\n", fhdr.spi_size_map);
}
sect_size = 4 * 1024;
if (1 >= freqdiv) {
freqbits = SPI_FLASH_CLK_EQU_SYSCLK;
SET_PERI_REG_MASK(PERIPHS_SPI_FLASH_CTRL, SPI_FLASH_CLK_EQU_SYSCLK);
SET_PERI_REG_MASK(PERIPHS_IO_MUX_CONF_U, SPI0_CLK_EQU_SYSCLK);
} else {
freqbits = ((freqdiv - 1) << 8) + ((freqdiv / 2 - 1) << 4) + (freqdiv - 1);
CLEAR_PERI_REG_MASK(PERIPHS_SPI_FLASH_CTRL, SPI_FLASH_CLK_EQU_SYSCLK);
CLEAR_PERI_REG_MASK(PERIPHS_IO_MUX_CONF_U, SPI0_CLK_EQU_SYSCLK);
}
SET_PERI_REG_BITS(PERIPHS_SPI_FLASH_CTRL, 0xfff, freqbits, 0);
ret = esp_get_boot_param(flash_size, sect_size, &bhdr, sizeof(boot_hdr_t));
if (ret) {
ESP_LOGE(TAG, "Get boot parameters %d\n", ret);
}
if (bhdr.user_bin == 1) {
if (bhdr.boot_status == 1)
usebin = 1;
else
usebin = 0;
} else {
if (bhdr.boot_status == 1)
usebin = 0;
else {
if (bhdr.version == 4) {
bhdr.boot_status = 1;
usebin = 0;
} else
usebin = 1;
}
}
cache_map = 0;
if (fhdr.spi_size_map == FLASH_SIZE_16M_MAP_1024_1024
|| fhdr.spi_size_map == FLASH_SIZE_32M_MAP_1024_1024
|| fhdr.spi_size_map == FLASH_SIZE_64M_MAP_1024_1024
|| fhdr.spi_size_map == FLASH_SIZE_128M_MAP_1024_1024) {
if (bhdr.version >= 4
&& bhdr.version <= 0x1f) {
if (usebin == 1)
cache_map = 1;
} else {
ESP_LOGE(TAG, "Need boot 1.4+\n");
}
}
cache_init(cache_map, 0, 0);
if (bhdr.to_qio == 0)
user_spi_flash_dio_to_qio_pre_init();
}

View File

@ -1,15 +1,52 @@
#include "sdkconfig.h" #include "sdkconfig.h"
#include <stdint.h> #include <stdint.h>
#include <stddef.h>
#include <stdarg.h> #include <stdarg.h>
#include <string.h>
#include "esp_log.h"
#include "nvs_flash.h"
#include "tcpip_adapter.h"
#include "esp_wifi_osi.h"
#include "esp_image_format.h" #include "esp_image_format.h"
#define FLASH_MAP_ADDR 0x40200000 #define FLASH_MAP_ADDR 0x40200000
static void user_init_entry(void *param)
{
void (*func)(void);
extern void (__init_array_start)(void);
extern void (__init_array_end)(void);
extern void app_main(void);
/* initialize C++ construture function */
for (func = &__init_array_start; func < &__init_array_end; func++)
func();
tcpip_adapter_init();
app_main();
wifi_task_delete(NULL);
}
void call_user_start(void) void call_user_start(void)
{ {
int i; int i;
extern void user_start(void); int *p;
extern int _bss_start, _bss_end;
extern void chip_boot(void);
extern int rtc_init(void);
extern int mac_init(void);
extern int base_gpio_init(void);
extern int phy_calibrate(void);
extern int watchdog_init(void);
extern int wifi_timer_init(void);
extern int wifi_nvs_init(void);
esp_image_header_t *head = (esp_image_header_t *)(FLASH_MAP_ADDR + CONFIG_PARTITION_TABLE_CUSTOM_APP_BIN_OFFSET); esp_image_header_t *head = (esp_image_header_t *)(FLASH_MAP_ADDR + CONFIG_PARTITION_TABLE_CUSTOM_APP_BIN_OFFSET);
esp_image_segment_header_t *segment = (esp_image_segment_header_t *)((uintptr_t)head + sizeof(esp_image_header_t)); esp_image_segment_header_t *segment = (esp_image_segment_header_t *)((uintptr_t)head + sizeof(esp_image_header_t));
@ -25,11 +62,31 @@ void call_user_start(void)
*dest++ = *src++; *dest++ = *src++;
} }
/* clear bss data */
for (p = &_bss_start; p < &_bss_end; p++)
*p = 0;
__asm__ __volatile__( __asm__ __volatile__(
"rsil a2, 2\n"
"movi a1, _chip_interrupt_tmp\n"
"movi a2, 0xffffff00\n"
"and a1, a1, a2\n"
"movi a2, 0x40100000\n" "movi a2, 0x40100000\n"
"wsr a2, vecbase\n"); "wsr a2, vecbase\n");
user_start(); chip_boot();
wifi_os_init();
assert(nvs_flash_init() == 0);
assert(wifi_nvs_init() == 0);
assert(rtc_init() == 0);
assert(mac_init() == 0);
assert(base_gpio_init() == 0);
assert(phy_calibrate() == 0);
assert(watchdog_init() == 0);
assert(wifi_timer_init() == 0);
assert(wifi_task_create(user_init_entry, "uiT", 512, NULL, wifi_task_get_max_priority()) != NULL);
wifi_os_start();
} }

View File

@ -124,6 +124,9 @@ STRUCT_END(HighPriFrame)
#define PANIC_STK_FRMSZ 0x60 #define PANIC_STK_FRMSZ 0x60
#define CHIP_INTERRUPT_STK_MAX 1024
.global panicHandler .global panicHandler
// Allocate save area and stack: // Allocate save area and stack:
@ -159,6 +162,14 @@ LABEL(_Pri_,_HandlerAddress): .space 4
LABEL(_Pri_,_NMICount): .space 4 LABEL(_Pri_,_NMICount): .space 4
#endif #endif
.section .data, "aw"
.global _chip_interrupt_stk, _chip_interrupt_tmp
.align 16
_chip_interrupt_stk:
.space CHIP_INTERRUPT_STK_MAX
_chip_interrupt_tmp:
.word 0
/*************************** LoadStoreError Handler **************************/ /*************************** LoadStoreError Handler **************************/
.section .text .section .text
@ -442,7 +453,7 @@ LoadStoreErrorHandler_common:
l32i a3, sp, 0x0c l32i a3, sp, 0x0c
l32i a4, sp, 0x10 l32i a4, sp, 0x10
rsr a1, excsave1 rsr a1, excsave1
call0 user_fatal_exception_handler call0 _xt_ext_panic
.balign 4 .balign 4
.LSE_assign_a1: .LSE_assign_a1:
@ -642,7 +653,7 @@ _DebugExceptionVector:
jx a3 jx a3
#else #else
wsr a0, EXCSAVE+XCHAL_DEBUGLEVEL /* save original a0 somewhere */ wsr a0, EXCSAVE+XCHAL_DEBUGLEVEL /* save original a0 somewhere */
call0 user_fatal_exception_handler /* does not return */ call0 _xt_ext_panic /* does not return */
rfi XCHAL_DEBUGLEVEL /* make a0 point here not later */ rfi XCHAL_DEBUGLEVEL /* make a0 point here not later */
#endif #endif
@ -671,7 +682,7 @@ _DoubleExceptionVector:
#if XCHAL_HAVE_DEBUG #if XCHAL_HAVE_DEBUG
break 1, 4 /* unhandled double exception */ break 1, 4 /* unhandled double exception */
#endif #endif
call0 user_fatal_exception_handler /* does not return */ call0 _xt_ext_panic /* does not return */
rfde /* make a0 point here not later */ rfde /* make a0 point here not later */
.end literal_prefix .end literal_prefix
@ -705,7 +716,7 @@ _xt_kernel_exc:
#if XCHAL_HAVE_DEBUG #if XCHAL_HAVE_DEBUG
break 1, 0 /* unhandled kernel exception */ break 1, 0 /* unhandled kernel exception */
#endif #endif
call0 user_fatal_exception_handler /* does not return */ call0 _xt_ext_panic /* does not return */
rfe /* make a0 point here not there */ rfe /* make a0 point here not there */
@ -847,7 +858,7 @@ _xt_user_entry1:
#if XCHAL_HAVE_DEBUG #if XCHAL_HAVE_DEBUG
break 1, 1 /* unhandled user exception */ break 1, 1 /* unhandled user exception */
#endif #endif
call0 user_fatal_exception_handler call0 _xt_ext_panic
/* Handle level 1 interrupts. OK to enable med-pri interrupts now. */ /* Handle level 1 interrupts. OK to enable med-pri interrupts now. */
.L_xt_user_int: .L_xt_user_int:
@ -909,7 +920,15 @@ _xt_user_entry1:
sub a2, a2, a3 /* clear timer int from mask */ sub a2, a2, a3 /* clear timer int from mask */
#endif #endif
3: 3:
movi a0, _chip_interrupt_tmp
s32i a1, a0, 0
mov a1, a0
call0 _xt_isr_handler call0 _xt_isr_handler
movi a0, _chip_interrupt_tmp
l32i a1, a0, 0
bnez a2, .Ln_xt_user_int_timer bnez a2, .Ln_xt_user_int_timer
#endif #endif
4: 4:
@ -921,7 +940,7 @@ _xt_user_entry1:
break 1, 1 /* unhandled user exception */ break 1, 1 /* unhandled user exception */
/* EXCCAUSE == 4 (level 1 int) */ /* EXCCAUSE == 4 (level 1 int) */
#endif #endif
call0 user_fatal_exception_handler call0 _xt_ext_panic
/* Done handling after XT_RTOS_INT_ENTER. Give control to RTOS. */ /* Done handling after XT_RTOS_INT_ENTER. Give control to RTOS. */
.L_xt_user_done: .L_xt_user_done: