This is an automated email from Gerrit. Artur Troian ([email protected]) just uploaded a new patch set to Gerrit, which you can find at http://openocd.zylin.com/5303
-- gerrit commit 62a6f88918b6ff80f1e1ea6db68bbac9a436252b Author: Artur Troian <[email protected]> Date: Fri Sep 20 14:16:42 2019 +0800 flash/nor/stm32lx.c: fix target flash loader make target loader to count nop cycles 63 AHB between first 2 words and 6 between all next in half-page programming mode. It prevents CPU to fall into BSY loop when second word missed because flash controller is not yet ready to accept it Refer to the DocID025942 Rev 8:Multiple programming operation (half page): page 73 Change-Id: I0c73fb06baf72db39ef568b6bd5ae20c1f8c67a4 Signed-off-by: Artur Troian <[email protected]> diff --git a/contrib/loaders/flash/stm32/stm32lx.S b/contrib/loaders/flash/stm32/stm32lx.S index bcae7a4..4fcd84e 100644 --- a/contrib/loaders/flash/stm32/stm32lx.S +++ b/contrib/loaders/flash/stm32/stm32lx.S @@ -10,6 +10,8 @@ * * * Copyright (C) 2017 Armin van der Togt * * [email protected] * + * Copyright (C) 2019 Artur Troian * + * troian dot ap at gmail dot com * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * @@ -27,37 +29,49 @@ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * ***************************************************************************/ - .text .syntax unified .cpu cortex-m0 .thumb /* - r0 - destination address - r1 - source address - r2 - count -*/ + * Params : + * r0 = target address + * r1 = source address + * r2 = count (32bit words) + * r3 = flash base + */ .thumb_func .global _start _start: - // r2 = source + count * 4 - lsls r2, r2, #2 - adds r2, r1, r2 - // Go to compare - b test_done -write_word: - // load word from address in r1 and increase r1 by 4 - ldmia r1!, {r3} - // store word to address in r0 and increase r0 by 4 - stmia r0!, {r3} -test_done: - // compare r1 and r2 - cmp r1, r2 - // loop if not equal - bne write_word + movs r6, #0 + +check_bounds: + cmp r2, #0 + bne store_word + bkpt 0x0000 - // Set breakpoint to exit - bkpt #0x00 +end_loop: + b end_loop +store_word: + movs r4, #15 + lsls r5, r6, #2 + ldmia r1!, {r7} + stmia r0!, {r7} + adds r5, r6, #1 + movs r6, r5 + tst r5, r4 + bne store_word + movs r5, r3 +copy_loop: + movs r4, #1 + ldr r7, [r5, #24] + tst r7, r4 + bne copy_loop + ldr r7, [r5, #24] + subs r2, #16 + orrs r7, r4 + str r7, [r5, #24] + b check_bounds diff --git a/contrib/loaders/flash/stm32/stm32lx.inc b/contrib/loaders/flash/stm32/stm32lx.inc index eaaf184..b73a49b 100644 --- a/contrib/loaders/flash/stm32/stm32lx.inc +++ b/contrib/loaders/flash/stm32/stm32lx.inc @@ -1,2 +1,5 @@ /* Autogenerated with ../../../../src/helper/bin2char.sh */ -0x92,0x00,0x8a,0x18,0x01,0xe0,0x08,0xc9,0x08,0xc0,0x91,0x42,0xfb,0xd1,0x00,0xbe, +0x00,0x26,0x00,0x2a,0x01,0xd1,0x00,0xbe,0xfe,0xe7,0x0f,0x24,0xb5,0x00,0x80,0xc9, +0x80,0xc0,0x75,0x1c,0x2e,0x00,0x25,0x42,0xf7,0xd1,0x1d,0x00,0x01,0x24,0xaf,0x69, +0x27,0x42,0xfb,0xd1,0xaf,0x69,0x10,0x3a,0x27,0x43,0xaf,0x61,0xe9,0xe7, + diff --git a/src/flash/nor/stm32lx.c b/src/flash/nor/stm32lx.c index e6473f8..6a2651b 100644 --- a/src/flash/nor/stm32lx.c +++ b/src/flash/nor/stm32lx.c @@ -436,7 +436,7 @@ static int stm32lx_write_half_pages(struct flash_bank *bank, const uint8_t *buff struct working_area *source; uint32_t address = bank->base + offset; - struct reg_param reg_params[3]; + struct reg_param reg_params[4]; struct armv7m_algorithm armv7m_info; int retval = ERROR_OK; @@ -490,6 +490,7 @@ static int stm32lx_write_half_pages(struct flash_bank *bank, const uint8_t *buff init_reg_param(®_params[0], "r0", 32, PARAM_OUT); init_reg_param(®_params[1], "r1", 32, PARAM_OUT); init_reg_param(®_params[2], "r2", 32, PARAM_OUT); + init_reg_param(®_params[3], "r3", 32, PARAM_OUT); /* Enable half-page write */ retval = stm32lx_enable_write_half_page(bank); @@ -500,6 +501,7 @@ static int stm32lx_write_half_pages(struct flash_bank *bank, const uint8_t *buff destroy_reg_param(®_params[0]); destroy_reg_param(®_params[1]); destroy_reg_param(®_params[2]); + destroy_reg_param(®_params[3]); return retval; } @@ -532,6 +534,7 @@ static int stm32lx_write_half_pages(struct flash_bank *bank, const uint8_t *buff buf_set_u32(reg_params[1].value, 0, 32, source->address); /* The length of the copy (R2) */ buf_set_u32(reg_params[2].value, 0, 32, this_count / 4); + buf_set_u32(reg_params[3].value, 0, 32, stm32lx_info->flash_base); /* 5: Execute the bunch of code */ retval = target_run_algorithm(target, 0, NULL, sizeof(reg_params) @@ -599,6 +602,7 @@ static int stm32lx_write_half_pages(struct flash_bank *bank, const uint8_t *buff destroy_reg_param(®_params[0]); destroy_reg_param(®_params[1]); destroy_reg_param(®_params[2]); + destroy_reg_param(®_params[3]); return retval; } @@ -1045,7 +1049,7 @@ static int stm32lx_enable_write_half_page(struct flash_bank *bank) if (retval != ERROR_OK) return retval; - reg32 |= FLASH_PECR__FPRG; + reg32 |= FLASH_PECR__FPRG | FLASH_PECR__PROG; retval = target_write_u32(target, stm32lx_info->flash_base + FLASH_PECR, reg32); if (retval != ERROR_OK) -- _______________________________________________ OpenOCD-devel mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/openocd-devel
