subsys/fs/nvs: Use flash_get_parameters() to get erase value

Use new flash API call to obtain erase value instead of relaying on
hardcoded literals.

Signed-off-by: Dominik Ermel <dominik.ermel@nordicsemi.no>
This commit is contained in:
Dominik Ermel 2020-06-03 18:33:09 +00:00 committed by Carles Cufí
commit 076282a117
4 changed files with 39 additions and 14 deletions

View file

@ -57,6 +57,7 @@ struct nvs_fs {
struct k_mutex nvs_lock;
struct device *flash_device;
const struct flash_parameters *flash_parameters;
};
/**

View file

@ -66,7 +66,9 @@ static int nvs_flash_al_wrt(struct nvs_fs *fs, uint32_t addr, const void *data,
}
if (len) {
memcpy(buf, data8, len);
(void)memset(buf + len, 0xff, fs->write_block_size - len);
(void)memset(buf + len, fs->flash_parameters->erase_value,
fs->write_block_size - len);
rc = flash_write(fs->flash_device, offset, buf,
fs->write_block_size);
if (rc) {
@ -221,7 +223,8 @@ static int nvs_flash_erase_sector(struct nvs_fs *fs, uint32_t addr)
off_t offset;
addr &= ADDR_SECT_MASK;
rc = nvs_flash_cmp_const(fs, addr, 0xff, fs->sector_size);
rc = nvs_flash_cmp_const(fs, addr, fs->flash_parameters->erase_value,
fs->sector_size);
if (rc <= 0) {
/* flash error or empty sector */
return rc;
@ -351,7 +354,7 @@ static int nvs_prev_ate(struct nvs_fs *fs, uint32_t *addr, struct nvs_ate *ate)
return rc;
}
rc = nvs_ate_cmp_const(&close_ate, 0xff);
rc = nvs_ate_cmp_const(&close_ate, fs->flash_parameters->erase_value);
/* at the end of filesystem */
if (!rc) {
*addr = fs->ate_wra;
@ -460,7 +463,7 @@ static int nvs_gc(struct nvs_fs *fs)
return rc;
}
rc = nvs_ate_cmp_const(&close_ate, 0xff);
rc = nvs_ate_cmp_const(&close_ate, fs->flash_parameters->erase_value);
if (!rc) {
rc = nvs_flash_erase_sector(fs, sec_addr);
if (rc) {
@ -545,6 +548,7 @@ static int nvs_startup(struct nvs_fs *fs)
*/
uint32_t addr = 0U;
uint16_t i, closed_sectors = 0;
uint8_t erase_value = fs->flash_parameters->erase_value;
k_mutex_lock(&fs->nvs_lock, K_FOREVER);
@ -555,14 +559,14 @@ static int nvs_startup(struct nvs_fs *fs)
for (i = 0; i < fs->sector_count; i++) {
addr = (i << ADDR_SECT_SHIFT) +
(uint16_t)(fs->sector_size - ate_size);
rc = nvs_flash_cmp_const(fs, addr, 0xff,
sizeof(struct nvs_ate));
rc = nvs_flash_cmp_const(fs, addr, erase_value,
sizeof(struct nvs_ate));
if (rc) {
/* closed sector */
closed_sectors++;
nvs_sector_advance(fs, &addr);
rc = nvs_flash_cmp_const(fs, addr, 0xff,
sizeof(struct nvs_ate));
rc = nvs_flash_cmp_const(fs, addr, erase_value,
sizeof(struct nvs_ate));
if (!rc) {
/* open sector */
break;
@ -581,8 +585,8 @@ static int nvs_startup(struct nvs_fs *fs)
* two sectors. Then we can only set it to the first sector if
* the last sector contains no ate's. So we check this first
*/
rc = nvs_flash_cmp_const(fs, addr - ate_size, 0xff,
sizeof(struct nvs_ate));
rc = nvs_flash_cmp_const(fs, addr - ate_size, erase_value,
sizeof(struct nvs_ate));
if (!rc) {
/* empty ate */
nvs_sector_advance(fs, &addr);
@ -590,7 +594,7 @@ static int nvs_startup(struct nvs_fs *fs)
}
/* addr contains address of the last ate in the most recent sector
* search for the first ate containing all 0xff
* search for the first ate containing all cells erased.
*/
fs->ate_wra = addr - ate_size;
fs->data_wra = addr & ADDR_SECT_MASK;
@ -601,7 +605,8 @@ static int nvs_startup(struct nvs_fs *fs)
goto end;
}
rc = nvs_ate_cmp_const(&last_ate, 0xff);
rc = nvs_ate_cmp_const(&last_ate, erase_value);
if (!rc) {
/* found ff empty location */
break;
@ -630,7 +635,8 @@ static int nvs_startup(struct nvs_fs *fs)
while (fs->ate_wra > fs->data_wra) {
empty_len = fs->ate_wra - fs->data_wra;
rc = nvs_flash_cmp_const(fs, fs->data_wra, 0xff, empty_len);
rc = nvs_flash_cmp_const(fs, fs->data_wra, erase_value,
empty_len);
if (rc < 0) {
goto end;
}
@ -647,7 +653,7 @@ static int nvs_startup(struct nvs_fs *fs)
*/
addr = fs->ate_wra & ADDR_SECT_MASK;
nvs_sector_advance(fs, &addr);
rc = nvs_flash_cmp_const(fs, addr, 0xff, fs->sector_size);
rc = nvs_flash_cmp_const(fs, addr, erase_value, fs->sector_size);
if (rc < 0) {
goto end;
}
@ -706,6 +712,12 @@ int nvs_init(struct nvs_fs *fs, const char *dev_name)
return -ENXIO;
}
fs->flash_parameters = flash_get_parameters(fs->flash_device);
if (fs->flash_parameters == NULL) {
LOG_ERR("Could not obtain flash parameters");
return -EINVAL;
}
write_block_size = flash_get_write_block_size(fs->flash_device);
/* check that the write block size is supported */

View file

@ -0,0 +1,9 @@
/*
* Copyright (c) 2020 Nordic Semiconductor ASA
*
* SPDX-License-Identifier: Apache-2.0
*/
&sim_flash {
erase-value = < 0x00 >;
};

View file

@ -1,3 +1,6 @@
tests:
filesystem.nvs:
platform_whitelist: qemu_x86
filesystem.nvs_0x00:
extra_args: DTC_OVERLAY_FILE=boards/qemu_x86_ev_0x00.overlay
platform_whitelist: qemu_x86