aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavid Gibson <david@gibson.dropbear.id.au>2021-06-08 15:17:11 +1000
committerDavid Gibson <david@gibson.dropbear.id.au>2021-06-08 15:17:11 +1000
commit4c2ef8f4d14ca411b41b9c6891028d58d2079bf7 (patch)
tree620618e13ceda692202d9ae02ddfae0488a68a93
parente59ca36fb70e32f8b4850135ab94fdf44cd22557 (diff)
downloaddtc-4c2ef8f4d14ca411b41b9c6891028d58d2079bf7.tar.gz
checks: Introduce is_multiple_of()
In a number of places we check if one number is a multiple of another, using a modulus. In some of those cases the divisor is potentially zero, which needs special handling or we could trigger a divide by zero. Introduce an is_multiple_of() helper to safely handle this case, and use it in a bunch of places. This should close Coverity issue 1501687, maybe others as well. Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
-rw-r--r--checks.c18
1 files changed, 13 insertions, 5 deletions
diff --git a/checks.c b/checks.c
index 7ff044d..e6c7c3e 100644
--- a/checks.c
+++ b/checks.c
@@ -143,6 +143,14 @@ static void check_nodes_props(struct check *c, struct dt_info *dti, struct node
check_nodes_props(c, dti, child);
}
+static bool is_multiple_of(int multiple, int divisor)
+{
+ if (divisor == 0)
+ return multiple == 0;
+ else
+ return (multiple % divisor) == 0;
+}
+
static bool run_check(struct check *c, struct dt_info *dti)
{
struct node *dt = dti->dt;
@@ -766,7 +774,7 @@ static void check_reg_format(struct check *c, struct dt_info *dti,
size_cells = node_size_cells(node->parent);
entrylen = (addr_cells + size_cells) * sizeof(cell_t);
- if (!entrylen || (prop->val.len % entrylen) != 0)
+ if (!is_multiple_of(prop->val.len, entrylen))
FAIL_PROP(c, dti, node, prop, "property has invalid length (%d bytes) "
"(#address-cells == %d, #size-cells == %d)",
prop->val.len, addr_cells, size_cells);
@@ -807,7 +815,7 @@ static void check_ranges_format(struct check *c, struct dt_info *dti,
"#size-cells (%d) differs from %s (%d)",
ranges, c_size_cells, node->parent->fullpath,
p_size_cells);
- } else if ((prop->val.len % entrylen) != 0) {
+ } else if (!is_multiple_of(prop->val.len, entrylen)) {
FAIL_PROP(c, dti, node, prop, "\"%s\" property has invalid length (%d bytes) "
"(parent #address-cells == %d, child #address-cells == %d, "
"#size-cells == %d)", ranges, prop->val.len,
@@ -1382,7 +1390,7 @@ static void check_property_phandle_args(struct check *c,
struct node *root = dti->dt;
int cell, cellsize = 0;
- if (prop->val.len % sizeof(cell_t)) {
+ if (!is_multiple_of(prop->val.len, sizeof(cell_t))) {
FAIL_PROP(c, dti, node, prop,
"property size (%d) is invalid, expected multiple of %zu",
prop->val.len, sizeof(cell_t));
@@ -1594,7 +1602,7 @@ static void check_interrupts_property(struct check *c,
if (!irq_prop)
return;
- if (irq_prop->val.len % sizeof(cell_t))
+ if (!is_multiple_of(irq_prop->val.len, sizeof(cell_t)))
FAIL_PROP(c, dti, node, irq_prop, "size (%d) is invalid, expected multiple of %zu",
irq_prop->val.len, sizeof(cell_t));
@@ -1643,7 +1651,7 @@ static void check_interrupts_property(struct check *c,
}
irq_cells = propval_cell(prop);
- if (irq_prop->val.len % (irq_cells * sizeof(cell_t))) {
+ if (!is_multiple_of(irq_prop->val.len, irq_cells * sizeof(cell_t))) {
FAIL_PROP(c, dti, node, prop,
"size is (%d), expected multiple of %d",
irq_prop->val.len, (int)(irq_cells * sizeof(cell_t)));