Add update code to updater and use uart for status updates

This commit is contained in:
Mario Hüttel 2021-04-08 21:23:25 +02:00
parent d962110823
commit 08ec458e8f
8 changed files with 173 additions and 9 deletions

View File

@ -37,7 +37,7 @@
#include <stm-periph/stm32-gpio-macros.h>
#include <stm-periph/rcc-manager.h>
#include <stm-periph/uart.h>
#include <reflow-controller/shell-uart-config.h>
#include <reflow-controller/periph-config/shell-uart-config.h>
#include <reflow-controller/oven-driver.h>
#include <fatfs/ff.h>
#include <reflow-controller/ui/gui.h>

View File

@ -13,7 +13,7 @@ set(ELFFILE "${PROJECT_NAME}.elf")
aux_source_directory("." SRCS)
aux_source_directory("fatfs" FATFS_SRCS)
aux_source_directory("fatfs/shimatta_sdio_driver" SDIO_SRCS)
aux_source_directory("../../stm-periph" STM_PERIPH_SRCS)
set(STM_PERIPH_SRCS "../../stm-periph/backup-ram.c" "../../stm-periph/rcc-manager.c" "../../stm-periph/crc-unit.c")
set(SAFETY_MEMORY_SRCS "../../safety/safety-memory.c")
add_executable(${ELFFILE} ${SRCS} ${FATFS_SRCS} ${SDIO_SRCS} ${STM_PERIPH_SRCS} ${SAFETY_MEMORY_SRCS})

View File

