From 2e3ca1c2f7f35775010cd7637bd85fac0ef6dbef Mon Sep 17 00:00:00 2001 From: Angus Gratton Date: Wed, 4 Jan 2017 15:36:40 +1100 Subject: [PATCH] bootloader: Boost bootloader CPU to 80MHz Partially needed to use RNG, also useful to improve boot performance. --- .../bootloader/src/main/bootloader_start.c | 46 +++++++++---------- components/bootloader/src/main/component.mk | 8 ++++ components/esp32/system_api.c | 4 ++ 3 files changed, 34 insertions(+), 24 deletions(-) diff --git a/components/bootloader/src/main/bootloader_start.c b/components/bootloader/src/main/bootloader_start.c index e5fda9cf53..cd845b0b92 100644 --- a/components/bootloader/src/main/bootloader_start.c +++ b/components/bootloader/src/main/bootloader_start.c @@ -44,6 +44,7 @@ #include "bootloader_flash.h" #include "bootloader_config.h" +#include "rtc.h" extern int _bss_start; extern int _bss_end; @@ -232,6 +233,13 @@ static bool ota_select_valid(const esp_ota_select_entry_t *s) void bootloader_main() { + /* Set CPU to 80MHz. + Start by ensuring it is set to XTAL, as PLL must be off first + (may still be on due to soft reset.) + */ + rtc_set_cpu_freq(CPU_XTAL); + rtc_set_cpu_freq(CPU_80M); + uart_console_configure(); ESP_LOGI(TAG, "Espressif ESP32 2nd stage bootloader v. %s", BOOT_VERSION); #if defined(CONFIG_SECURE_BOOT_ENABLED) || defined(CONFIG_FLASH_ENCRYPTION_ENABLED) @@ -666,26 +674,6 @@ void print_flash_info(const esp_image_header_t* phdr) #endif } -#if CONFIG_CONSOLE_UART_CUSTOM -static uint32_t get_apb_freq(void) -{ - // Get the value of APB clock from RTC memory. - // The value is initialized in ROM code, and updated by librtc.a - // when APB clock is changed. - // This value is stored in RTC_CNTL_STORE5_REG as follows: - // RTC_CNTL_STORE5_REG = (freq >> 12) | ((freq >> 12) << 16) - uint32_t apb_freq_reg = REG_READ(RTC_CNTL_STORE5_REG); - uint32_t apb_freq_l = apb_freq_reg & 0xffff; - uint32_t apb_freq_h = apb_freq_reg >> 16; - if (apb_freq_l == apb_freq_h && apb_freq_l != 0) { - return apb_freq_l << 12; - } else { - // fallback value - return APB_CLK_FREQ_ROM; - } -} -#endif - static void uart_console_configure(void) { #if CONFIG_CONSOLE_UART_NONE @@ -695,20 +683,21 @@ static void uart_console_configure(void) uartAttach(); ets_install_uart_printf(); + // ROM bootloader may have put a lot of text into UART0 FIFO. + // Wait for it to be printed. + uart_tx_wait_idle(0); + #if CONFIG_CONSOLE_UART_CUSTOM // Some constants to make the following code less upper-case const int uart_num = CONFIG_CONSOLE_UART_NUM; const int uart_baud = CONFIG_CONSOLE_UART_BAUDRATE; const int uart_tx_gpio = CONFIG_CONSOLE_UART_TX_GPIO; const int uart_rx_gpio = CONFIG_CONSOLE_UART_RX_GPIO; - // ROM bootloader may have put a lot of text into UART0 FIFO. - // Wait for it to be printed. - uart_tx_wait_idle(0); // Switch to the new UART (this just changes UART number used for // ets_printf in ROM code). uart_tx_switch(uart_num); // Set new baud rate - uart_div_modify(uart_num, (((uint64_t) get_apb_freq()) << 4) / uart_baud); + uart_div_modify(uart_num, (APB_CLK_FREQ << 4) / uart_baud); // If console is attached to UART1 or if non-default pins are used, // need to reconfigure pins using GPIO matrix if (uart_num != 0 || uart_tx_gpio != 1 || uart_rx_gpio != 3) { @@ -727,3 +716,12 @@ static void uart_console_configure(void) #endif // CONFIG_CONSOLE_UART_CUSTOM #endif // CONFIG_CONSOLE_UART_NONE } + +/* empty rtc_printf implementation, to work with librtc + linking. Can be removed once -lrtc is removed from bootloader's + main component.mk. +*/ +int rtc_printf(void) +{ + return 0; +} diff --git a/components/bootloader/src/main/component.mk b/components/bootloader/src/main/component.mk index e98545fc47..9bcc5352a0 100644 --- a/components/bootloader/src/main/component.mk +++ b/components/bootloader/src/main/component.mk @@ -10,3 +10,11 @@ LINKER_SCRIPTS := esp32.bootloader.ld $(IDF_PATH)/components/esp32/ld/esp32.rom. COMPONENT_ADD_LDFLAGS := -L $(COMPONENT_PATH) -lmain $(addprefix -T ,$(LINKER_SCRIPTS)) COMPONENT_ADD_LINKER_DEPS := $(LINKER_SCRIPTS) + +ifdef IS_BOOTLOADER_BUILD +# following lines are a workaround to link librtc into the +# bootloader, until clock setting code is in a source-based esp-idf +# component. See also rtc_printf() in bootloader_start.c +COMPONENT_ADD_LDFLAGS += -L $(IDF_PATH)/components/esp32/lib/ -lrtc +COMPONENT_EXTRA_INCLUDES += $(IDF_PATH)/components/esp32/ +endif diff --git a/components/esp32/system_api.c b/components/esp32/system_api.c index e8013441b1..63a28de533 100644 --- a/components/esp32/system_api.c +++ b/components/esp32/system_api.c @@ -29,6 +29,7 @@ #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "freertos/xtensa_api.h" +#include "rtc.h" static const char* TAG = "system_api"; @@ -119,6 +120,9 @@ void IRAM_ATTR esp_restart(void) DPORT_TIMERS_RST | DPORT_SPI_RST_1 | DPORT_UART_RST); REG_WRITE(DPORT_PERIP_RST_EN_REG, 0); + // Set CPU back to XTAL source, no PLL, same as hard reset + rtc_set_cpu_freq(CPU_XTAL); + // Reset CPUs if (core_id == 0) { // Running on PRO CPU: APP CPU is stalled. Can reset both CPUs.