diff options
-rw-r--r-- | include/fdtdec.h | 23 | ||||
-rw-r--r-- | lib/fdtdec.c | 22 |
2 files changed, 41 insertions, 4 deletions
diff --git a/include/fdtdec.h b/include/fdtdec.h index 6249f22..1e198f8 100644 --- a/include/fdtdec.h +++ b/include/fdtdec.h @@ -213,6 +213,29 @@ int fdtdec_find_aliases_for_id(const void *blob, const char *name, enum fdt_compat_id id, int *node_list, int maxcount); /* + * This function is similar to fdtdec_find_aliases_for_id() except that it + * adds to the node_list that is passed in. Any 0 elements are considered + * available for allocation - others are considered already used and are + * skipped. + * + * You can use this by calling fdtdec_find_aliases_for_id() with an + * uninitialised array, then setting the elements that are returned to -1, + * say, then calling this function, perhaps with a different compat id. + * Any elements you get back that are >0 are new nodes added by the call + * to this function. + * + * Note that if you have some nodes with aliases and some without, you are + * sailing close to the wind. The call to fdtdec_find_aliases_for_id() with + * one compat_id may fill in positions for which you have aliases defined + * for another compat_id. When you later call *this* function with the second + * compat_id, the alias positions may already be used. A debug warning may + * be generated in this case, but it is safest to define aliases for all + * nodes when you care about the ordering. + */ +int fdtdec_add_aliases_for_id(const void *blob, const char *name, + enum fdt_compat_id id, int *node_list, int maxcount); + +/* * Get the name for a compatible ID * * @param id Compatible ID to look for diff --git a/lib/fdtdec.c b/lib/fdtdec.c index 5239e79..2149bd7 100644 --- a/lib/fdtdec.c +++ b/lib/fdtdec.c @@ -153,10 +153,18 @@ int fdtdec_next_alias(const void *blob, const char *name, return node; } -/* TODO: Can we tighten this code up a little? */ int fdtdec_find_aliases_for_id(const void *blob, const char *name, enum fdt_compat_id id, int *node_list, int maxcount) { + memset(node_list, '\0', sizeof(*node_list) * maxcount); + + return fdtdec_add_aliases_for_id(blob, name, id, node_list, maxcount); +} + +/* TODO: Can we tighten this code up a little? */ +int fdtdec_add_aliases_for_id(const void *blob, const char *name, + enum fdt_compat_id id, int *node_list, int maxcount) +{ int name_len = strlen(name); int nodes[maxcount]; int num_found = 0; @@ -185,8 +193,6 @@ int fdtdec_find_aliases_for_id(const void *blob, const char *name, __func__, name); /* Now find all the aliases */ - memset(node_list, '\0', sizeof(*node_list) * maxcount); - for (offset = fdt_first_property_offset(blob, alias_node); offset > 0; offset = fdt_next_property_offset(blob, offset)) { @@ -233,11 +239,19 @@ int fdtdec_find_aliases_for_id(const void *blob, const char *name, * it as done. */ if (fdtdec_get_is_enabled(blob, node)) { + if (node_list[number]) { + debug("%s: warning: alias '%s' requires that " + "a node be placed in the list in a " + "position which is already filled by " + "node '%s'\n", __func__, path, + fdt_get_name(blob, node, NULL)); + continue; + } node_list[number] = node; if (number >= num_found) num_found = number + 1; } - nodes[j] = 0; + nodes[found] = 0; } /* Add any nodes not mentioned by an alias */ |