@ -37,22 +37,22 @@ void flash_writer_perform_mass_erase(void)
uint32_t flash_writer_get_flash_size(void)
{
uint32_t flash_size;
const uint32_t *flash_size_ptr = (const uint32_t *)0x1FFF7A22UL;
const uint16_t *flash_size_ptr = (const uint16_t *)0x1FFF7A22UL;
flash_size = *flash_size_ptr;
flash_size = (uint32_t)*flash_size_ptr;
flash_size *= 1024;
return flash_size;
}
int flash_writer_write_to_memory(void *dest, void *src, uint32_t size)
int flash_writer_write_to_memory(void *dest, const void *src, uint32_t size)
{
uint32_t full_word_cnt;
uint32_t byte_cnt;
uint32_t idx;
uint32_t *word_src_ptr;
const uint32_t *word_src_ptr;
uint32_t *word_dest_ptr;
char *char_src_ptr;
const char *char_src_ptr;
char *char_dest_ptr;
flash_writer_enable_access();

View File

@ -11,6 +11,6 @@ uint32_t flash_writer_get_flash_size(void);
uint32_t flash_writer_get_base_address(void);
int flash_writer_write_to_memory(void *dest, void *src, uint32_t size);
int flash_writer_write_to_memory(void *dest, const void *src, uint32_t size);
#endif /* _FLASH_WRITER_H_ */

View File

@ -13,6 +13,8 @@
#include "flash-writer.h"
#include <stdbool.h>
#include <string.h>
#include "uart.h"
static volatile unsigned int wait_tick;
@ -46,6 +48,9 @@ static void __attribute__((noreturn)) ram_code_exit(bool updated)
boot_status.reboot_to_bootloader = 0x0UL;
safety_memory_set_boot_status(&boot_status);
uart_send_string("Rebooting in 1s...\r\n");
sdio_wait_ms(1000);
NVIC_SystemReset();
while(1);
}
@ -90,17 +95,103 @@ exit:
return retval;
}
int write_flash_from_buffer(const char *buffer, uint32_t len, uint32_t addr)
{
return flash_writer_write_to_memory((void *)addr, buffer, len);
}
int update_flash_from_file(const char *fname)
{
enum hex_parser_ret hex_ret;
struct hex_parser parser;
static char write_buffer[4096];
uint32_t wbuffer_base_addr = 0;
uint32_t wbuffer_fill_level = 0;
uint32_t addr;
static char tmp_buff[256];
size_t dlen;
int retval = 0;
int res;
hex_ret = hex_parser_open(&parser, fname);
if (hex_ret != HEX_PARSER_OK) {
uart_send_string("Error reading hex file.\r\n");
return -1;
}
do {
hex_ret = hex_parser_parse(&parser, &addr, tmp_buff, sizeof(tmp_buff), &dlen);
if (hex_ret == HEX_PARSER_DATA_OK) {
/* Check if tmp would fit in wbuffer */
if (dlen + wbuffer_fill_level > sizeof(write_buffer)) {
/* Write out the buffer and clean it if it doens't fit */
res = write_flash_from_buffer(write_buffer, wbuffer_fill_level, wbuffer_base_addr);
if (res) {
retval = -4;
goto exit_parser_close;
}
wbuffer_fill_level = 0;
wbuffer_base_addr = 0;
}
/* Check if parsed data can be linearily appended to buffer */
if (wbuffer_fill_level && wbuffer_base_addr + wbuffer_fill_level != addr) {
/* Write out the buffer and clean it if it cannot be appended */
res = write_flash_from_buffer(write_buffer, wbuffer_fill_level, wbuffer_base_addr);
if (res) {
retval = -4;
goto exit_parser_close;
}
wbuffer_fill_level = 0;
wbuffer_base_addr = 0;
}
/* Fill in the data into the buffer */
if (wbuffer_fill_level == 0) {
wbuffer_base_addr = addr;
}
memcpy(&write_buffer[wbuffer_fill_level], tmp_buff, dlen);
wbuffer_fill_level += dlen;
}
} while (hex_ret == HEX_PARSER_DATA_OK || hex_ret == HEX_PARSER_OK);
if (hex_ret == HEX_PARSER_EOF_RECORD) {
if (wbuffer_fill_level > 0) {
res = write_flash_from_buffer(write_buffer, wbuffer_fill_level, wbuffer_base_addr);
if (res) {
retval = -4;
goto exit_parser_close;
}
}
retval = 0;
} else {
retval = -3;
}
exit_parser_close:
hex_parser_close(&parser);
return retval;
}
int ram_code_main(void)
{
FRESULT fres;
int res;
enum safety_memory_state safety_mem_state;
static char filename[256];
int retries = 3;
SysTick_Config(168000UL);
external_watchdog_disable();
__enable_irq();
/* Init the uart module
* Pins don't need configuration. They're already setup by the main program
*/
uart_init();
uart_send_string("Updater started.\r\n");
res = safety_memory_init(&safety_mem_state);
if (res || safety_mem_state != SAFETY_MEMORY_INIT_VALID_MEMORY) {
ram_code_exit(false);
@ -108,6 +199,7 @@ int ram_code_main(void)
fres = f_mount(fs, "0:/", 1);
if (fres != FR_OK) {
uart_send_string("Could not mount SD card\r\n");
ram_code_exit(false);
}
@ -115,10 +207,43 @@ int ram_code_main(void)
if (res)
ram_code_exit(false);
uart_send_string("Checking hex file\r\n");
uart_send_string(filename);
uart_send_string("\r\n");
if (check_hex_file(filename)) {
uart_send_string("Error in hex file\r\n");
ram_code_exit(false);
}
uart_send_string("File ");
uart_send_string(filename);
uart_send_string(" checked successfully.\r\n");
uart_send_string("Starting updater...\r\n");
do {
uart_send_string("Erasing chip...");
flash_writer_perform_mass_erase();
uart_send_string(" done\r\n");
uart_send_string("Programming flash...\r\n");
res = update_flash_from_file(filename);
if (res) {
uart_send_string("Programming NOT successful.\r\n");
if (retries > 0) {
uart_send_string("Will retry...\r\n");
}
} else {
uart_send_string("Programming completed successfully!\r\n");
break;
}
} while (retries > 0);
if (res) {
}
while(1) {
__WFI();
}

View File

@ -0,0 +1,29 @@
#include "uart.h"
#include <reflow-controller/periph-config/shell-uart-config.h>
#include <stm32/stm32f4xx.h>
#include <string.h>
void uart_init(void)
{
SHELL_UART_RCC_REG |= SHELL_UART_RCC_MASK;
SHELL_UART_PERIPH->BRR = SHELL_UART_BRR_REG_VALUE;
SHELL_UART_PERIPH->CR2 = 0;
SHELL_UART_PERIPH->CR3 = 0;
SHELL_UART_PERIPH->CR1 = USART_CR1_TE | USART_CR1_UE;
}
void uart_send_char(char c)
{
while (!(SHELL_UART_PERIPH->SR & USART_SR_TXE));
SHELL_UART_PERIPH->DR = c;
}
void uart_send_string(const char *str)
{
int len, i;
len = strlen(str);
for (i = 0; i < len; i++) {
uart_send_char(str[i]);
}
}

View File

@ -0,0 +1,10 @@
#ifndef _UART_H_
#define _UART_H_
void uart_init(void);
void uart_send_char(char c);
void uart_send_string(const char *str);
#endif /* _UART_H_ */