drivers/flash/nrf: Workaround for nrf91 errata 7
Fix UICR read access. Signed-off-by: Dominik Ermel <dominik.ermel@nordicsemi.no>
This commit is contained in:
parent
cc5766bc4b
commit
1f3605de21
1 changed files with 31 additions and 2 deletions
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 2017-2018 Nordic Semiconductor ASA
|
* Copyright (c) 2017-2023 Nordic Semiconductor ASA
|
||||||
* Copyright (c) 2016 Linaro Limited
|
* Copyright (c) 2016 Linaro Limited
|
||||||
* Copyright (c) 2016 Intel Corporation
|
* Copyright (c) 2016 Intel Corporation
|
||||||
*
|
*
|
||||||
|
@ -116,6 +116,26 @@ static inline bool is_uicr_addr_valid(off_t addr, size_t len)
|
||||||
#endif /* CONFIG_SOC_FLASH_NRF_UICR */
|
#endif /* CONFIG_SOC_FLASH_NRF_UICR */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if CONFIG_SOC_FLASH_NRF_UICR && IS_ENABLED(NRF91_ERRATA_7_ENABLE_WORKAROUND)
|
||||||
|
static inline void nrf91_errata_7_enter(void)
|
||||||
|
{
|
||||||
|
__disable_irq();
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void nrf91_errata_7_exit(void)
|
||||||
|
{
|
||||||
|
__DSB();
|
||||||
|
__enable_irq();
|
||||||
|
}
|
||||||
|
|
||||||
|
static void nrf_buffer_read_91_uicr(void *data, off_t addr, size_t len)
|
||||||
|
{
|
||||||
|
nrf91_errata_7_enter();
|
||||||
|
nrf_nvmc_buffer_read(data, (uint32_t)addr, len);
|
||||||
|
nrf91_errata_7_exit();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
static void nvmc_wait_ready(void)
|
static void nvmc_wait_ready(void)
|
||||||
{
|
{
|
||||||
while (!nrfx_nvmc_write_done_check()) {
|
while (!nrfx_nvmc_write_done_check()) {
|
||||||
|
@ -125,9 +145,11 @@ static void nvmc_wait_ready(void)
|
||||||
static int flash_nrf_read(const struct device *dev, off_t addr,
|
static int flash_nrf_read(const struct device *dev, off_t addr,
|
||||||
void *data, size_t len)
|
void *data, size_t len)
|
||||||
{
|
{
|
||||||
|
const bool within_uicr = is_uicr_addr_valid(addr, len);
|
||||||
|
|
||||||
if (is_regular_addr_valid(addr, len)) {
|
if (is_regular_addr_valid(addr, len)) {
|
||||||
addr += DT_REG_ADDR(SOC_NV_FLASH_NODE);
|
addr += DT_REG_ADDR(SOC_NV_FLASH_NODE);
|
||||||
} else if (!is_uicr_addr_valid(addr, len)) {
|
} else if (!within_uicr) {
|
||||||
LOG_ERR("invalid address: 0x%08lx:%zu",
|
LOG_ERR("invalid address: 0x%08lx:%zu",
|
||||||
(unsigned long)addr, len);
|
(unsigned long)addr, len);
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
|
@ -137,6 +159,13 @@ static int flash_nrf_read(const struct device *dev, off_t addr,
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if CONFIG_SOC_FLASH_NRF_UICR && IS_ENABLED(NRF91_ERRATA_7_ENABLE_WORKAROUND)
|
||||||
|
if (within_uicr) {
|
||||||
|
nrf_buffer_read_91_uicr(data, (uint32_t)addr, len);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
nrf_nvmc_buffer_read(data, (uint32_t)addr, len);
|
nrf_nvmc_buffer_read(data, (uint32_t)addr, len);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue