<div dir="ltr"><div dir="ltr"><br></div><br><div class="gmail_quote gmail_quote_container"><div dir="ltr" class="gmail_attr">On Fri, 28 Mar 2025 at 16:52, Patrice Chotard <<a href="mailto:patrice.chotard@foss.st.com">patrice.chotard@foss.st.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">Since introduction of OF_UPSTREAM flag, U-Boot's dtc must be able<br>
to compile Kernel's device tree.<br>
<br>
Since kernel commit 7de129f5389b ("ARM: dts: stm32: stm32mp151a-prtt1l:<br>
Fix QSPI configuration"), label relative path references has been<br>
introduced. These label relative path references is not supported<br>
by current U-Boot dtc version 1.5.0: (see mailing list discussion [1]).<br>
<br>
In order to support such label relative patch references<br>
adds following commit from upstream DTC tree:<br></blockquote><div><br></div><div>Maybe we need to rebase to the latest upstream dtc, I'm not sure pulling in a random set of bits from upstream is the right way to do things as it's brings things selectively which may bring along other issues.</div><div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">
commit 651410e54cb9 ("util: introduce xstrndup helper")<br>
commit ec7986e682cf ("dtc: introduce label relative path references")<br>
<br>
[1] <a href="https://lore.kernel.org/all/20250115144428.GZ3476@bill-the-cat/T/" rel="noreferrer" target="_blank">https://lore.kernel.org/all/20250115144428.GZ3476@bill-the-cat/T/</a><br>
<br>
Signed-off-by: Patrice Chotard <<a href="mailto:patrice.chotard@foss.st.com" target="_blank">patrice.chotard@foss.st.com</a>><br>
Cc: Tom Rini <<a href="mailto:trini@konsulko.com" target="_blank">trini@konsulko.com</a>><br>
Cc: Simon Glass <<a href="mailto:sjg@chromium.org" target="_blank">sjg@chromium.org</a>><br>
---<br>
<br>
scripts/dtc/dtc-lexer.l | 2 +-<br>
scripts/dtc/dtc-parser.y | 13 +++++++++++++<br>
scripts/dtc/livetree.c | 33 ++++++++++++++++++++++++++++++---<br>
scripts/dtc/util.c | 11 +++++++++++<br>
scripts/dtc/util.h | 1 +<br>
5 files changed, 56 insertions(+), 4 deletions(-)<br>
<br>
diff --git a/scripts/dtc/dtc-lexer.l b/scripts/dtc/dtc-lexer.l<br>
index d3694d6cf20..d34e1b04220 100644<br>
--- a/scripts/dtc/dtc-lexer.l<br>
+++ b/scripts/dtc/dtc-lexer.l<br>
@@ -215,7 +215,7 @@ static void PRINTF(1, 2) lexical_error(const char *fmt, ...);<br>
return DT_REF;<br>
}<br>
<br>
-<*>"&{/"{PATHCHAR}*\} { /* new-style path reference */<br>
+<*>"&{"{PATHCHAR}*\} { /* new-style path reference */<br>
yytext[yyleng-1] = '\0';<br>
DPRINT("Ref: %s\n", yytext+2);<br>
yylval.labelref = xstrdup(yytext+2);<br>
diff --git a/scripts/dtc/dtc-parser.y b/scripts/dtc/dtc-parser.y<br>
index 011a5b25539..b3b9c83873d 100644<br>
--- a/scripts/dtc/dtc-parser.y<br>
+++ b/scripts/dtc/dtc-parser.y<br>
@@ -34,6 +34,12 @@ extern void yyerror(char const *s);<br>
<br>
extern struct dt_info *parser_output;<br>
extern bool treesource_error;<br>
+<br>
+static bool is_ref_relative(const char *ref)<br>
+{<br>
+ return ref[0] != '/' && strchr(&ref[1], '/');<br>
+}<br>
+<br>
%}<br>
<br>
%union {<br>
@@ -176,12 +182,17 @@ devicetree:<br>
*/<br>
if (!($<flags>-1 & DTSF_PLUGIN))<br>
ERROR(&@2, "Label or path %s not found", $1);<br>
+ else if (is_ref_relative($1))<br>
+ ERROR(&@2, "Label-relative reference %s not supported in plugin", $1);<br>
$$ = add_orphan_node(name_node(build_node(NULL, NULL), ""), $2, $1);<br>
}<br>
| devicetree DT_LABEL DT_REF nodedef<br>
{<br>
struct node *target = get_node_by_ref($1, $3);<br>
<br>
+ if (($<flags>-1 & DTSF_PLUGIN) && is_ref_relative($3))<br>
+ ERROR(&@2, "Label-relative reference %s not supported in plugin", $3);<br>
+<br>
if (target) {<br>
add_label(&target->labels, $2);<br>
merge_nodes(target, $4);<br>
@@ -197,6 +208,8 @@ devicetree:<br>
* so $-1 is what we want (plugindecl)<br>
*/<br>
if ($<flags>-1 & DTSF_PLUGIN) {<br>
+ if (is_ref_relative($2))<br>
+ ERROR(&@2, "Label-relative reference %s not supported in plugin", $2);<br>
add_orphan_node($1, $3, $2);<br>
} else {<br>
struct node *target = get_node_by_ref($1, $2);<br>
diff --git a/scripts/dtc/livetree.c b/scripts/dtc/livetree.c<br>
index ba06ef348be..4cfc2adccdd 100644<br>
--- a/scripts/dtc/livetree.c<br>
+++ b/scripts/dtc/livetree.c<br>
@@ -583,12 +583,39 @@ struct node *get_node_by_phandle(struct node *tree, cell_t phandle)<br>
<br>
struct node *get_node_by_ref(struct node *tree, const char *ref)<br>
{<br>
+ struct node *target = tree;<br>
+ const char *label = NULL, *path = NULL;<br>
+<br>
if (streq(ref, "/"))<br>
return tree;<br>
- else if (ref[0] == '/')<br>
- return get_node_by_path(tree, ref);<br>
+<br>
+ if (ref[0] == '/')<br>
+ path = ref;<br>
else<br>
- return get_node_by_label(tree, ref);<br>
+ label = ref;<br>
+<br>
+ if (label) {<br>
+ const char *slash = strchr(label, '/');<br>
+ char *buf = NULL;<br>
+<br>
+ if (slash) {<br>
+ buf = xstrndup(label, slash - label);<br>
+ label = buf;<br>
+ path = slash + 1;<br>
+ }<br>
+<br>
+ target = get_node_by_label(tree, label);<br>
+<br>
+ free(buf);<br>
+<br>
+ if (!target)<br>
+ return NULL;<br>
+ }<br>
+<br>
+ if (path)<br>
+ target = get_node_by_path(target, path);<br>
+<br>
+ return target;<br>
}<br>
<br>
cell_t get_node_phandle(struct node *root, struct node *node)<br>
diff --git a/scripts/dtc/util.c b/scripts/dtc/util.c<br>
index 23334d39bb6..25d4db1e8c2 100644<br>
--- a/scripts/dtc/util.c<br>
+++ b/scripts/dtc/util.c<br>
@@ -46,6 +46,17 @@ char *xstrdup(const char *s)<br>
return d;<br>
}<br>
<br>
+char *xstrndup(const char *s, size_t n)<br>
+{<br>
+ size_t len = strnlen(s, n) + 1;<br>
+ char *d = xmalloc(len);<br>
+<br>
+ memcpy(d, s, len - 1);<br>
+ d[len - 1] = '\0';<br>
+<br>
+ return d;<br>
+}<br>
+<br>
/* based in part from (3) vsnprintf */<br>
int xasprintf(char **strp, const char *fmt, ...)<br>
{<br>
diff --git a/scripts/dtc/util.h b/scripts/dtc/util.h<br>
index 211d584435d..23e32962385 100644<br>
--- a/scripts/dtc/util.h<br>
+++ b/scripts/dtc/util.h<br>
@@ -70,6 +70,7 @@ static inline void *xrealloc(void *p, size_t len)<br>
}<br>
<br>
extern char *xstrdup(const char *s);<br>
+extern char *xstrndup(const char *s, size_t len);<br>
<br>
extern int PRINTF(2, 3) xasprintf(char **strp, const char *fmt, ...);<br>
extern char *join_path(const char *path, const char *name);<br>
-- <br>
2.25.1<br>
<br>
</blockquote></div></div>