Просмотр исходного кода

AT32Fxx: Implement firmware update

Keir Fraser 4 лет назад
Родитель
Сommit
001cf97ca8

+ 2 - 2
bootloader/Bootloader.ld.S

@@ -1,10 +1,10 @@
 
-#if MCU == STM32F1 || MCU == AT32F415
+#if MCU == STM32F1
 
 #define FLASH_BASE 0x08000000
 #define FLASH_LEN  8K
 
-#elif MCU == STM32F7
+#elif MCU == STM32F7 || MCU == AT32F415
 
 #define FLASH_BASE 0x08000000
 #define FLASH_LEN  16K

+ 3 - 0
inc/mcu/at32/f415.h

@@ -1,2 +1,5 @@
 
 #include "../stm32/f1.h"
+
+#undef FLASH_PAGE_SIZE
+extern unsigned int FLASH_PAGE_SIZE;

+ 3 - 0
inc/util.h

@@ -109,6 +109,9 @@ uint16_t crc16_ccitt(const void *buf, size_t len, uint16_t crc);
 /* Build info. */
 extern const uint8_t fw_major, fw_minor;
 
+/* Bootloader mode flag. */
+extern volatile uint32_t _reset_flag;
+
 /* Text/data/BSS address ranges. */
 extern char _stext[], _etext[];
 extern char _sdat[], _edat[], _ldat[];

+ 3 - 3
scripts/greaseweazle/tools/util.py

@@ -271,7 +271,7 @@ def usb_open(devicename, is_update=False, mode_check=True):
         if not usb.jumperless_update:
             print(" - Disconnect from USB")
             print(" - Install the Update Jumper at pins %s"
-                  % ("RXI-TXO" if usb.hw_model == 7 else "DCLK-GND"))
+                  % ("RXI-TXO" if usb.hw_model != 1 else "DCLK-GND"))
             print(" - Reconnect to USB")
         print(" - Run \"gw update\" to install firmware v%u.%u" %
               (version.major, version.minor))
@@ -282,7 +282,7 @@ def usb_open(devicename, is_update=False, mode_check=True):
     usb = USB.Unit(serial.Serial(devicename))
     usb.port_info = port_info(devicename)
     is_win7 = (platform.system() == 'Windows' and platform.release() == '7')
-    usb.jumperless_update = usb.hw_model == 7 and not is_win7
+    usb.jumperless_update = usb.hw_model != 1 and not is_win7
 
     if not mode_check:
         return usb
@@ -297,7 +297,7 @@ def usb_open(devicename, is_update=False, mode_check=True):
         if usb.update_jumpered:
             print(" - For normal operation disconnect from USB and remove "
                   "the Update Jumper at pins %s"
-                  % ("RXI-TXO" if usb.hw_model == 7 else "DCLK-GND"))
+                  % ("RXI-TXO" if usb.hw_model != 1 else "DCLK-GND"))
         else:
             print(" - Main firmware is erased: You *must* perform an update!")
         sys.exit(1)

+ 1 - 1
scripts/mk_update.py

@@ -41,7 +41,7 @@ hw_model_to_name = { 1: 'STM32F103',
 def mk_cat_entry(dat, hw_model, sig):
     max_kb = { 1: { b'BL':  8, b'GW': 56 },
                7: { b'BL': 16, b'GW': 48 },
-               4: { b'BL':  8, b'GW': 56 } }
+               4: { b'BL': 16, b'GW': 48 } }
     dlen = len(dat)
     assert (dlen & 3) == 0, "input is not longword padded"
     assert dlen <= max_kb[hw_model][sig]*1024, "input is too long"

+ 9 - 1
scripts/stm32.ld.S

@@ -28,6 +28,13 @@ SECTIONS
     _etext = .;
   } >FLASH
 
+#if MCU == AT32F415
+  .flags : {
+    _reset_flag = .;
+    . = . + 4;
+  } >RAM
+#endif
+
   .data : AT (_etext) {
     . = ALIGN(4);
     _sdat = .;
@@ -55,8 +62,9 @@ SECTIONS
 
 #if MCU == STM32F7
   .ext_ram (NOLOAD) : {
-    . = ALIGN(8);
     _ext_ram_start = .;
+    _reset_flag = .;
+    . = . + 4;
     *(.ext_ram)
     . = ALIGN(4);
     _ext_ram_end = .;

+ 2 - 2
src/Greaseweazle.ld.S

@@ -1,10 +1,10 @@
 
-#if MCU == STM32F1 || MCU == AT32F415
+#if MCU == STM32F1
 
 #define FLASH_BASE 0x08002000
 #define FLASH_LEN  56K
 
-#elif MCU == STM32F7
+#elif MCU == STM32F7 || MCU == AT32F415
 
 #define FLASH_BASE 0x08004000
 #define FLASH_LEN  48K

+ 2 - 2
src/floppy.c

@@ -1321,7 +1321,7 @@ static void process_command(void)
         sink_source_prep(&ssb);
         break;
     }
-#if MCU == STM32F7
+#if MCU != STM32F1
     case CMD_SWITCH_FW_MODE: {
         uint8_t mode = u_buf[2];
         if ((len != 3) || (mode & ~1))
@@ -1330,7 +1330,7 @@ static void process_command(void)
             usb_deinit();
             delay_ms(500);
             /* Poke a flag in SRAM1, picked up by the bootloader. */
-            *(volatile uint32_t *)0x20010000 = 0xdeadbeef;
+            _reset_flag = 0xdeadbeef;
             dcache_disable();
             system_reset();
         }

+ 8 - 44
src/fw_update.c

@@ -9,11 +9,11 @@
  * See the file COPYING for more details, or visit <http://unlicense.org>.
  */
 
-#if MCU == STM32F1 || MCU == AT32F415
+#if MCU == STM32F1
 /*  8kB-64kB (56kB total) */
 #define FIRMWARE_START 0x08002000
 #define FIRMWARE_END   0x08010000
-#elif MCU == STM32F7
+#elif MCU == STM32F7 || MCU == AT32F415
 /* 16kB-64KB (48kB total) */
 #define FIRMWARE_START 0x08004000
 #define FIRMWARE_END   0x08010000
@@ -159,7 +159,7 @@ static void process_command(void)
         update_prep(u_len);
         break;
     }
