device_tree: Have absolute paths start with '/'

Currently DT paths are *not* expected to start with '/'. This is not
what the spec says (see Devicetree Specification v0.2, 2.2.3 Path Names)
and also not what is done by Linux.

Change dt_find_node_by_path() to expect paths to start with '/' and add
a leading '/' to all DT path strings. Besides the compatibility with the
spec this change is also needed to support aliases in the future.

This patch was adapted from depthcharge's http://crosreview.com/1252770

Change-Id: Ibdf59ccbb4ead38c6193b630642fd1f1e847dd89
Signed-off-by: Julius Werner <jwerner@chromium.org>
Reviewed-on: https://review.coreboot.org/c/coreboot/+/32865
Reviewed-by: Hung-Te Lin <hungte@chromium.org>
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
This commit is contained in:
Julius Werner 2019-05-03 18:29:28 -07:00 committed by Patrick Georgi
parent f36d53c653
commit fbec63d15f
2 changed files with 9 additions and 9 deletions

View File

@ -556,7 +556,7 @@ struct device_tree_node *dt_find_node(struct device_tree_node *parent,
* *
* @param tree The device tree to search. * @param tree The device tree to search.
* @param path A string representing a path in the device tree, with * @param path A string representing a path in the device tree, with
* nodes separated by '/'. Example: "soc/firmware/coreboot" * nodes separated by '/'. Example: "/firmware/coreboot"
* @param addrcp Pointer that will be updated with any #address-cells * @param addrcp Pointer that will be updated with any #address-cells
* value found in the path. May be NULL to ignore. * value found in the path. May be NULL to ignore.
* @param sizecp Pointer that will be updated with any #size-cells * @param sizecp Pointer that will be updated with any #size-cells
@ -565,13 +565,13 @@ struct device_tree_node *dt_find_node(struct device_tree_node *parent,
* @return The found/created node, or NULL. * @return The found/created node, or NULL.
* *
* It is the caller responsibility to provide the correct path string, namely * It is the caller responsibility to provide the correct path string, namely
* not starting or ending with a '/', and not having "//" anywhere in it. * starting with a '/', not ending in a '/' and not having "//" anywhere in it.
*/ */
struct device_tree_node *dt_find_node_by_path(struct device_tree *tree, struct device_tree_node *dt_find_node_by_path(struct device_tree *tree,
const char *path, u32 *addrcp, const char *path, u32 *addrcp,
u32 *sizecp, int create) u32 *sizecp, int create)
{ {
char *dup_path = strdup(path); char *dup_path = strdup(&path[1]); /* remove leading '/' */
/* Hopefully enough depth for any node. */ /* Hopefully enough depth for any node. */
const char *path_array[15]; const char *path_array[15];
int i; int i;
@ -995,7 +995,7 @@ struct device_tree_node *dt_init_reserved_memory_node(struct device_tree *tree)
struct device_tree_node *reserved; struct device_tree_node *reserved;
u32 addr = 0, size = 0; u32 addr = 0, size = 0;
reserved = dt_find_node_by_path(tree, "reserved-memory", &addr, reserved = dt_find_node_by_path(tree, "/reserved-memory", &addr,
&size, 1); &size, 1);
if (!reserved) if (!reserved)
return NULL; return NULL;

View File

@ -185,7 +185,7 @@ static int dt_platform_fixup(struct device_tree_fixup *fixup,
size_t i; size_t i;
/* Set the sclk clock rate. */ /* Set the sclk clock rate. */
dt_node = dt_find_node_by_path(tree, "soc@0/sclk", NULL, NULL, 0); dt_node = dt_find_node_by_path(tree, "/soc@0/sclk", NULL, NULL, 0);
if (dt_node) { if (dt_node) {
const u32 freq = thunderx_get_io_clock(); const u32 freq = thunderx_get_io_clock();
printk(BIOS_INFO, "%s: Set SCLK to %u Hz\n", __func__, freq); printk(BIOS_INFO, "%s: Set SCLK to %u Hz\n", __func__, freq);
@ -195,7 +195,7 @@ static int dt_platform_fixup(struct device_tree_fixup *fixup,
__func__); __func__);
/* Set refclkuaa clock rate. */ /* Set refclkuaa clock rate. */
dt_node = dt_find_node_by_path(tree, "soc@0/refclkuaa", NULL, dt_node = dt_find_node_by_path(tree, "/soc@0/refclkuaa", NULL,
NULL, 0); NULL, 0);
if (dt_node) { if (dt_node) {
const u32 freq = uart_platform_refclk(); const u32 freq = uart_platform_refclk();
@ -211,7 +211,7 @@ static int dt_platform_fixup(struct device_tree_fixup *fixup,
char path[32]; char path[32];
const uint64_t addr = UAAx_PF_BAR0(i); const uint64_t addr = UAAx_PF_BAR0(i);
/* Remove the node */ /* Remove the node */
snprintf(path, sizeof(path), "soc@0/serial@%llx", addr); snprintf(path, sizeof(path), "/soc@0/serial@%llx", addr);
dt_node = dt_find_node_by_path(tree, path, NULL, NULL, 0); dt_node = dt_find_node_by_path(tree, path, NULL, NULL, 0);
if (!dt_node || uart_is_enabled(i)) { if (!dt_node || uart_is_enabled(i)) {
printk(BIOS_INFO, "%s: ignoring %s\n", __func__, path); printk(BIOS_INFO, "%s: ignoring %s\n", __func__, path);
@ -227,7 +227,7 @@ static int dt_platform_fixup(struct device_tree_fixup *fixup,
u32 phandle = 0; u32 phandle = 0;
const uint64_t addr = PEM_PEMX_PF_BAR0(i); const uint64_t addr = PEM_PEMX_PF_BAR0(i);
/* Remove the node */ /* Remove the node */
snprintf(path, sizeof(path), "soc@0/pci@%llx", addr); snprintf(path, sizeof(path), "/soc@0/pci@%llx", addr);
dt_node = dt_find_node_by_path(tree, path, NULL, NULL, 0); dt_node = dt_find_node_by_path(tree, path, NULL, NULL, 0);
if (!dt_node || bdk_pcie_is_running(0, i)) { if (!dt_node || bdk_pcie_is_running(0, i)) {
printk(BIOS_INFO, "%s: ignoring %s\n", __func__, path); printk(BIOS_INFO, "%s: ignoring %s\n", __func__, path);
@ -239,7 +239,7 @@ static int dt_platform_fixup(struct device_tree_fixup *fixup,
list_remove(&dt_node->list_node); list_remove(&dt_node->list_node);
/* Remove phandle to non existing nodes */ /* Remove phandle to non existing nodes */
snprintf(path, sizeof(path), "soc@0/smmu0@%llx", SMMU_PF_BAR0); snprintf(path, sizeof(path), "/soc@0/smmu0@%llx", SMMU_PF_BAR0);
dt_node = dt_find_node_by_path(tree, path, NULL, NULL, 0); dt_node = dt_find_node_by_path(tree, path, NULL, NULL, 0);
if (!dt_node) { if (!dt_node) {
printk(BIOS_ERR, "%s: SMMU entry not found\n", printk(BIOS_ERR, "%s: SMMU entry not found\n",