From 31f6a6fa70aa9140a6587a1e3f23bb604e5abbca Mon Sep 17 00:00:00 2001 From: Daniel Campora Date: Wed, 5 Aug 2015 17:05:41 +0200 Subject: [PATCH] cc3200: Enable bootloader safe boot on latest firmware. The first safe boot level executes the latest firmware but skips 'main.py' and 'boot.py'. --- cc3200/bootmgr/main.c | 34 +++++++++++++++++++++++----------- docs/wipy/general.rst | 35 +++++++++++++++++++++++++++++------ 2 files changed, 52 insertions(+), 17 deletions(-) diff --git a/cc3200/bootmgr/main.c b/cc3200/bootmgr/main.c index 95df47c297..32210e6de9 100644 --- a/cc3200/bootmgr/main.c +++ b/cc3200/bootmgr/main.c @@ -64,14 +64,16 @@ #define BOOTMGR_HASH_SIZE 32 #define BOOTMGR_BUFF_SIZE 512 -#define BOOTMGR_WAIT_SAFE_MODE_0_MS 3000 -#define BOOTMGR_WAIT_SAFE_MODE_0_BLINK_MS 500 +#define BOOTMGR_WAIT_SAFE_MODE_0_MS 500 #define BOOTMGR_WAIT_SAFE_MODE_1_MS 3000 #define BOOTMGR_WAIT_SAFE_MODE_1_BLINK_MS 250 -#define BOOTMGR_WAIT_SAFE_MODE_2_MS 1500 -#define BOOTMGR_WAIT_SAFE_MODE_2_BLINK_MS 100 +#define BOOTMGR_WAIT_SAFE_MODE_2_MS 3000 +#define BOOTMGR_WAIT_SAFE_MODE_2_BLINK_MS 250 + +#define BOOTMGR_WAIT_SAFE_MODE_3_MS 1500 +#define BOOTMGR_WAIT_SAFE_MODE_3_BLINK_MS 100 //***************************************************************************** // Exported functions declarations @@ -85,6 +87,7 @@ static void bootmgr_board_init (void); static bool bootmgr_verify (_u8 *image); static void bootmgr_load_and_execute (_u8 *image); static bool wait_while_blinking (uint32_t wait_time, uint32_t period, bool force_wait); +static bool safe_boot_request_start (uint32_t wait_time); static void wait_for_safe_boot (sBootInfo_t *psBootInfo); static void bootmgr_image_loader (sBootInfo_t *psBootInfo); @@ -260,24 +263,33 @@ static bool wait_while_blinking (uint32_t wait_time, uint32_t period, bool force return MAP_GPIOPinRead(MICROPY_SAFE_BOOT_PORT, MICROPY_SAFE_BOOT_PORT_PIN) ? true : false; } +static bool safe_boot_request_start (uint32_t wait_time) { + if (MAP_GPIOPinRead(MICROPY_SAFE_BOOT_PORT, MICROPY_SAFE_BOOT_PORT_PIN)) { + UtilsDelay(UTILS_DELAY_US_TO_COUNT(wait_time * 1000)); + } + return MAP_GPIOPinRead(MICROPY_SAFE_BOOT_PORT, MICROPY_SAFE_BOOT_PORT_PIN) ? true : false; +} + //***************************************************************************** //! Check for the safe mode pin //***************************************************************************** static void wait_for_safe_boot (sBootInfo_t *psBootInfo) { - if (wait_while_blinking(BOOTMGR_WAIT_SAFE_MODE_0_MS, BOOTMGR_WAIT_SAFE_MODE_0_BLINK_MS, false)) { - // go back one step in time - psBootInfo->ActiveImg = psBootInfo->PrevImg; + if (safe_boot_request_start(BOOTMGR_WAIT_SAFE_MODE_0_MS)) { if (wait_while_blinking(BOOTMGR_WAIT_SAFE_MODE_1_MS, BOOTMGR_WAIT_SAFE_MODE_1_BLINK_MS, false)) { - // go back directly to the factory image - psBootInfo->ActiveImg = IMG_ACT_FACTORY; - wait_while_blinking(BOOTMGR_WAIT_SAFE_MODE_2_MS, BOOTMGR_WAIT_SAFE_MODE_2_BLINK_MS, true); + // go back one step in time + psBootInfo->ActiveImg = psBootInfo->PrevImg; + if (wait_while_blinking(BOOTMGR_WAIT_SAFE_MODE_2_MS, BOOTMGR_WAIT_SAFE_MODE_2_BLINK_MS, false)) { + // go back directly to the factory image + psBootInfo->ActiveImg = IMG_ACT_FACTORY; + wait_while_blinking(BOOTMGR_WAIT_SAFE_MODE_3_MS, BOOTMGR_WAIT_SAFE_MODE_3_BLINK_MS, true); + } } // turn off the system led MAP_GPIOPinWrite(MICROPY_SYS_LED_PORT, MICROPY_SYS_LED_PORT_PIN, 0); // request a safe boot to the application PRCMRequestSafeBoot(); } - // uninit the safe boot pin + // deinit the safe boot pin mperror_deinit_sfe_pin(); } diff --git a/docs/wipy/general.rst b/docs/wipy/general.rst index 37900deac8..b59e0d71a5 100644 --- a/docs/wipy/general.rst +++ b/docs/wipy/general.rst @@ -18,7 +18,7 @@ There is a small internal file system (a drive) on the WiPy, called ``/flash``, which is stored within the external serial flash memory. If a micro SD card is hooked-up and enabled, it is available as ``/sd``. -When the WiPy boots up, it always boots from the ``boot.py`` located in the +When the WiPy boots up, it always boots from the ``boot.py`` located in the ``/flash`` file system. If during the boot process the SD card is enabled and it's selected as the current drive then the WiPy will try to execute ``main.py`` that should be located in the SD card. @@ -28,6 +28,27 @@ Open your FTP client of choice and connect to: ``ftp://192.168.1.1``, ``user: micro``, ``password: python`` +FileZilla settings +------------------ +Do not use the quick connect button, instead, open the site manager and create a new +configuration. In the ``General`` tab make sure that encryption is set to: ``Only use +plain FTP (insecure)``. In the Transfer Settings tab limit the max number of connections +to one, otherwise FileZilla will try to open a second command connection when retrieving +and saving files, and for simplicity and to reduce code size, only one command and one +data connections are possible. Other FTP clients might behave in a similar way. + +Upgrading the firmware Over The Air +----------------------------------- + +OTA software updates can be performed through the FTP server. Upload the ``mcuimg.bin`` file +to: ``/flash/sys/mcuimg.bin`` it will take around 6s. You won't see the file being stored +inside ``/flash/sys/`` because it's actually saved bypassing the user file system, but rest +assured that it was successfully transferred, and it has been signed with a MD5 checksum to +verify its integrity. Now, reset the MCU by pressing the switch on the board, or by typing:: + + import pyb + pyb.reset() + Boot modes ---------- @@ -54,19 +75,21 @@ and the WiPy will proceed to boot. The firmware selection mechanism is as follow +-------------------------+-------------------------+----------------------------+ | 1st 3 secs window | 2nd 3 secs window | Final 1.5 secs window | +=========================+=========================+============================+ -| | Normal boot, *latest* | | Safe boot, *previous* | | Safe boot, the *factory* | +| | Safe boot, *latest* | | Safe boot, *previous* | | Safe boot, the *factory* | | | firmware is selected | | user update selected | | firmware is selected | +-------------------------+-------------------------+----------------------------+ -When selecting a previous firmware version, safe boot mode is entered, meaning -that the execution of both ``boot.py`` and ``main.py`` is skipped. This is -useful to recover from crash situations caused by the user scripts. +In any if the above 3 scenarios, safe boot mode is entered, meaning that +the execution of both ``boot.py`` and ``main.py`` is skipped. This is +useful to recover from crash situations caused by the user scripts. The selection +made during safe boot is not persistent, meaning that after the next normal reset, +the latest firmware will run again. The heart beat LED ------------------ By default the heart beat LED flashes once every 5s to signal that the system is -alive. This can be overridden through the HeartBeat class: +alive. This can be overridden through the HeartBeat class: ``pyb.HeartBeat().disable()``