Pad all but last sector in flash binary to write whole of sector (#800)
This commit is contained in:
parent
81bdcb6681
commit
0d2591e1f1
@ -6,6 +6,7 @@
|
|||||||
|
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
#include <map>
|
#include <map>
|
||||||
|
#include <set>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <cstdarg>
|
#include <cstdarg>
|
||||||
@ -21,6 +22,8 @@ typedef unsigned int uint;
|
|||||||
#define ERROR_READ_FAILED -4
|
#define ERROR_READ_FAILED -4
|
||||||
#define ERROR_WRITE_FAILED -5
|
#define ERROR_WRITE_FAILED -5
|
||||||
|
|
||||||
|
#define FLASH_SECTOR_ERASE_SIZE 4096u
|
||||||
|
|
||||||
static char error_msg[512];
|
static char error_msg[512];
|
||||||
static bool verbose;
|
static bool verbose;
|
||||||
|
|
||||||
@ -295,6 +298,28 @@ int elf2uf2(FILE *in, FILE *out) {
|
|||||||
MAIN_RAM_START, sp);
|
MAIN_RAM_START, sp);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
} else {
|
||||||
|
// Fill in empty dummy uf2 pages to align the binary to flash sectors (except for the last sector which we don't
|
||||||
|
// need to pad, and choose not to to avoid making all SDK UF2s bigger)
|
||||||
|
// That workaround is required because the bootrom uses the block number for erase sector calculations:
|
||||||
|
// https://github.com/raspberrypi/pico-bootrom/blob/c09c7f08550e8a36fc38dc74f8873b9576de99eb/bootrom/virtual_disk.c#L205
|
||||||
|
|
||||||
|
std::set<uint32_t> touched_sectors;
|
||||||
|
for (auto& page_entry : pages) {
|
||||||
|
uint32_t sector = page_entry.first / FLASH_SECTOR_ERASE_SIZE;
|
||||||
|
touched_sectors.insert(sector);
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32_t last_page = pages.rbegin()->first;
|
||||||
|
for (uint32_t sector : touched_sectors) {
|
||||||
|
for (uint32_t page = sector * FLASH_SECTOR_ERASE_SIZE; page < (sector + 1) * FLASH_SECTOR_ERASE_SIZE; page += PAGE_SIZE) {
|
||||||
|
if (page < last_page) {
|
||||||
|
// Create a dummy page, if it does not exist yet. note that all present pages are first
|
||||||
|
// zeroed before they are filled with any contents, so a dummy page will be all zeros.
|
||||||
|
auto &dummy = pages[page];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
uf2_block block;
|
uf2_block block;
|
||||||
block.magic_start0 = UF2_MAGIC_START0;
|
block.magic_start0 = UF2_MAGIC_START0;
|
||||||
@ -308,7 +333,8 @@ int elf2uf2(FILE *in, FILE *out) {
|
|||||||
block.target_addr = page_entry.first;
|
block.target_addr = page_entry.first;
|
||||||
block.block_no = page_num++;
|
block.block_no = page_num++;
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
printf("Page %d / %d %08x\n", block.block_no, block.num_blocks, block.target_addr);
|
printf("Page %d / %d %08x%s\n", block.block_no, block.num_blocks, block.target_addr,
|
||||||
|
page_entry.second.empty() ? " (padding)": "");
|
||||||
}
|
}
|
||||||
memset(block.data, 0, sizeof(block.data));
|
memset(block.data, 0, sizeof(block.data));
|
||||||
rc = realize_page(in, page_entry.second, block.data, sizeof(block.data));
|
rc = realize_page(in, page_entry.second, block.data, sizeof(block.data));
|
||||||
|
Loading…
Reference in New Issue
Block a user