-#if MCU == STM32F7
+#if MCU != STM32F1
     case CMD_SWITCH_FW_MODE: {
         uint8_t mode = u_buf[2];
         if ((len != 3) || (mode & ~1))
@@ -247,13 +247,13 @@ static bool_t enter_bootloader(void)
     return upd_strapped;
 }
 
-#elif MCU == STM32F7
+#else
 
 static bool_t check_update_requested(void)
 {
     /* Check-and-clear a magic value poked into SRAM1 by the main firmware. */
-    bool_t match = (*(volatile uint32_t *)0x20010000 == 0xdeadbeef);
-    *(volatile uint32_t *)0x20010000 = 0;
+    bool_t match = (_reset_flag == 0xdeadbeef);
+    _reset_flag = 0;
     return match;
 }
 
@@ -262,48 +262,12 @@ static bool_t check_update_strapped(void)
     int i, j;
 
     /* Check whether the Serial TX/RX lines (PA9/PA10) are strapped. */
+#if MCU == STM32F7
     rcc->ahb1enr |= RCC_AHB1ENR_GPIOAEN;
     (void)rcc->ahb1enr;
-    gpio_configure_pin(gpioa, 9, GPO_pushpull(IOSPD_LOW, HIGH));
-    gpio_configure_pin(gpioa, 10, GPI_pull_up);
-    for (i = 0; i < 10; i++) {
-        gpio_write_pin(gpioa, 9, i&1);
-        for (j = 0; j < 10000; j++)
-            cpu_relax();
-        if (gpio_read_pin(gpioa, 10) != (i&1))
-            return FALSE;
-    }
-
-    return TRUE;
-}
-
-static bool_t enter_bootloader(void)
-{
-    bool_t upd_requested = check_update_requested();
-    upd_strapped = check_update_strapped();
-    return upd_requested || upd_strapped;
-}
-
-#elif MCU == AT32F415
-
-static bool_t check_update_requested(void)
-{
-#if 1
-    return FALSE;
 #else
-    /* Check-and-clear a magic value poked into SRAM1 by the main firmware. */
-    bool_t match = (*(volatile uint32_t *)0x20010000 == 0xdeadbeef);
-    *(volatile uint32_t *)0x20010000 = 0;
-    return match;
-#endif
-}
-
-static bool_t check_update_strapped(void)
-{
-    int i, j;
-
-    /* Check whether the Serial TX/RX lines (PA9/PA10) are strapped. */
     rcc->apb2enr |= RCC_APB2ENR_IOPAEN;
+#endif
     gpio_configure_pin(gpioa, 9, GPO_pushpull(IOSPD_LOW, HIGH));
     gpio_configure_pin(gpioa, 10, GPI_pull_up);
     for (i = 0; i < 10; i++) {

+ 1 - 1
src/mcu/at32f415/floppy.c

@@ -103,7 +103,7 @@ found:
 
 
 /* We sometimes cast u_buf to uint32_t[], hence the alignment constraint. */
-#define U_BUF_SZ 8192
+#define U_BUF_SZ 16384
 static uint8_t u_buf[U_BUF_SZ] aligned(4);
 
 static void floppy_mcu_init(void)

+ 10 - 0
src/mcu/at32f415/stm32.c

@@ -9,6 +9,8 @@
  * See the file COPYING for more details, or visit <http://unlicense.org>.
  */
 
+unsigned int FLASH_PAGE_SIZE = 2048;
+
 static void clock_init(void)
 {
     /* Flash controller: reads require 2 wait states at 72MHz. */
@@ -57,12 +59,20 @@ static void peripheral_init(void)
     gpio_configure_pin(gpiob,  4, GPI_floating);
 }
 
+static void identify_mcu(void)
+{
+    unsigned int flash_kb = *(uint16_t *)0x1ffff7e0;
+    if (flash_kb <= 128)
+        FLASH_PAGE_SIZE = 1024;
+}
+
 void stm32_init(void)
 {
     cortex_init();
     clock_init();
     peripheral_init();
     cpu_sync();
+    identify_mcu();
 }
 
 void gpio_configure_pin(GPIO gpio, unsigned int pin, unsigned int mode)