[PATCH v1 2/3] fdt_support: validate dma-ranges length in fdt_get_dma_range
Aristo Chen
aristo.chen at canonical.com
Mon May 25 15:26:24 CEST 2026
fdt_get_dma_range() fetches the dma-ranges property with fdt_getprop()
and checks only that the length is non-zero before reading one full
entry from it. The entry size depends on na, pna and ns cells returned
by count_cells, which come from the parent buses in the devicetree.
A dma-ranges property shorter than (na + pna + ns) * sizeof(u32) bytes
causes fdt_read_number() and fdt_translate_dma_address() to read past
the end of the property within the FDT blob, an out-of-bounds read of
attacker-influenced data when the OS devicetree is not signature
verified.
Reject the property when its length is smaller than one full entry and
return -EINVAL, matching the existing failure paths in this function.
Signed-off-by: Aristo Chen <aristo.chen at canonical.com>
---
boot/fdt_support.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/boot/fdt_support.c b/boot/fdt_support.c
index 3e9445603ff..c4c2a5d02f6 100644
--- a/boot/fdt_support.c
+++ b/boot/fdt_support.c
@@ -1633,6 +1633,13 @@ int fdt_get_dma_range(const void *blob, int node, phys_addr_t *cpu,
goto out;
}
+ if (len < (int)((na + pna + ns) * sizeof(*ranges))) {
+ printf("%s: dma-ranges too short for %s\n", __func__,
+ fdt_get_name(blob, node, NULL));
+ ret = -EINVAL;
+ goto out;
+ }
+
*bus = fdt_read_number(ranges, na);
*cpu = fdt_translate_dma_address(blob, node, ranges + na);
*size = fdt_read_number(ranges + na + pna, ns);
--
2.43.0
More information about the U-Boot
mailing list