diff --git a/flashloaders/stm32l0x.s b/flashloaders/stm32l0x.s index 9fc44468f..fcbd06e39 100644 --- a/flashloaders/stm32l0x.s +++ b/flashloaders/stm32l0x.s @@ -34,31 +34,29 @@ .global write /* - r0 - destination address - r1 - source address + r0 - source address + r1 - destination address r2 - count */ - // Set 0 to r3 - movs r3, #0 // Go to compare - b.n test_done + b test_done write_word: // Load one word from address in r0, increment by 4 - ldr r4, [r1] + ldr r4, [r0] // Store the word to address in r1, increment by 4 - str r4, [r0] - // Increment r3 - adds r3, #1 + str r4, [r1] + // Decrement r2 + subs r2, #1 adds r1, #4 // does not matter, only first addr is important // next 15 bytes are in sequnce RM0367 page 66 adds r0, #4 test_done: - // Compare r3 and r2 - cmp r3, r2 + // Test r2 + cmp r2, #0 // Loop if not zero bcc.n write_word diff --git a/flashloaders/stm32lx.s b/flashloaders/stm32lx.s index 799d1345c..10e5644bf 100644 --- a/flashloaders/stm32lx.s +++ b/flashloaders/stm32lx.s @@ -25,7 +25,7 @@ ***************************************************************************/ -// Build : arm-eabi-gcc -c stm32lx.S +// Build : arm-eabi-gcc -c stm32lx.s .text .syntax unified .cpu cortex-m3 @@ -34,29 +34,27 @@ .global write /* - r0 - destination address - r1 - source address - r2 - count + r0 - source address + r1 - destination address + r2 - output, remaining word count */ - // Set 0 to r3 - movs r3, #0 // Go to compare - b.n test_done + b test_done write_word: // Load one word from address in r0, increment by 4 - ldr.w ip, [r1], #4 + ldr.w ip, [r0], #4 // Store the word to address in r1, increment by 4 - str.w ip, [r0], #4 - // Increment r3 - adds r3, #1 + str.w ip, [r1], #4 + // Decrement r2 + subs r2, #1 test_done: - // Compare r3 and r2 - cmp r3, r2 + // Test r2 + cmp r2, #0 // Loop if not zero - bcc.n write_word + bhi write_word // Set breakpoint to exit bkpt #0x00 diff --git a/src/common.c b/src/common.c index 7504c27ac..a3ffda7e4 100644 --- a/src/common.c +++ b/src/common.c @@ -593,6 +593,12 @@ int stlink_load_device_params(stlink_t *sl) { return -1; } + if (params->flash_type == FLASH_TYPE_UNKNOWN) { + WLOG("Invalid flash type, please check device declaration\n"); + return -1; + } + + // These are fixed... sl->flash_base = STM32_FLASH_BASE; sl->sram_base = STM32_SRAM_BASE; @@ -1503,47 +1509,20 @@ int write_loader_to_sram(stlink_t *sl, stm32_addr_t* addr, size_t* size) { }; static const uint8_t loader_code_stm32l[] = { - - /* openocd.git/contrib/loaders/flash/stm32lx.S - r0, input, dest addr - r1, input, source addr - r2, input, word count - r3, output, word count - */ - - 0x00, 0x23, - 0x04, 0xe0, - - 0x51, 0xf8, 0x04, 0xcb, - 0x40, 0xf8, 0x04, 0xcb, - 0x01, 0x33, - - 0x93, 0x42, - 0xf8, 0xd3, - 0x00, 0xbe - }; - - static const uint8_t loader_code_stm32l0[] = { - - /* - r0, input, dest addr - r1, input, source addr - r2, input, word count - r3, output, word count - */ - - 0x00, 0x23, - 0x04, 0xe0, - - 0x0c, 0x68, - 0x04, 0x60, - 0x01, 0x33, - 0x04, 0x31, - 0x04, 0x30, - - 0x93, 0x42, - 0xf8, 0xd3, - 0x00, 0xbe + // flashloaders/stm32lx.s + + 0x04, 0xe0, // b test_done ; Go to compare + // write_word: + 0x04, 0x68, // ldr r4, [r0] ; Load one word from address in r0 + 0x0c, 0x60, // str r4, [r1] ; Store the word to address in r1 + 0x04, 0x30, // adds r0, #4 ; Increment r0 + 0x04, 0x31, // adds r1, #4 ; Increment r1 + 0x01, 0x3a, // subs r2, #1 ; Decrement r2 + // test_done: + 0x00, 0x2a, // cmp r2, #0 ; Compare r2 to 0 + 0xf8, 0xd8, // bhi write_word ; Loop if above 0 + 0x00, 0xbe, // bkpt #0x00 ; Set breakpoint to exit + 0x00, 0x00 }; static const uint8_t loader_code_stm32f4[] = { @@ -1604,7 +1583,7 @@ int write_loader_to_sram(stlink_t *sl, stm32_addr_t* addr, size_t* size) { 0xfb, 0xd1, // bne.n 0x00, 0xf1, 0x08, 0x00, // add.w r0, r0, #8 0x01, 0xf1, 0x08, 0x01, // add.w r1, r1, #8 - 0xa2, 0xf1, 0x02, 0x02, // add.w r2, r2, #2 + 0xa2, 0xf1, 0x01, 0x02, // sub.w r2, r2, #1 0xef, 0xe7, // b.n 0x00, 0xbe, // done: bkpt 0x0000 0x00, 0x20, 0x02, 0x40 // flash_base: .word 0x40022000 @@ -1632,7 +1611,8 @@ int write_loader_to_sram(stlink_t *sl, stm32_addr_t* addr, size_t* size) { if (sl->chip_id == STM32_CHIPID_L1_MEDIUM || sl->chip_id == STM32_CHIPID_L1_CAT2 || sl->chip_id == STM32_CHIPID_L1_MEDIUM_PLUS || sl->chip_id == STM32_CHIPID_L1_HIGH - || sl->chip_id == STM32_CHIPID_L152_RE) { /* stm32l */ + || sl->chip_id == STM32_CHIPID_L152_RE + || sl->chip_id == STM32_CHIPID_L0 || sl->chip_id == STM32_CHIPID_L0_CAT5) { /* stm32l */ loader_code = loader_code_stm32l; loader_size = sizeof(loader_code_stm32l); } else if (sl->core_id == STM32VL_CORE_ID @@ -1663,9 +1643,6 @@ int write_loader_to_sram(stlink_t *sl, stm32_addr_t* addr, size_t* size) { } else if (sl->chip_id == STM32_CHIPID_F0 || sl->chip_id == STM32_CHIPID_F04 || sl->chip_id == STM32_CHIPID_F0_CAN || sl->chip_id == STM32_CHIPID_F0_SMALL || sl->chip_id == STM32_CHIPID_F09X) { loader_code = loader_code_stm32f0; loader_size = sizeof(loader_code_stm32f0); - } else if (sl->chip_id == STM32_CHIPID_L0 || sl->chip_id == STM32_CHIPID_L0_CAT5) { - loader_code = loader_code_stm32l0; - loader_size = sizeof(loader_code_stm32l0); } else if (sl->chip_id == STM32_CHIPID_L4) { loader_code = loader_code_stm32l4; loader_size = sizeof(loader_code_stm32l4); @@ -2068,8 +2045,8 @@ int stlink_fwrite_flash(stlink_t *sl, const char* path, stm32_addr_t addr) { int run_flash_loader(stlink_t *sl, flash_loader_t* fl, stm32_addr_t target, const uint8_t* buf, size_t size) { reg rr; - int target_reg, source_reg, i = 0; - size_t count; + int i = 0; + size_t count = 0; DLOG("Running flash loader, write address:%#x, size: %zd\n", target, size); // FIXME This can never return -1 @@ -2079,36 +2056,23 @@ int run_flash_loader(stlink_t *sl, flash_loader_t* fl, stm32_addr_t target, cons return -1; } - if (sl->flash_type == FLASH_TYPE_L0) { - count = size / sizeof(uint32_t); - if (size % sizeof(uint32_t)) - ++count; - target_reg = 0; - source_reg = 1; - } else if (sl->flash_type == FLASH_TYPE_F0) { + if (sl->flash_type == FLASH_TYPE_F0) { count = size / sizeof(uint16_t); if (size % sizeof(uint16_t)) ++count; - target_reg = 1; - source_reg = 0; - } else if (sl->flash_type == FLASH_TYPE_F4 || sl->flash_type == FLASH_TYPE_L4) { + } else if (sl->flash_type == FLASH_TYPE_F4 || sl->flash_type == FLASH_TYPE_L0) { count = size / sizeof(uint32_t); if (size % sizeof(uint32_t)) ++count; - if (sl->chip_id == STM32_CHIPID_L4) { - if (count % 2) - ++count; - } - target_reg = 1; - source_reg = 0; - } else { - fprintf(stderr, "unknown coreid 0x%x, don't know what flash loader to use\n", sl->core_id); - return -1; + } else if (sl->flash_type == FLASH_TYPE_L4) { + count = size / sizeof(uint64_t); + if (size % sizeof(uint64_t)) + ++count; } /* setup core */ - stlink_write_reg(sl, fl->buf_addr, source_reg); /* source */ - stlink_write_reg(sl, target, target_reg); /* target */ + stlink_write_reg(sl, fl->buf_addr, 0); /* source */ + stlink_write_reg(sl, target, 1); /* target */ stlink_write_reg(sl, count, 2); /* count */ stlink_write_reg(sl, 0, 3); /* flash bank 0 (input), only used on F0, but armless fopr others */ stlink_write_reg(sl, fl->loader_addr, 15); /* pc register */ @@ -2129,19 +2093,11 @@ int run_flash_loader(stlink_t *sl, flash_loader_t* fl, stm32_addr_t target, cons return -1; } - stlink_read_all_regs(sl, &rr); - /* check written byte count */ - if (sl->flash_type == FLASH_TYPE_L0) { - if (rr.r[3] != count) { - fprintf(stderr, "write error, count == %u\n", rr.r[3]); - return -1; - } - } else { - if (rr.r[2] != 0) { - fprintf(stderr, "write error, count == %u\n", rr.r[2]); - return -1; - } + stlink_read_reg(sl, 2, &rr); + if (rr.r[2] != 0) { + fprintf(stderr, "write error, count == %u\n", rr.r[2]); + return -1; } return 0;