Coverage Report

Created: 2025-08-26 06:55

/work/fu-uf2-struct.c
Line
Count
Source (jump to first uncovered line)
1
/* auto-generated, do not modify */
2
#include "config.h"
3
4
#include "fu-uf2-struct.h"
5
#include "fu-byte-array.h"
6
#include "fu-mem-private.h"
7
#include "fu-string.h"
8
9
#ifdef G_LOG_DOMAIN
10
  #undef G_LOG_DOMAIN
11
#endif
12
0
#define G_LOG_DOMAIN "FuStruct"
13
14
static const gchar *
15
fu_uf2_firmware_block_flags_to_string(FuUf2FirmwareBlockFlags val)
16
0
{
17
0
    if (val == FU_UF2_FIRMWARE_BLOCK_FLAG_NONE)
18
0
        return "none";
19
0
    if (val == FU_UF2_FIRMWARE_BLOCK_FLAG_NOFLASH)
20
0
        return "noflash";
21
0
    if (val == FU_UF2_FIRMWARE_BLOCK_FLAG_IS_CONTAINER)
22
0
        return "is-container";
23
0
    if (val == FU_UF2_FIRMWARE_BLOCK_FLAG_HAS_FAMILY)
24
0
        return "has-family";
25
0
    if (val == FU_UF2_FIRMWARE_BLOCK_FLAG_HAS_MD5)
26
0
        return "has-md5";
27
0
    if (val == FU_UF2_FIRMWARE_BLOCK_FLAG_HAS_EXTENSION_TAG)
28
0
        return "has-extension-tag";
29
0
    return NULL;
30
0
}
31
32
const gchar *
33
fu_uf2_firmware_tag_to_string(FuUf2FirmwareTag val)
34
7
{
35
7
    if (val == FU_UF2_FIRMWARE_TAG_VERSION)
36
0
        return "version";
37
7
    if (val == FU_UF2_FIRMWARE_TAG_DESCRIPTION)
38
0
        return "description";
39
7
    if (val == FU_UF2_FIRMWARE_TAG_PAGE_SZ)
40
0
        return "page-sz";
41
7
    if (val == FU_UF2_FIRMWARE_TAG_SHA2)
42
0
        return "sha2";
43
7
    if (val == FU_UF2_FIRMWARE_TAG_DEVICE_ID)
44
0
        return "device-id";
45
7
    return NULL;
46
7
}
47
/* getters */
48
/**
49
 * fu_struct_uf2_extension_get_size: (skip):
50
 **/
51
guint8
52
fu_struct_uf2_extension_get_size(const FuStructUf2Extension *st)
53
10.7k
{
54
10.7k
    g_return_val_if_fail(st != NULL, 0x0);
55
10.7k
    return st->data[0];
56
10.7k
}
57
/**
58
 * fu_struct_uf2_extension_get_tag: (skip):
59
 **/
60
FuUf2FirmwareTag
61
fu_struct_uf2_extension_get_tag(const FuStructUf2Extension *st)
62
10.5k
{
63
10.5k
    g_return_val_if_fail(st != NULL, 0x0);
64
10.5k
    return fu_memread_uint24(st->data + 1, G_LITTLE_ENDIAN);
65
10.5k
}
66
67
/* setters */
68
/**
69
 * fu_struct_uf2_extension_set_size: (skip):
70
 **/
71
void
72
fu_struct_uf2_extension_set_size(FuStructUf2Extension *st, guint8 value)
73
928
{
74
928
    g_return_if_fail(st != NULL);
75
928
    st->data[0] = value;
76
928
}
77
/**
78
 * fu_struct_uf2_extension_set_tag: (skip):
79
 **/
80
void
81
fu_struct_uf2_extension_set_tag(FuStructUf2Extension *st, FuUf2FirmwareTag value)
82
928
{
83
928
    g_return_if_fail(st != NULL);
84
928
    fu_memwrite_uint24(st->data + 1, value, G_LITTLE_ENDIAN);
85
928
}
86
/**
87
 * fu_struct_uf2_extension_new: (skip):
88
 **/
89
FuStructUf2Extension *
90
fu_struct_uf2_extension_new(void)
91
1.41k
{
92
1.41k
    FuStructUf2Extension *st = g_byte_array_sized_new(4);
93
1.41k
    fu_byte_array_set_size(st, 4, 0x0);
94
1.41k
    return st;
95
1.41k
}
96
/**
97
 * fu_struct_uf2_extension_to_string: (skip):
98
 **/
