This is an automated email from Gerrit. "Jérôme Pouiller <[email protected]>" just uploaded a new patch set to Gerrit, which you can find at https://review.openocd.org/c/openocd/+/9448
-- gerrit commit a5c1938c873f13339c7324fdea3fdf1ee12451a8 Author: Jérôme Pouiller <[email protected]> Date: Tue Feb 3 13:25:43 2026 +0100 flash/nor/efm32: Learn how to start CMU before to flash Silabs Series-2 SoC requiresto configure the CMU (Clock Management Unit) before to access to the flash. Co-developed-by: Peter Johanson <[email protected]> Signed-off-by: Peter Johanson <[email protected]> Signed-off-by: Jérôme Pouiller <[email protected]> Change-Id: I3fcedd2fcf24307e98ce47ba5eca1880fc8e5bc5 diff --git a/jimtcl b/jimtcl index f160866171..a77ef1a621 160000 --- a/jimtcl +++ b/jimtcl @@ -1 +1 @@ -Subproject commit f160866171457474f7c4d6ccda70f9b77524407e +Subproject commit a77ef1a6218fad4c928ddbdc03c1aedc41007e70 diff --git a/src/flash/nor/efm32.c b/src/flash/nor/efm32.c index 88613cac89..3d72ecc67f 100644 --- a/src/flash/nor/efm32.c +++ b/src/flash/nor/efm32.c @@ -98,6 +98,9 @@ static const struct efm32_dev_info_addr efm32_dev_info_addr[] = { #define EFM32_MSC_STATUS_ERASEABORTED_MASK 0x0020 #define EFM32_MSC_LOCK_LOCKKEY 0x1b71 +/* Series 2 only */ +#define EFM32_CMU_REG_CLKEN1_SET 0x50009068 + enum efm32_bank_index { EFM32_BANK_INDEX_MAIN, EFM32_BANK_INDEX_USER_DATA, @@ -386,6 +389,58 @@ static void efm32_free_driver_priv(struct flash_bank *bank) } } +static int efm32_mcs_clock_enable(struct flash_bank *bank) +{ + struct efm32_flash_chip *efm32_info = bank->driver_priv; + unsigned int s2_family; + uint32_t msc_clken; + int ret; + + if (efm32_info->info.family_data->series == 0 || + efm32_info->info.family_data->series == 1) + return ERROR_OK; + + ret = target_read_u32(bank->target, + EFM32_CMU_REG_CLKEN1_SET, + &msc_clken); + if (ret != ERROR_OK) { + LOG_ERROR("Failed to read CMU register"); + return ret; + } + + s2_family = FIELD_GET(EFM32_DI_PARTINFO_FAMILY_MASK, + efm32_info->info.part_info); + switch (s2_family) { + case 21: + msc_clken = 0; + break; + case 22: + case 27: + case 29: + msc_clken = BIT(17); + break; + case 23: + case 24: + case 25: + case 26: + case 28: + msc_clken = BIT(16); + break; + default: + LOG_WARNING("Don't know EFR/EFM Gx family number, can't set MSC register. Use default values.."); + msc_clken = BIT(16); + } + ret = target_write_u32(bank->target, + EFM32_CMU_REG_CLKEN1_SET, + msc_clken); + if (ret != ERROR_OK) { + LOG_ERROR("Failed to enable MSC clock"); + return ret; + } + + return ERROR_OK; +} + /* set or reset given bits in a register */ static int efm32_set_reg_bits(struct flash_bank *bank, uint32_t reg, uint32_t bitmask, int set) @@ -515,6 +570,8 @@ static int efm32_erase(struct flash_bank *bank, unsigned int first, return ERROR_TARGET_NOT_HALTED; } + efm32_mcs_clock_enable(bank); + efm32_msc_lock(bank, 0); ret = efm32_set_wren(bank, 1); if (ret != ERROR_OK) { @@ -1005,6 +1062,8 @@ static int efm32_priv_write(struct flash_bank *bank, const uint8_t *buffer, uint32_t words_remaining = count / 4; int retval, retval2; + efm32_mcs_clock_enable(bank); + /* unlock flash registers */ efm32_msc_lock(bank, 0); retval = efm32_set_wren(bank, 1); @@ -1120,6 +1179,8 @@ static int efm32_probe(struct flash_bank *bank) free(bank->sectors); bank->sectors = NULL; + efm32_mcs_clock_enable(bank); + if (bank->base == EFM32_FLASH_BASE) { bank->num_sectors = efm32_mcu_info->flash_sz_kib * 1024 / efm32_mcu_info->page_size; assert(bank->num_sectors > 0); --
