Skip to content

Commit 8b87449

Browse files
committed
Changed partition table reads to be split into fixed-length field sections and variable-length field sections
1 parent 1015067 commit 8b87449

File tree

1 file changed

+62
-58
lines changed

1 file changed

+62
-58
lines changed

flash/partition_info/partition_info.c

Lines changed: 62 additions & 58 deletions
Original file line numberDiff line numberDiff line change
@@ -17,21 +17,21 @@
1717
#define PARTITION_LOCATION_AND_FLAGS_SIZE 2
1818
#define PARTITION_ID_SIZE 2
1919
#define PARTITION_NAME_MAX 127
20-
#define PARTITION_SIZE_MAX (PARTITION_LOCATION_AND_FLAGS_SIZE + PARTITION_ID_SIZE + PARTITION_NAME_MAX + 1)
20+
#define PARTITION_TABLE_FIXED_INFO_SIZE (4 + PARTITION_TABLE_MAX_PARTITIONS * (PARTITION_LOCATION_AND_FLAGS_SIZE + PARTITION_ID_SIZE))
2121

2222
/*
2323
* Stores partition table information and data read status
2424
*/
2525
typedef struct {
26-
uint32_t workarea[4 + PARTITION_TABLE_MAX_PARTITIONS * PARTITION_SIZE_MAX];
27-
size_t table_size;
26+
uint32_t table[PARTITION_TABLE_FIXED_INFO_SIZE];
2827
uint32_t fields;
2928
int partition_count;
3029
uint32_t unpartitioned_space_first_sector;
3130
uint32_t unpartitioned_space_last_sector;
3231
uint32_t permission;
3332
int current_partition;
3433
size_t idx;
34+
int status;
3535
} pico_partition_table_t;
3636

