Skip to content

Commit fa04f1b

Browse files
committed
[nrf fromlist] susbys/dfu/img_util: refined ERASE PROGRESSIVELY implementation
Moved MCUboot trailer's status erase ahead any write operation. Upstream PR: zephyrproject-rtos/zephyr#79152 Signed-off-by: Andrzej Puzdrowski <[email protected]>
1 parent ae75e9e commit fa04f1b

File tree

1 file changed

+58
-27
lines changed

1 file changed

+58
-27
lines changed

subsys/dfu/img_util/flash_img.c

Lines changed: 58 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -43,44 +43,75 @@ BUILD_ASSERT((CONFIG_IMG_BLOCK_BUF_SIZE % FLASH_WRITE_BLOCK_SIZE == 0),
4343
"FLASH_WRITE_BLOCK_SIZE");
4444
#endif
4545

46+
static int scramble_mcuboot_trailer(struct flash_img_context *ctx)
47+
{
48+
int rc = 0;
49+
50+
#ifdef CONFIG_IMG_ERASE_PROGRESSIVELY
51+
if (stream_flash_bytes_written(&ctx->stream) == 0) {
52+
off_t toff = boot_get_trailer_status_offset(ctx->flash_area->fa_size);
53+
off_t offset;
54+
size_t size;
55+
const struct flash_parameters *fparams =
56+
flash_get_parameters(flash_area_get_device(ctx->flash_area));
57+
#ifdef CONFIG_STREAM_FLASH_ERASE
58+
/* for erasable devices prgressive-erase works only along with CONFIG_STREAM_FLASH_ERASE option*/
59+
if (flash_params_get_erase_cap(fparams) & FLASH_ERASE_C_EXPLICIT) {
60+
/* On devices with explicit erase we are aligning to page
61+
* layout.
62+
*/
63+
struct flash_pages_info info;
64+
65+
rc = flash_get_page_info_by_offs(flash_area_get_device(ctx->flash_area), toff,
66+
&info);
67+
if (rc != 0) {
68+
return rc;
69+
}
70+
offset = info.start_offset;
71+
size = info.size;
72+
73+
} else
74+
#endif
75+
{
76+
77+
/* On devices with no erase, we are aligning to write block
78+
* size.
79+
*/
80+
offset = (toff + fparams->write_block_size - 1) &
81+
~(fparams->write_block_size - 1);
82+
/* No alignment correction neede here, offset is corrected already */
83+
size = ctx->flash_area->fa_size - offset;
84+
}
85+
86+
rc = flash_area_flatten(ctx->flash_area, offset, size);
87+
}
88+
#endif
89+
90+
return rc;
91+
}
92+
93+
4694
int flash_img_buffered_write(struct flash_img_context *ctx, const uint8_t *data,
4795
size_t len, bool flush)
4896
{
4997
int rc;
5098

51-
rc = stream_flash_buffered_write(&ctx->stream, data, len, flush);
52-
if (!flush) {
99+
/* If there is need to erase trailer, that should happen before any
100+
* write is done to partition.
101+
*/
102+
rc = scramble_mcuboot_trailer(ctx);
103+
if (rc != 0) {
53104
return rc;
54105
}
55106

56-
#ifdef CONFIG_IMG_ERASE_PROGRESSIVELY
57-
ssize_t status_offset = boot_get_trailer_status_offset(
58-
ctx->flash_area->fa_size);
59107

60-
#ifdef CONFIG_STREAM_FLASH_ERASE
61-
const struct flash_parameters *fparams =
62-
flash_get_parameters(flash_area_get_device(ctx->flash_area));
63-
64-
if ((flash_params_get_erase_cap(fparams) & FLASH_ERASE_C_EXPLICIT)) {
65-
/* use pistine-page-erase procedure for a device which needs it */
66-
rc = stream_flash_erase_page(&ctx->stream,
67-
ctx->flash_area->fa_off +
68-
status_offset);
69-
} else
70-
#endif
71-
{
72-
if (status_offset > stream_flash_bytes_written(&ctx->stream)) {
73-
rc = flash_area_flatten(ctx->flash_area, status_offset,
74-
ctx->flash_area->fa_off - status_offset);
75-
} else {
76-
rc = 0;
77-
}
78-
}
79-
80-
if (rc) {
108+
/* if CONFIG_IMG_ERASE_PROGRESSIVELY is enabled the enabled CONFIG_STREAM_FLASH_ERASE
109+
* ensures that stream_flash erases flash progresively.
110+
*/
111+
rc = stream_flash_buffered_write(&ctx->stream, data, len, flush);
112+
if (!flush) {
81113
return rc;
82114
}
83-
#endif
84115

85116
flash_area_close(ctx->flash_area);
86117
ctx->flash_area = NULL;

0 commit comments

Comments
 (0)