99
static gchar *
100
fu_struct_uf2_extension_to_string(const FuStructUf2Extension *st)
101
0
{
102
0
    g_autoptr(GString) str = g_string_new("FuStructUf2Extension:\n");
103
0
    g_return_val_if_fail(st != NULL, NULL);
104
0
    g_string_append_printf(str, "  size: 0x%x\n",
105
0
                           (guint) fu_struct_uf2_extension_get_size(st));
106
0
    {
107
0
        const gchar *tmp = fu_uf2_firmware_tag_to_string(fu_struct_uf2_extension_get_tag(st));
108
0
        if (tmp != NULL) {
109
0
            g_string_append_printf(str, "  tag: 0x%x [%s]\n", (guint) fu_struct_uf2_extension_get_tag(st), tmp);
110
0
        } else {
111
0
            g_string_append_printf(str, "  tag: 0x%x\n", (guint) fu_struct_uf2_extension_get_tag(st));
112
0
        }
113
0
    }
114
0
    if (str->len > 0)
115
0
        g_string_set_size(str, str->len - 1);
116
0
    return g_string_free(g_steal_pointer(&str), FALSE);
117
0
}
118
static gboolean
119
fu_struct_uf2_extension_validate_internal(FuStructUf2Extension *st, GError **error)
120
10.7k
{
121
10.7k
    g_return_val_if_fail(st != NULL, FALSE);
122
10.7k
    return TRUE;
123
10.7k
}
124
static gboolean
125
fu_struct_uf2_extension_parse_internal(FuStructUf2Extension *st, GError **error)
126
10.7k
{
127
10.7k
    if (g_getenv("FWUPD_VERBOSE") != NULL) {
128
0
        g_autofree gchar *str = fu_struct_uf2_extension_to_string(st);
129
0
        g_debug("%s", str);
130
0
    }
131
10.7k
    if (!fu_struct_uf2_extension_validate_internal(st, error))
132
0
        return FALSE;
133
10.7k
    return TRUE;
134
10.7k
}
135
136
/**
137
 * fu_struct_uf2_extension_parse: (skip):
138
 **/
139
FuStructUf2Extension *
140
fu_struct_uf2_extension_parse(const guint8 *buf, gsize bufsz, gsize offset, GError **error)
141
10.7k
{
142
10.7k
    g_autoptr(GByteArray) st = g_byte_array_new();
143
10.7k
    g_return_val_if_fail(buf != NULL, NULL);
144
10.7k
    g_return_val_if_fail(error == NULL || *error == NULL, NULL);
145
10.7k
    if (!fu_memchk_read(bufsz, offset, 4, error)) {
146
7
        g_prefix_error_literal(error, "invalid struct FuStructUf2Extension: ");
147
7
        return NULL;
148
7
    }
149
10.7k
    g_byte_array_append(st, buf + offset, 4);
150
10.7k
    if (!fu_struct_uf2_extension_parse_internal(st, error))
151
0
        return NULL;
152
10.7k
    return g_steal_pointer(&st);
153
10.7k
}
154
/* getters */
155
/**
156
 * fu_struct_uf2_get_magic0: (skip):
157
 **/
158
static guint32
159
fu_struct_uf2_get_magic0(const FuStructUf2 *st)
160
1.42k
{
161
1.42k
    g_return_val_if_fail(st != NULL, 0x0);
162
1.42k
    return fu_memread_uint32(st->data + 0, G_LITTLE_ENDIAN);
163
1.42k
}
164
/**
165
 * fu_struct_uf2_get_magic1: (skip):
166
 **/
167
static guint32
168
fu_struct_uf2_get_magic1(const FuStructUf2 *st)
169
1.33k
{
170
1.33k
    g_return_val_if_fail(st != NULL, 0x0);
171
1.33k
    return fu_memread_uint32(st->data + 4, G_LITTLE_ENDIAN);
172
1.33k
}
173
/**
174
 * fu_struct_uf2_get_flags: (skip):
175
 **/
176
FuUf2FirmwareBlockFlags
177
fu_struct_uf2_get_flags(const FuStructUf2 *st)
178
1.15k
{
179
1.15k
    g_return_val_if_fail(st != NULL, 0x0);
180
1.15k
    return fu_memread_uint32(st->data + 8, G_LITTLE_ENDIAN);
181
1.15k
}
182
/**
183
 * fu_struct_uf2_get_target_addr: (skip):
184
 **/
185
guint32
186
fu_struct_uf2_get_target_addr(const FuStructUf2 *st)
187
425
{
188
425
    g_return_val_if_fail(st != NULL, 0x0);
189
425
    return fu_memread_uint32(st->data + 12, G_LITTLE_ENDIAN);
190
425
}
191
/**
192
 * fu_struct_uf2_get_payload_size: (skip):
193
 **/
194
guint32
195
fu_struct_uf2_get_payload_size(const FuStructUf2 *st)
196
1.15k
{
197
1.15k
    g_return_val_if_fail(st != NULL, 0x0);
198
1.15k
    return fu_memread_uint32(st->data + 16, G_LITTLE_ENDIAN);
199
1.15k
}
200
/**
201
 * fu_struct_uf2_get_block_no: (skip):
202
 **/
203
guint32
204
fu_struct_uf2_get_block_no(const FuStructUf2 *st)
205
1.17k
{
206
1.17k
    g_return_val_if_fail(st != NULL, 0x0);
207
1.17k
    return fu_memread_uint32(st->data + 20, G_LITTLE_ENDIAN);
208
1.17k
}
209
/**
210
 * fu_struct_uf2_get_num_blocks: (skip):
211
 **/
212
guint32
213
fu_struct_uf2_get_num_blocks(const FuStructUf2 *st)
214
1.06k
{
215
1.06k
    g_return_val_if_fail(st != NULL, 0x0);
216
1.06k
    return fu_memread_uint32(st->data + 24, G_LITTLE_ENDIAN);
217
1.06k
}
218
/**
219
 * fu_struct_uf2_get_family_id: (skip):
220
 **/
221
guint32
222
fu_struct_uf2_get_family_id(const FuStructUf2 *st)
223
794
{
224
794
    g_return_val_if_fail(st != NULL, 0x0);
225
794
    return fu_memread_uint32(st->data + 28, G_LITTLE_ENDIAN);
226
794
}
227
/**
228
 * fu_struct_uf2_get_data: (skip):
229
 **/
230
const guint8 *
231
fu_struct_uf2_get_data(const FuStructUf2 *st, gsize *bufsz)
232
1.06k
{
233
1.06k
    g_return_val_if_fail(st != NULL, NULL);
234
1.06k
    if (bufsz != NULL)
235
0
        *bufsz = 476;
236
1.06k
    return st->data + 32;
237
1.06k
}
238
/**
239
 * fu_struct_uf2_get_magic_end: (skip):
240
 **/
241
static guint32
242
fu_struct_uf2_get_magic_end(const FuStructUf2 *st)
243
1.33k
{
244
1.33k
    g_return_val_if_fail(st != NULL, 0x0);
245
1.33k
    return fu_memread_uint32(st->data + 508, G_LITTLE_ENDIAN);
246
1.33k
}
247
248
/* setters */
249
/**
250
 * fu_struct_uf2_set_magic0: (skip):
251
 **/
252
static void
253
fu_struct_uf2_set_magic0(FuStructUf2 *st, guint32 value)
254
920
{
255
920
    g_return_if_fail(st != NULL);
256
920
    fu_memwrite_uint32(st->data + 0, value, G_LITTLE_ENDIAN);
257
920
}
258
/**
259
 * fu_struct_uf2_set_magic1: (skip):
260
 **/
261
static void
262
fu_struct_uf2_set_magic1(FuStructUf2 *st, guint32 value)
263
920
{
264
920
    g_return_if_fail(st != NULL);
265
920
    fu_memwrite_uint32(st->data + 4, value, G_LITTLE_ENDIAN);
266
920
}
267
/**
268
 * fu_struct_uf2_set_flags: (skip):
269
 **/
270
void
271
fu_struct_uf2_set_flags(FuStructUf2 *st, FuUf2FirmwareBlockFlags value)
272
920
{
273
920
    g_return_if_fail(st != NULL);
274
920
    fu_memwrite_uint32(st->data + 8, value, G_LITTLE_ENDIAN);
275
920
}
276
/**
277
 * fu_struct_uf2_set_target_addr: (skip):
278
 **/
279
void
280
fu_struct_uf2_set_target_addr(FuStructUf2 *st, guint32 value)
281
920
{
282
920
    g_return_if_fail(st != NULL);
283
920
    fu_memwrite_uint32(st->data + 12, value, G_LITTLE_ENDIAN);
284
920
}
285
/**
286
 * fu_struct_uf2_set_payload_size: (skip):
287
 **/
288
void
289
fu_struct_uf2_set_payload_size(FuStructUf2 *st, guint32 value)
290
920
{
291
920
    g_return_if_fail(st != NULL);
292
920
    fu_memwrite_uint32(st->data + 16, value, G_LITTLE_ENDIAN);
293
920
}
294
/**
295
 * fu_struct_uf2_set_block_no: (skip):
296
 **/
297
void
298
fu_struct_uf2_set_block_no(FuStructUf2 *st, guint32 value)
299
920
{
300
920
    g_return_if_fail(st != NULL);
301
920
    fu_memwrite_uint32(st->data + 20, value, G_LITTLE_ENDIAN);
302
920
}
303
/**
304
 * fu_struct_uf2_set_num_blocks: (skip):
305
 **/
306
void
307
fu_struct_uf2_set_num_blocks(FuStructUf2 *st, guint32 value)
308
920
{
309
920
    g_return_if_fail(st != NULL);
310
920
    fu_memwrite_uint32(st->data + 24, value, G_LITTLE_ENDIAN);
311
920
}
312
/**
313
 * fu_struct_uf2_set_family_id: (skip):
314
 **/
315
void
316
fu_struct_uf2_set_family_id(FuStructUf2 *st, guint32 value)
317
920
{
318
920
    g_return_if_fail(st != NULL);
319
920
    fu_memwrite_uint32(st->data + 28, value, G_LITTLE_ENDIAN);
320
920
}
321
/**
322
 * fu_struct_uf2_set_data: (skip):
323
 **/
324
gboolean
325
fu_struct_uf2_set_data(FuStructUf2 *st, const guint8 *buf, gsize bufsz, GError **error)
326
920
{
327
920
    g_return_val_if_fail(st != NULL, FALSE);
328
920
    g_return_val_if_fail(buf != NULL, FALSE);
329
920
    g_return_val_if_fail(error == NULL || *error == NULL, FALSE);
330
920
    return fu_memcpy_safe(st->data, st->len, 32, buf, bufsz, 0x0, bufsz, error);
331
920
}
332
/**
333
 * fu_struct_uf2_set_magic_end: (skip):
334
 **/
335
static void
336
fu_struct_uf2_set_magic_end(FuStructUf2 *st, guint32 value)
337
920
{
338
920
    g_return_if_fail(st != NULL);
339
920
    fu_memwrite_uint32(st->data + 508, value, G_LITTLE_ENDIAN);
340
920
}
341
/**
342
 * fu_struct_uf2_new: (skip):
343
 **/
344
FuStructUf2 *
345
fu_struct_uf2_new(void)
346
920
{
347
920
    FuStructUf2 *st = g_byte_array_sized_new(512);
348
920
    fu_byte_array_set_size(st, 512, 0x0);
349
920
    fu_struct_uf2_set_magic0(st, 0x0A324655);
350
920
    fu_struct_uf2_set_magic1(st, 0x9E5D5157);
351
920
    fu_struct_uf2_set_magic_end(st, 0x0AB16F30);
352
920
    return st;
353
920
}
354
/**
355
 * fu_struct_uf2_to_string: (skip):
356
 **/