3737
/*
@@ -40,7 +40,7 @@ typedef struct {
4040
typedef struct {
4141
uint32_t first_sector;
4242
uint32_t last_sector;
43-
uint32_t permission;
43+
uint32_t flags_and_permissions;
4444
uint64_t partition_id;
4545
char name[PARTITION_NAME_MAX + 1]; // name length is indicated by 7 bits
4646
} pico_partition_t;
@@ -51,71 +51,74 @@ typedef struct {
5151
*
5252
* See the RP2350 datasheet 5.1.2, 5.4.8.16 for flags and structures that can be specified.
5353
*/
54-
int pico_partitions_open(pico_partition_table_t *pt, int flags) {
55-
int rc = rom_get_partition_table_info(pt->workarea, sizeof(pt->workarea), flags);
54+
int pico_partitions_open(pico_partition_table_t *pt) {
55+
// Reads a fixed size fields
56+
int rc = rom_get_partition_table_info(pt->table, sizeof(pt->table),
57+
(PT_INFO_PT_INFO |
58+
PT_INFO_PARTITION_LOCATION_AND_FLAGS |
59+
PT_INFO_PARTITION_ID));
5660
if (rc < 0) {
61+
pt->status = rc;
5762
return rc;
5863
}
59-
pt->table_size = rc * WORD_SIZE; // word to bytes
6064

6165
size_t pos = 0;
62-
pt->fields = pt->workarea[pos++];
63-
pt->partition_count = pt->workarea[pos++] & 0x000000FF;
64-
uint32_t location = pt->workarea[pos++];
66+
pt->fields = pt->table[pos++];
67+
pt->partition_count = pt->table[pos++] & 0x000000FF;
68+
uint32_t location = pt->table[pos++];
6569
pt->unpartitioned_space_first_sector = PART_LOC_FIRST(location);
6670
pt->unpartitioned_space_last_sector = PART_LOC_LAST(location);
67-
pt->permission = pt->workarea[pos++];
68-
pt->idx = pos; // point to the beggining of eath partition
71+
pt->permission = pt->table[pos++];
6972
pt->current_partition = 0;
73+
pt->idx = pos;
74+
pt->status = 0;
7075

7176
return 0;
7277
}
7378

7479
/*
75-
* Parse a partition table and extract information
80+
* Extract each partition information
7681
*/
77-
size_t pico_partitions_parse(pico_partition_table_t *pt, pico_partition_t *p) {
78-
size_t idx = pt->idx;
79-
if (pt->fields & PT_INFO_PARTITION_LOCATION_AND_FLAGS) {
80-
uint32_t location = pt->workarea[idx++];
81-
p->first_sector = PART_LOC_FIRST(location);
82-
p->last_sector = PART_LOC_LAST(location);
83-
p->permission = pt->workarea[idx++];
84-
} else {
85-
p->first_sector = 0;
86-
p->last_sector = 0;
87-
p->permission = 0;
82+
bool pico_partitions_next(pico_partition_table_t *pt, pico_partition_t *p) {
83+
if (pt->current_partition >= pt->partition_count) {
84+
return false;
8885
}
8986

90-
if (pt->fields & PT_INFO_PARTITION_ID) {
91-
uint32_t id_low = pt->workarea[idx++];
92-
uint32_t id_high = pt->workarea[idx++];
87+
size_t idx = pt->idx;
88+
uint32_t location = pt->table[idx++];
89+
p->first_sector = PART_LOC_FIRST(location);
90+
p->last_sector = PART_LOC_LAST(location);
91+
p->flags_and_permissions = pt->table[idx++];
92+
93+
if (p->flags_and_permissions & PICOBIN_PARTITION_FLAGS_HAS_ID_BITS) {
94+
uint32_t id_low = pt->table[idx++];
95+
uint32_t id_high = pt->table[idx++];
9396
p->partition_id = ((uint64_t)id_high << 32) | id_low;
9497
} else {
9598
p->partition_id = 0;
9699
}
97-
98-
if (pt->fields & PT_INFO_PARTITION_NAME) {
99-
uint8_t *name_field = (uint8_t *)&pt->workarea[idx];
100-
uint8_t name_length = name_field[0];
101-
memcpy(p->name, name_field + 1, name_length);
100+
pt->idx = idx;
101+
102+
if (p->flags_and_permissions & PICOBIN_PARTITION_FLAGS_HAS_NAME_BITS) {
103+
// Read variable length fields
104+
uint32_t name_buf[(PARTITION_NAME_MAX + 1) / WORD_SIZE] = {0};
105+
int rc = rom_get_partition_table_info(name_buf, sizeof(name_buf),
106+
(pt->current_partition << 24 |
107+
PT_INFO_SINGLE_PARTITION |
108+
PT_INFO_PARTITION_NAME));
109+
if (rc < 0) {
110+
pt->status = rc;
111+
return false;
112+
}
113+
uint32_t __attribute__((unused)) fields = name_buf[0];
114+
uint8_t *name_buf_u8 = (uint8_t *)&name_buf[1];
115+
uint8_t name_length = *name_buf_u8++;
116+
memcpy(p->name, name_buf_u8, name_length);
102117
p->name[name_length] = '\0';
103-
size_t total_name_field_length = 1 + name_length;
104-
idx += WORD_PADDED_BYTES(total_name_field_length) / WORD_SIZE;
105118
} else {
106119
p->name[0] = '\0';
107120
}
108-
return idx;
109-
}
110121

111-
/*
112-
* Extract one partition information
113-
*/
114-
bool pico_partitions_next(pico_partition_table_t *pt, pico_partition_t *p) {
115-
if (pt->current_partition >= pt->partition_count) {
116-
return false;
117-
}
118-
pt->idx = pico_partitions_parse(pt, p);
119122
pt->current_partition++;
120123
return true;
121124
}
@@ -124,8 +127,7 @@ int main() {
124127
stdio_init_all();
125128

126129
pico_partition_table_t pt;
127-
pico_partitions_open(&pt, PT_INFO_PT_INFO | PT_INFO_PARTITION_LOCATION_AND_FLAGS |
128-
PT_INFO_PARTITION_ID | PT_INFO_PARTITION_NAME);
130+
pico_partitions_open(&pt);
129131
printf("un-partitioned_space: S(%s%s) NSBOOT(%s%s) NS(%s%s)\n",
130132
(pt.permission & PICOBIN_PARTITION_PERMISSION_S_R_BITS ? "r" : ""),
131133
(pt.permission & PICOBIN_PARTITION_PERMISSION_S_W_BITS ? "w" : ""),
@@ -137,24 +139,26 @@ int main() {
137139
pico_partition_t p;
138140
while (pico_partitions_next(&pt, &p)) {
139141
printf("%3d:", pt.current_partition - 1);
140-
if (pt.fields & PT_INFO_PARTITION_LOCATION_AND_FLAGS) {
141-
printf(" %08x->%08x S(%s%s) NSBOOT(%s%s) NS(%s%s)",
142-
p.first_sector * 4096, p.last_sector * 4096,
143-
(p.permission & PICOBIN_PARTITION_PERMISSION_S_R_BITS ? "r" : ""),
144-
(p.permission & PICOBIN_PARTITION_PERMISSION_S_W_BITS ? "w" : ""),
145-
(p.permission & PICOBIN_PARTITION_PERMISSION_NSBOOT_R_BITS ? "r" : ""),
146-
(p.permission & PICOBIN_PARTITION_PERMISSION_NSBOOT_W_BITS ? "w" : ""),
147-
(p.permission & PICOBIN_PARTITION_PERMISSION_NS_R_BITS ? "r" : ""),
148-
(p.permission & PICOBIN_PARTITION_PERMISSION_NS_W_BITS ? "w" : ""));
149-
}
150-
if (pt.fields & PT_INFO_PARTITION_ID) {
142+
printf(" %08x->%08x S(%s%s) NSBOOT(%s%s) NS(%s%s)",
143+
p.first_sector * 4096, p.last_sector * 4096,
144+
(p.flags_and_permissions & PICOBIN_PARTITION_PERMISSION_S_R_BITS ? "r" : ""),
145+
(p.flags_and_permissions & PICOBIN_PARTITION_PERMISSION_S_W_BITS ? "w" : ""),
146+
(p.flags_and_permissions & PICOBIN_PARTITION_PERMISSION_NSBOOT_R_BITS ? "r" : ""),
147+
(p.flags_and_permissions & PICOBIN_PARTITION_PERMISSION_NSBOOT_W_BITS ? "w" : ""),
148+
(p.flags_and_permissions & PICOBIN_PARTITION_PERMISSION_NS_R_BITS ? "r" : ""),
149+
(p.flags_and_permissions & PICOBIN_PARTITION_PERMISSION_NS_W_BITS ? "w" : ""));
150+
if (p.flags_and_permissions & PICOBIN_PARTITION_FLAGS_HAS_ID_BITS) {
151151
printf(", id=%016llx", p.partition_id);
152152
}
153-
if (pt.fields & PT_INFO_PARTITION_NAME) {
153+
if (p.flags_and_permissions & PICOBIN_PARTITION_FLAGS_HAS_NAME_BITS) {
154154
printf(", \"%s\"", p.name);
155155
}
156156
printf("\n");
157157
}
158+
if (pt.status != 0) {
159+
fprintf(stderr, "rom_get_partition_table_info rc=%d\n", pt.status);
160+
return 1;
161+
}
158162

159163
return 0;
160164
}

0 commit comments

Comments
 (0)