From: openocd-gerrit <ope...@us...> - 2025-04-25 09:41:55
|
This is an automated email from the git hooks/post-receive script. It was generated because a ref change was pushed to the repository containing the project "Main OpenOCD repository". The branch, master has been updated via c914cfceab54245fae1aefd70e20d0ed549f9308 (commit) via 26729aa8b089230bf0896c32df9a4b7ae3ef6fee (commit) from 20d1d4405d73fe47efc07cb109454c088a8ecbc8 (commit) Those revisions listed above that are new to this repository have not appeared on any other notification email; so we list those revisions in full, below. - Log ----------------------------------------------------------------- commit c914cfceab54245fae1aefd70e20d0ed549f9308 Author: Tomas Vanek <va...@fb...> Date: Wed Aug 14 10:47:36 2024 +0200 flash/nor/rp2040: refactor finalizing calls and use them after erase Invalidate cache and restore flash XIP mode after erase and also in error cleanup after write/erase. Signed-off-by: Tomas Vanek <va...@fb...> Change-Id: If7e0c2d75f50f923e6bcbf0aa7bab53fe91b6cc8 Reviewed-on: https://review.openocd.org/c/openocd/+/8454 Tested-by: jenkins diff --git a/src/flash/nor/rp2040.c b/src/flash/nor/rp2040.c index c28bc8509..514cea8b6 100644 --- a/src/flash/nor/rp2040.c +++ b/src/flash/nor/rp2040.c @@ -732,6 +732,42 @@ static int setup_for_raw_flash_cmd(struct target *target, struct rp2040_flash_ba return ERROR_OK; } +static int rp2xxx_invalidate_cache_restore_xip(struct target *target, struct rp2040_flash_bank *priv) +{ + // Flash content has changed. We can now do a bit of poking to make + // the new flash contents visible to us via memory-mapped (XIP) interface + // in the 0x1... memory region. + + LOG_DEBUG("Flushing flash cache after write behind"); + + rp2xxx_rom_call_batch_record_t finishing_calls[2] = { + { + .pc = priv->jump_flush_cache, + .sp = priv->stack->address + priv->stack->size + }, + { + .sp = priv->stack->address + priv->stack->size + }, + }; + + int num_finishing_calls = 1; + // Note on RP2350 it's not *required* to call flash_enter_cmd_xip, since + // the ROM leaves flash XIPable by default in between direct-mode + // accesses + if (IS_RP2040(priv->id)) { + finishing_calls[num_finishing_calls++].pc = priv->jump_enter_cmd_xip; + } else if (priv->jump_flash_reset_address_trans) { + // Note flash_reset_address_trans function does not exist on older devices + finishing_calls[num_finishing_calls++].pc = priv->jump_flash_reset_address_trans; + } + + int retval = rp2xxx_call_rom_func_batch(target, priv, finishing_calls, num_finishing_calls); + if (retval != ERROR_OK) + LOG_ERROR("RP2040 write: failed to flush flash cache/restore XIP"); + + return retval; +} + static void cleanup_after_raw_flash_cmd(struct target *target, struct rp2040_flash_bank *priv) { /* OpenOCD is prone to trashing work-area allocations on target state @@ -805,45 +841,12 @@ static int rp2040_flash_write(struct flash_bank *bank, const uint8_t *buffer, ui count -= write_size; } - if (err != ERROR_OK) - goto cleanup_and_return; - - // Flash is successfully programmed. We can now do a bit of poking to make - // the new flash contents visible to us via memory-mapped (XIP) interface - // in the 0x1... memory region. - // - // Note on RP2350 it's not *required* to call flash_enter_cmd_xip, since - // the ROM leaves flash XIPable by default in between direct-mode - // accesses, but there's no harm in calling it anyway. - - LOG_DEBUG("Flushing flash cache after write behind"); - err = rp2xxx_call_rom_func(target, priv, priv->jump_flush_cache, NULL, 0); - - rp2xxx_rom_call_batch_record_t finishing_calls[3] = { - { - .pc = priv->jump_flush_cache, - .sp = priv->stack->address + priv->stack->size - }, - { - .pc = priv->jump_enter_cmd_xip, - .sp = priv->stack->address + priv->stack->size - }, - { - .pc = priv->jump_flash_reset_address_trans, - .sp = priv->stack->address + priv->stack->size - } - }; - // Note the last function does not exist on older devices: - int num_finishing_calls = priv->jump_flash_reset_address_trans ? 3 : 2; - - err = rp2xxx_call_rom_func_batch(target, priv, finishing_calls, num_finishing_calls); - if (err != ERROR_OK) { - LOG_ERROR("RP2040 write: failed to flush flash cache"); - goto cleanup_and_return; - } cleanup_and_return: target_free_working_area(target, bounce); + /* Don't propagate error or user gets fooled the flash write failed */ + (void)rp2xxx_invalidate_cache_restore_xip(target, priv); + cleanup_after_raw_flash_cmd(target, priv); return err; } @@ -912,6 +915,9 @@ static int rp2040_flash_erase(struct flash_bank *bank, unsigned int first, unsig cleanup_and_return: + /* Don't propagate error or user gets fooled the flash erase failed */ + (void)rp2xxx_invalidate_cache_restore_xip(target, priv); + cleanup_after_raw_flash_cmd(target, priv); return err; } commit 26729aa8b089230bf0896c32df9a4b7ae3ef6fee Author: Tomas Vanek <va...@fb...> Date: Wed Aug 14 10:41:55 2024 +0200 flash/nor/rp2040: improve flash write buffer size computation While on it: Define the names for the fixed flash page/sector sizes and use them instead of magic values. Fix memory leak on error return. Partially backported from former upstream rp2040.c Signed-off-by: Tomas Vanek <va...@fb...> Change-Id: If51c912f4d381ee47756a70f616ecdbee1ac0da7 Reviewed-on: https://review.openocd.org/c/openocd/+/8453 Tested-by: jenkins diff --git a/src/flash/nor/rp2040.c b/src/flash/nor/rp2040.c index 65c1e095b..c28bc8509 100644 --- a/src/flash/nor/rp2040.c +++ b/src/flash/nor/rp2040.c @@ -73,6 +73,9 @@ #define RP2XXX_MAX_ALGO_STACK_USAGE 1024 #define RP2XXX_MAX_RAM_ALGO_SIZE 1024 +#define RP2XXX_ROM_API_FIXED_FLASH_PAGE 256 +#define RP2XXX_ROM_API_FIXED_FLASH_SECTOR 4096 + // Calling bootrom functions on Arm RP2350 requires the redundancy // coprocessor (RCP) to be initialised. Usually this is done first thing by // the bootrom, but the debugger may skip this, e.g. by resetting the cores @@ -758,17 +761,19 @@ static int rp2040_flash_write(struct flash_bank *bank, const uint8_t *buffer, ui return ERROR_TARGET_NOT_HALTED; } - struct working_area *bounce; + struct working_area *bounce = NULL; int err = setup_for_raw_flash_cmd(target, priv); if (err != ERROR_OK) goto cleanup_and_return; - // Allocate as much memory as possible, rounded down to a whole number of flash pages - const unsigned int chunk_size = target_get_working_area_avail(target) & ~0xffu; - if (chunk_size == 0 || target_alloc_working_area(target, chunk_size, &bounce) != ERROR_OK) { + unsigned int avail_pages = target_get_working_area_avail(target) / RP2XXX_ROM_API_FIXED_FLASH_PAGE; + /* We try to allocate working area rounded down to device page size, + * al least 1 page, at most the write data size */ + unsigned int chunk_size = MIN(MAX(avail_pages, 1) * RP2XXX_ROM_API_FIXED_FLASH_PAGE, count); + err = target_alloc_working_area(target, chunk_size, &bounce); + if (err != ERROR_OK) { LOG_ERROR("Could not allocate bounce buffer for flash programming. Can't continue"); - err = ERROR_TARGET_RESOURCE_NOT_AVAILABLE; goto cleanup_and_return; } @@ -787,7 +792,8 @@ static int rp2040_flash_write(struct flash_bank *bank, const uint8_t *buffer, ui bounce->address, /* data */ write_size /* count */ }; - err = rp2xxx_call_rom_func(target, priv, priv->jump_flash_range_program, args, ARRAY_SIZE(args)); + err = rp2xxx_call_rom_func(target, priv, priv->jump_flash_range_program, + args, ARRAY_SIZE(args)); keep_alive(); if (err != ERROR_OK) { LOG_ERROR("Failed to invoke flash programming code on target"); @@ -798,7 +804,6 @@ static int rp2040_flash_write(struct flash_bank *bank, const uint8_t *buffer, ui offset += write_size; count -= write_size; } - target_free_working_area(target, bounce); if (err != ERROR_OK) goto cleanup_and_return; @@ -837,6 +842,8 @@ static int rp2040_flash_write(struct flash_bank *bank, const uint8_t *buffer, ui goto cleanup_and_return; } cleanup_and_return: + target_free_working_area(target, bounce); + cleanup_after_raw_flash_cmd(target, priv); return err; } @@ -1113,8 +1120,8 @@ static int rp2040_flash_probe(struct flash_bank *bank) return retval; /* the Boot ROM flash_range_program() routine requires page alignment */ - bank->write_start_alignment = 256; - bank->write_end_alignment = 256; + bank->write_start_alignment = RP2XXX_ROM_API_FIXED_FLASH_PAGE; + bank->write_end_alignment = RP2XXX_ROM_API_FIXED_FLASH_PAGE; uint32_t flash_id = 0; if (priv->size_override) { @@ -1168,7 +1175,7 @@ static int rp2040_flash_probe(struct flash_bank *bank) return ERROR_FLASH_BANK_INVALID; } - bank->num_sectors = bank->size / 4096; + bank->num_sectors = bank->size / RP2XXX_ROM_API_FIXED_FLASH_SECTOR; if (priv->size_override) { LOG_INFO("%s, QSPI Flash size override = %u KiB in %u sectors", @@ -1180,7 +1187,7 @@ static int rp2040_flash_probe(struct flash_bank *bank) } free(bank->sectors); - bank->sectors = alloc_block_array(0, 4096, bank->num_sectors); + bank->sectors = alloc_block_array(0, RP2XXX_ROM_API_FIXED_FLASH_SECTOR, bank->num_sectors); if (!bank->sectors) return ERROR_FAIL; ----------------------------------------------------------------------- Summary of changes: src/flash/nor/rp2040.c | 105 +++++++++++++++++++++++++++---------------------- 1 file changed, 59 insertions(+), 46 deletions(-) hooks/post-receive -- Main OpenOCD repository |