Repository navigation
Conversation
Erasing a big region can stall interrupts for too long which can trigger the watchdog and cause a reset. Therefore we erase sector- or blockwise, depending on the flash. Assisted-By: Claude Code Opus 5.5
Large writes and/or erases can lead to watchdog timeouts if the MTD subsystem does not leave enough interrupt time. Add a large write and erase to check for that. Assisted-By: Claude Code Opus 5.5
|
Here comes the
The H2 is too fast for the watchdog to trigger. |
|
I added the results for an ESP32-S2 board in comment #22945 (comment). |
| return 0; | ||
| } | ||
|
|
||
| SHELL_COMMAND(test_erase_all, "Write to every sector & erase them at once", cmd_test_erase_all); |
There was a problem hiding this comment.
Shouldn't the command simply be called test_erase, since you can specify the size to be deleted as the second argument?
There was a problem hiding this comment.
This started as a command that erases everything, but for e.g. a multi-gigabyte SD card this would take forever, that's why it got changed.
Co-authored-by: Gunar Schorcht <gunar@schorcht.net> Co-authored-by: crasbe <crasbe@gmail.com>
benpicco
left a comment
There was a problem hiding this comment.
Just some minor comments from my side.
| uint32_t limit_mib = (argc > 2) ? strtoul(argv[2], NULL, 10) : 16; | ||
|
|
||
| if (dev == NULL || limit_mib == 0) { | ||
| printf("usage: %s <dev> [size in MiB, default 16, max flash size]\n", argv[0]); |
There was a problem hiding this comment.
| printf("usage: %s <dev> [size in MiB, default 16, max flash size]\n", argv[0]); | |
| printf("usage: %s <dev> [size in MiB, default 16]\n", argv[0]); |
I think max flash size just adds confusion, at least it confused me.
You can't erase more than is there anyway.
| @@ -79,10 +80,27 @@ extern uint32_t spi_flash_get_id(void); | |||
|
|
|||
| static inline esp_err_t spi_flash_erase_range(size_t start_address, size_t size) | |||
There was a problem hiding this comment.
| static inline esp_err_t spi_flash_erase_range(size_t start_address, size_t size) | |
| static esp_err_t spi_flash_erase_range(size_t start_address, size_t size) |
| * is erased block- or sectorwise. */ | ||
| while ((res == ESP_OK) && size) { | ||
| size_t chunk = ((start_address % block_size) == 0) && (size >= block_size) | ||
| ? block_size : sector_size; |
There was a problem hiding this comment.
I assume block_size >= sector_size?
Does it have an advantage to switch between the two? The esp8266 variant only uses sectors, but maybe that's all there is.
Just a short comment as to why this was done that way would be nice.
Contribution description
With the migration to ESP-IDF v5.4 in #21261, the erase function now erases a whole region instead of individual sectors/blocks. Depending on the size of the region, this can take a couple of seconds or more.
Since in that time, the interrupts have to be disabled, the interrupt that retriggers the watchdog is also disabled, causing a watchdog reset.
This PR changes the approach to erase the flash block- or sectorwise, leaving some space in between for interrupts.
Testing procedure
I extended the
tests/drivers/mtd_rawtest to write and erase a large section of the flash, which takes some seconds. This will trigger the watchdog reset reliably.The rest ran on an
esp32-wemos-d1-r32board, Claude ran the tests forseeedstudio-xiao-esp32c3,seeedstudio-xiao-esp32s3,esp32h2-devkitandesp32c6-devkitas well cuz I'm lazy. Can prove traces if wished.Behavior on
masterCherry-pick the commit with the test:
Behavior with this PR
Issues/PRs references
Fixes the new issue raised in #14506.
Also fixes #16130 and reverts #16131.
Declaration of AI-Tools / LLMs usage:
AI-Tools / LLMs that were used are: