Skip to content

Commit 5f20062

Browse files
committed
Peer review fixes
1 parent c06ce26 commit 5f20062

3 files changed

Lines changed: 65 additions & 18 deletions

File tree

docs/Targets.md

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1257,7 +1257,7 @@ MACHINE=mpfs-video-kit bitbake mchp-base-image-sdk
12571257
12581258
Build images are output to: `./tmp-glibc/deploy/images/mpfs-video-kit/`
12591259
1260-
#### Custom FIT image, signing and coping to SDCard
1260+
#### Custom FIT image, signing and copying to SDCard
12611261
12621262
wolfBoot can either decompress a gzipped kernel at boot time (`GZIP=1`,
12631263
the default for `polarfire_mpfs250.config` and `polarfire_mpfs250_qspi.config`)
@@ -3455,6 +3455,13 @@ and the `bl31`/`fsbl` versus `bl31`/`plm` boot chain. Set `GZIP=0` in
34553455
`.config` if you want to keep using an uncompressed `Image` plus
34563456
`compression = "none"`.
34573457

3458+
The decompressed-output bound for any single FIT subimage defaults to
3459+
`WOLFBOOT_FIT_MAX_DECOMP = 256 MB`. Override per target via
3460+
`CFLAGS+=-DWOLFBOOT_FIT_MAX_DECOMP=...` if a kernel/ramdisk legitimately
3461+
expands beyond that. The outer wolfBoot signature still authenticates the
3462+
entire FIT; this cap is defense-in-depth against a malformed-but-signed
3463+
stream.
3464+
34583465
**FIT ramdisk (initramfs)**
34593466

34603467
When PetaLinux is built with `INITRAMFS_IMAGE_BUNDLE = "0"` the rootfs cpio
@@ -3497,6 +3504,7 @@ images {
34973504
data = /incbin/("rootfs.cpio.gz");
34983505
type = "ramdisk";
34993506
compression = "gzip"; /* or "none" */
3507+
load = <0x40000000>; /* required for decompression / relocation */
35003508
hash-1 { algo = "sha256"; };
35013509
};
35023510
};

src/fdt.c

Lines changed: 36 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,16 @@
4040
#endif
4141
#endif /* WOLFBOOT_GZIP */
4242

43+
/* Default upper bound on a single FIT subimage's decompressed size.
44+
* The outer wolfBoot signature already authenticates the FIT, but a
45+
* concrete cap defends against a malformed-but-signed FIT scribbling
46+
* across unrelated memory. Override per target via:
47+
* CFLAGS+=-DWOLFBOOT_FIT_MAX_DECOMP=...
48+
*/
49+
#ifndef WOLFBOOT_FIT_MAX_DECOMP
50+
#define WOLFBOOT_FIT_MAX_DECOMP (256U * 1024U * 1024U)
51+
#endif
52+
4353
uint32_t cpu_to_fdt32(uint32_t x)
4454
{
4555
#ifdef BIG_ENDIAN_ORDER
@@ -911,6 +921,9 @@ static int fit_verify_hash(const void *fdt, int img_off,
911921
int hash_off, len = 0;
912922
const char *algo = NULL;
913923
const uint8_t *value = NULL;
924+
#if defined(WOLFBOOT_HASH_SHA256) || defined(WOLFBOOT_HASH_SHA384)
925+
int did_init = 0;
926+
#endif
914927
#ifdef WOLFBOOT_HASH_SHA256
915928
wc_Sha256 sha256_ctx;
916929
uint8_t sha256_digest[WC_SHA256_DIGEST_SIZE];
@@ -950,14 +963,20 @@ static int fit_verify_hash(const void *fdt, int img_off,
950963
}
951964
if (ret == 0) {
952965
ret = wc_InitSha256(&sha256_ctx);
966+
if (ret == 0) {
967+
did_init = 1;
968+
}
953969
}
954970
if (ret == 0) {
955971
ret = wc_Sha256Update(&sha256_ctx, data, (word32)data_len);
956972
}
957973
if (ret == 0) {
958974
ret = wc_Sha256Final(&sha256_ctx, sha256_digest);
959975
}
960-
wc_Sha256Free(&sha256_ctx);
976+
if (did_init) {
977+
wc_Sha256Free(&sha256_ctx);
978+
did_init = 0;
979+
}
961980
if (ret != 0) {
962981
wolfBoot_printf("FIT hash-1 (sha256): wc_Sha256 failed rc=%d\n",
963982
ret);
@@ -982,14 +1001,20 @@ static int fit_verify_hash(const void *fdt, int img_off,
9821001
}
9831002
if (ret == 0) {
9841003
ret = wc_InitSha384(&sha384_ctx);
1004+
if (ret == 0) {
1005+
did_init = 1;
1006+
}
9851007
}
9861008
if (ret == 0) {
9871009
ret = wc_Sha384Update(&sha384_ctx, data, (word32)data_len);
9881010
}
9891011
if (ret == 0) {
9901012
ret = wc_Sha384Final(&sha384_ctx, sha384_digest);
9911013
}
992-
wc_Sha384Free(&sha384_ctx);
1014+
if (did_init) {
1015+
wc_Sha384Free(&sha384_ctx);
1016+
did_init = 0;
1017+
}
9931018
if (ret != 0) {
9941019
wolfBoot_printf("FIT hash-1 (sha384): wc_Sha384 failed rc=%d\n",
9951020
ret);
@@ -1060,6 +1085,14 @@ void* fit_load_image_ex(void* fdt, const char* image, int* lenp,
10601085
return NULL;
10611086
#endif
10621087
}
1088+
else if (comp != NULL && complen > 0
1089+
&& strcmp(comp, "none") != 0) {
1090+
/* Unknown compression scheme; fail closed rather than
1091+
* silently memcpy compressed bytes as raw. */
1092+
wolfBoot_printf("FIT: subimage '%s' has unsupported "
1093+
"compression=\"%s\"\n", image, comp);
1094+
return NULL;
1095+
}
10631096
else {
10641097
wolfBoot_printf("Loading Image %s: %p -> %p (%d bytes)\n",
10651098
image, data, load, len);
@@ -1093,7 +1126,7 @@ void* fit_load_image_ex(void* fdt, const char* image, int* lenp,
10931126

10941127
void* fit_load_image(void* fdt, const char* image, int* lenp)
10951128
{
1096-
return fit_load_image_ex(fdt, image, lenp, 0xFFFFFFFFU);
1129+
return fit_load_image_ex(fdt, image, lenp, WOLFBOOT_FIT_MAX_DECOMP);
10971130
}
10981131

10991132
#endif /* (MMU || WOLFBOOT_FDT) && !BUILD_LOADER_STAGE1 */

tools/unit-tests/unit-gzip.c

Lines changed: 20 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@
3535
#include "gzip.h"
3636

3737
/* Pull in the implementation under test directly */
38-
#include "gzip.c"
38+
#include "../../src/gzip.c"
3939

4040
/* ------------------------------------------------------------------------- */
4141
/* Helpers: gzip(1) on the host produces our test fixtures */
@@ -45,41 +45,47 @@ static uint8_t *gz_compress_buf(const uint8_t *in, size_t in_len, size_t *out_le
4545
{
4646
char in_path[64], out_path[64];
4747
char cmd[256];
48-
FILE *f;
48+
FILE *f = NULL;
4949
long n;
50-
uint8_t *buf;
50+
uint8_t *buf = NULL;
5151

5252
snprintf(in_path, sizeof(in_path), "/tmp/wb-gz-in-%d.bin", getpid());
5353
snprintf(out_path, sizeof(out_path), "/tmp/wb-gz-out-%d.gz", getpid());
5454

5555
f = fopen(in_path, "wb");
56-
if (f == NULL) return NULL;
56+
if (f == NULL) goto cleanup;
5757
if (in_len > 0) {
5858
if (fwrite(in, 1, in_len, f) != in_len) {
5959
fclose(f);
60-
return NULL;
60+
f = NULL;
61+
goto cleanup;
6162
}
6263
}
6364
fclose(f);
65+
f = NULL;
6466

6567
snprintf(cmd, sizeof(cmd), "gzip -nc %s > %s", in_path, out_path);
66-
if (system(cmd) != 0) return NULL;
68+
if (system(cmd) != 0) goto cleanup;
6769

6870
f = fopen(out_path, "rb");
69-
if (f == NULL) return NULL;
70-
fseek(f, 0, SEEK_END);
71+
if (f == NULL) goto cleanup;
72+
if (fseek(f, 0, SEEK_END) != 0) goto cleanup;
7173
n = ftell(f);
72-
fseek(f, 0, SEEK_SET);
74+
if (n < 0) goto cleanup;
75+
if (fseek(f, 0, SEEK_SET) != 0) goto cleanup;
7376
buf = (uint8_t*)malloc((size_t)n);
74-
if (buf == NULL) { fclose(f); return NULL; }
77+
if (buf == NULL) goto cleanup;
7578
if (fread(buf, 1, (size_t)n, f) != (size_t)n) {
76-
free(buf); fclose(f);
77-
return NULL;
79+
free(buf);
80+
buf = NULL;
81+
goto cleanup;
7882
}
79-
fclose(f);
83+
*out_len = (size_t)n;
84+
85+
cleanup:
86+
if (f != NULL) fclose(f);
8087
unlink(in_path);
8188
unlink(out_path);
82-
*out_len = (size_t)n;
8389
return buf;
8490
}
8591

0 commit comments

Comments
 (0)