357
static gchar *
358
fu_struct_uf2_to_string(const FuStructUf2 *st)
359
0
{
360
0
    g_autoptr(GString) str = g_string_new("FuStructUf2:\n");
361
0
    g_return_val_if_fail(st != NULL, NULL);
362
0
    {
363
0
        const gchar *tmp = fu_uf2_firmware_block_flags_to_string(fu_struct_uf2_get_flags(st));
364
0
        if (tmp != NULL) {
365
0
            g_string_append_printf(str, "  flags: 0x%x [%s]\n", (guint) fu_struct_uf2_get_flags(st), tmp);
366
0
        } else {
367
0
            g_string_append_printf(str, "  flags: 0x%x\n", (guint) fu_struct_uf2_get_flags(st));
368
0
        }
369
0
    }
370
0
    g_string_append_printf(str, "  target_addr: 0x%x\n",
371
0
                           (guint) fu_struct_uf2_get_target_addr(st));
372
0
    g_string_append_printf(str, "  payload_size: 0x%x\n",
373
0
                           (guint) fu_struct_uf2_get_payload_size(st));
374
0
    g_string_append_printf(str, "  block_no: 0x%x\n",
375
0
                           (guint) fu_struct_uf2_get_block_no(st));
376
0
    g_string_append_printf(str, "  num_blocks: 0x%x\n",
377
0
                           (guint) fu_struct_uf2_get_num_blocks(st));
378
0
    g_string_append_printf(str, "  family_id: 0x%x\n",
379
0
                           (guint) fu_struct_uf2_get_family_id(st));
380
0
    {
381
0
        gsize bufsz = 0;
382
0
        const guint8 *buf = fu_struct_uf2_get_data(st, &bufsz);
383
0
        g_autoptr(GString) tmp = g_string_new(NULL);
384
0
        for (gsize i = 0; i < bufsz; i++)
385
0
            g_string_append_printf(tmp, "%02X", buf[i]);
386
0
        g_string_append_printf(str, "  data: 0x%s\n", tmp->str);
387
0
    }
388
0
    if (str->len > 0)
389
0
        g_string_set_size(str, str->len - 1);
390
0
    return g_string_free(g_steal_pointer(&str), FALSE);
391
0
}
392
static gboolean
393
fu_struct_uf2_validate_internal(FuStructUf2 *st, GError **error)
394
1.36k
{
395
1.36k
    g_return_val_if_fail(st != NULL, FALSE);
396
1.36k
    if (fu_struct_uf2_get_magic0(st) != 0x0A324655) {
397
68
        g_set_error(error,
398
68
                    FWUPD_ERROR,
399
68
                    FWUPD_ERROR_INVALID_DATA,
400
68
                    "constant FuStructUf2.magic0 was not valid, "
401
68
                    "expected 0x%x and got 0x%x",
402
68
                    (guint) 0x0A324655,
403
68
                    (guint) fu_struct_uf2_get_magic0(st));
404
68
        return FALSE;
405
68
    }
406
1.29k
    if (fu_struct_uf2_get_magic1(st) != 0x9E5D5157) {
407
47
        g_set_error(error,
408
47
                    FWUPD_ERROR,
409
47
                    FWUPD_ERROR_INVALID_DATA,
410
47
                    "constant FuStructUf2.magic1 was not valid, "
411
47
                    "expected 0x%x and got 0x%x",
412
47
                    (guint) 0x9E5D5157,
413
47
                    (guint) fu_struct_uf2_get_magic1(st));
414
47
        return FALSE;
415
47
    }
416
1.24k
    if (fu_struct_uf2_get_magic_end(st) != 0x0AB16F30) {
417
89
        g_set_error(error,
418
89
                    FWUPD_ERROR,
419
89
                    FWUPD_ERROR_INVALID_DATA,
420
89
                    "constant FuStructUf2.magic_end was not valid, "
421
89
                    "expected 0x%x and got 0x%x",
422
89
                    (guint) 0x0AB16F30,
423
89
                    (guint) fu_struct_uf2_get_magic_end(st));
424
89
        return FALSE;
425
89
    }
426
1.15k
    return TRUE;
427
1.24k
}
428
static gboolean
429
fu_struct_uf2_parse_internal(FuStructUf2 *st, GError **error)
430
1.36k
{
431
1.36k
    if (g_getenv("FWUPD_VERBOSE") != NULL) {
432
0
        g_autofree gchar *str = fu_struct_uf2_to_string(st);
433
0
        g_debug("%s", str);
434
0
    }
435
1.36k
    if (!fu_struct_uf2_validate_internal(st, error))
436
204
        return FALSE;
437
1.15k
    return TRUE;
438
1.36k
}
439
440
/**
441
 * fu_struct_uf2_parse: (skip):
442
 **/
443
FuStructUf2 *
444
fu_struct_uf2_parse(const guint8 *buf, gsize bufsz, gsize offset, GError **error)
445
1.40k
{
446
1.40k
    g_autoptr(GByteArray) st = g_byte_array_new();
447
1.40k
    g_return_val_if_fail(buf != NULL, NULL);
448
1.40k
    g_return_val_if_fail(error == NULL || *error == NULL, NULL);
449
1.40k
    if (!fu_memchk_read(bufsz, offset, 512, error)) {
450
40
        g_prefix_error_literal(error, "invalid struct FuStructUf2: ");
451
40
        return NULL;
452
40
    }
453
1.36k
    g_byte_array_append(st, buf + offset, 512);
454
1.36k
    if (!fu_struct_uf2_parse_internal(st, error))
455
204
        return NULL;
456
1.15k
    return g_steal_pointer(&st);
457
1.36k
}