[U-Boot-Users] [PATCH u-boot-fdt] FDT command improvements.

Jerry Van Baren gvb.uboot at gmail.com
Sat May 12 16:05:43 CEST 2007


Fix "fdt set" so that it will create a non-existing property.
Add "fdt mknode" to create nodes.

Signed-off-by: Gerald Van Baren <vanbaren at cideas.com>
---
 common/cmd_fdt.c |  271 ++++++++++++++++++++++++++++-------------------------
 1 files changed, 143 insertions(+), 128 deletions(-)

diff --git a/common/cmd_fdt.c b/common/cmd_fdt.c
index a119985..8402ca7 100644
--- a/common/cmd_fdt.c
+++ b/common/cmd_fdt.c
@@ -56,27 +56,38 @@ static char data[SCRATCHPAD];
 static int fdt_valid(void);
 static void print_data(const void *data, int len);
 
+static int findnodeoffset(const char *pathp)
+{
+	int  nodeoffset;
+
+	if (strcmp(pathp, "/") == 0) {
+		nodeoffset = 0;
+	} else {
+		nodeoffset = fdt_path_offset (fdt, pathp);
+		if (nodeoffset < 0) {
+			/*
+			 * Not found or something else bad happened.
+			 */
+			printf ("findnodeoffset() libfdt: %s\n", fdt_strerror(nodeoffset));
+		}
+	}
+	return nodeoffset;
+}
 
 /*
  * Flattened Device Tree command, see the help for parameter definitions.
  */
 int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 {
-	char		op;
-
 	if (argc < 2) {
 		printf ("Usage:\n%s\n", cmdtp->usage);
 		return 1;
 	}
 
-	/*
-	 * Figure out which subcommand was given
-	 */
-	op = argv[1][0];
 	/********************************************************************
 	 * Set the address of the fdt
 	 ********************************************************************/
-	if (op == 'a') {
+	if (argv[1][0] == 'a') {
 		/*
 		 * Set the address [and length] of the fdt.
 		 */
@@ -102,7 +113,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 				 */
 				err = fdt_open_into(fdt, fdt, len);
 				if (err != 0) {
-					printf ("libfdt: %s\n", fdt_strerror(err));
+					printf ("libfdt fdt_open_into(): %s\n", fdt_strerror(err));
 				}
 			}
 		}
@@ -110,7 +121,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 	/********************************************************************
 	 * Move the fdt
 	 ********************************************************************/
-	} else if (op == 'm') {
+	} else if ((argv[1][0] == 'm') && (argv[1][1] == 'o')) {
 		struct fdt_header *newaddr;
 		int  len;
 		int  err;
@@ -150,15 +161,48 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 		 */
 		err = fdt_open_into(fdt, newaddr, len);
 		if (err != 0) {
-			printf ("libfdt: %s\n", fdt_strerror(err));
+			printf ("libfdt fdt_open_into(): %s\n", fdt_strerror(err));
 			return 1;
 		}
 		fdt = newaddr;
 
 	/********************************************************************
-	 * Set the value of a node in the fdt.
+	 * Make a new node
+	 ********************************************************************/
+	} else if ((argv[1][0] == 'm') && (argv[1][1] == 'k')) {
+		char *pathp;		/* path */
+		char *nodep;		/* new node to add */
+		int  nodeoffset;	/* node offset from libfdt */
+		int  err;
+
+		/*
+		 * Parameters: Node path, new node to be appended to the path.
+		 */
+		if (argc < 4) {
+			printf ("Usage:\n%s\n", cmdtp->usage);
+			return 1;
+		}
+
+		pathp = argv[2];
+		nodep = argv[3];
+
+		nodeoffset = findnodeoffset(pathp);
+		if (nodeoffset < 0) {
+			/*
+			 * Not found or something else bad happened.
+			 */
+			return 1;
+		}
+		err = fdt_add_subnode(fdt, nodeoffset, nodep);
+		if (err < 0) {
+			printf ("libfdt fdt_add_subnode(): %s\n", fdt_strerror(err));
+			return 1;
+		}
+
+	/********************************************************************
+	 * Set the value of a property in the fdt.
 	 ********************************************************************/
-	} else if (op == 's') {
+	} else if (argv[1][0] == 's') {
 		char *pathp;		/* path */
 		char *prop;			/* property */
 		struct fdt_property *nodep;	/* node struct pointer */
@@ -183,102 +227,85 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 		prop   = argv[3];
 		newval = argv[4];
 
-		if (strcmp(pathp, "/") == 0) {
-			nodeoffset = 0;
-		} else {
-			nodeoffset = fdt_path_offset (fdt, pathp);
-			if (nodeoffset < 0) {
-				/*
-			 	 * Not found or something else bad happened.
-			 	 */
-				printf ("libfdt: %s\n", fdt_strerror(nodeoffset));
-				return 1;
-			}
-		}
-		nodep = fdt_getprop (fdt, nodeoffset, prop, &oldlen);
-		if (oldlen < 0) {
-			printf ("libfdt %s\n", fdt_strerror(oldlen));
-			return 1;
-		} else if (oldlen == 0) {
+		nodeoffset = findnodeoffset(pathp);
+		if (nodeoffset < 0) {
 			/*
-			 * The specified property has no value
+			 * Not found or something else bad happened.
 			 */
-			printf("%s has no value, cannot set one (yet).\n", prop);
 			return 1;
-		} else {
+		}
+		/*
+		 * Convert the new property
+		 */
+		vp = data;
+		if (*newval == '<') {
 			/*
-			 * Convert the new property
+			 * Bigger values than bytes.
 			 */
-			vp = data;
-			if (*newval == '<') {
-				/*
-				 * Bigger values than bytes.
-				 */
-				len = 0;
-				newval++;
-				while ((*newval != '>') && (*newval != '\0')) {
-					cp = newval;
-					tmp = simple_strtoul(cp, &newval, 16);
-					if ((newval - cp) <= 2) {
-						*vp = tmp & 0xFF;
-						vp  += 1;
-						len += 1;
-					} else if ((newval - cp) <= 4) {
-						*(uint16_t *)vp = __cpu_to_be16(tmp);
-						vp  += 2;
-						len += 2;
-					} else if ((newval - cp) <= 8) {
-						*(uint32_t *)vp = __cpu_to_be32(tmp);
-						vp  += 4;
-						len += 4;
-					} else {
-						printf("Sorry, I could not convert \"%s\"\n", cp);
-						return 1;
-					}
-					while (*newval == ' ')
-						newval++;
-				}
-				if (*newval != '>') {
-					printf("Unexpected character '%c'\n", *newval);
-					return 1;
-				}
-			} else if (*newval == '[') {
-				/*
-				 * Byte stream.  Convert the values.
-				 */
-				len = 0;
-				newval++;
-				while ((*newval != ']') && (*newval != '\0')) {
-					tmp = simple_strtoul(newval, &newval, 16);
-					*vp++ = tmp & 0xFF;
-					len++;
-					while (*newval == ' ')
-						newval++;
-				}
-				if (*newval != ']') {
-					printf("Unexpected character '%c'\n", *newval);
+			len = 0;
+			newval++;
+			while ((*newval != '>') && (*newval != '\0')) {
+				cp = newval;
+				tmp = simple_strtoul(cp, &newval, 16);
+				if ((newval - cp) <= 2) {
+					*vp = tmp & 0xFF;
+					vp  += 1;
+					len += 1;
+				} else if ((newval - cp) <= 4) {
+					*(uint16_t *)vp = __cpu_to_be16(tmp);
+					vp  += 2;
+					len += 2;
+				} else if ((newval - cp) <= 8) {
+					*(uint32_t *)vp = __cpu_to_be32(tmp);
+					vp  += 4;
+					len += 4;
+				} else {
+					printf("Sorry, I could not convert \"%s\"\n", cp);
 					return 1;
 				}
-			} else {
-				/*
-				 * Assume it is a string.  Copy it into our data area for
-				 * convenience (including the terminating '\0').
-				 */
-				len = strlen(newval) + 1;
-				strcpy(data, newval);
+				while (*newval == ' ')
+					newval++;
 			}
-
-			ret = fdt_setprop(fdt, nodeoffset, prop, data, len);
-			if (ret < 0) {
-				printf ("libfdt %s\n", fdt_strerror(ret));
+			if (*newval != '>') {
+				printf("Unexpected character '%c'\n", *newval);
+				return 1;
+			}
+		} else if (*newval == '[') {
+			/*
+			 * Byte stream.  Convert the values.
+			 */
+			len = 0;
+			newval++;
+			while ((*newval != ']') && (*newval != '\0')) {
+				tmp = simple_strtoul(newval, &newval, 16);
+				*vp++ = tmp & 0xFF;
+				len++;
+				while (*newval == ' ')
+					newval++;
+			}
+			if (*newval != ']') {
+				printf("Unexpected character '%c'\n", *newval);
 				return 1;
 			}
+		} else {
+			/*
+			 * Assume it is a string.  Copy it into our data area for
+			 * convenience (including the terminating '\0').
+			 */
+			len = strlen(newval) + 1;
+			strcpy(data, newval);
+		}
+
+		ret = fdt_setprop(fdt, nodeoffset, prop, data, len);
+		if (ret < 0) {
+			printf ("libfdt fdt_setprop(): %s\n", fdt_strerror(ret));
+			return 1;
 		}
 
 	/********************************************************************
 	 * Print (recursive) / List (single level)
 	 ********************************************************************/
-	} else if ((op == 'p') || (op == 'l')) {
+	} else if ((argv[1][0] == 'p') || (argv[1][0] == 'l')) {
 		/*
 		 * Recursively print (a portion of) the fdt.
 		 */
@@ -297,7 +324,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 		/*
 		 * list is an alias for print, but limited to 1 level
 		 */
-		if (op == 'l') {
+		if (argv[1][0] == 'l') {
 			depth = 1;
 		}
 
@@ -311,18 +338,12 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 		else
 			prop = NULL;
 
-		if (strcmp(pathp, "/") == 0) {
-			nodeoffset = 0;
-			printf("/");
-		} else {
-			nodeoffset = fdt_path_offset (fdt, pathp);
-			if (nodeoffset < 0) {
-				/*
-				 * Not found or something else bad happened.
-				 */
-				printf ("libfdt %s\n", fdt_strerror(nodeoffset));
-				return 1;
-			}
+		nodeoffset = findnodeoffset(pathp);
+		if (nodeoffset < 0) {
+			/*
+			 * Not found or something else bad happened.
+			 */
+			return 1;
 		}
 		/*
 		 * The user passed in a property as well as node path.  Print only
@@ -339,7 +360,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 				printf("\n");
 				return 0;
 			} else {
-				printf ("libfdt %s\n", fdt_strerror(len));
+				printf ("libfdt fdt_getprop(): %s\n", fdt_strerror(len));
 				return 1;
 			}
 		}
@@ -359,7 +380,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 				level++;
 				offstack[level] = nodeoffset;
 				if (level >= MAX_LEVEL) {
-					printf("Aaaiii <splat> nested too deep.\n");
+					printf("Aaaiii <splat> nested too deep. Aborting.\n");
 					return 1;
 				}
 				break;
@@ -374,7 +395,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 			case FDT_PROP:
 				nodep = fdt_getprop (fdt, offstack[level], pathp, &len);
 				if (len < 0) {
-					printf ("libfdt %s\n", fdt_strerror(len));
+					printf ("libfdt fdt_getprop(): %s\n", fdt_strerror(len));
 					return 1;
 				} else if (len == 0) {
 					/* the property has no value */
@@ -403,7 +424,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 	/********************************************************************
 	 * Remove a property/node
 	 ********************************************************************/
-	} else if (op == 'r') {
+	} else if (argv[1][0] == 'r') {
 		int  nodeoffset;	/* node offset from libfdt */
 		int  err;
 
@@ -411,17 +432,12 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 		 * Get the path.  The root node is an oddball, the offset
 		 * is zero and has no name.
 		 */
-		if (strcmp(argv[2], "/") == 0) {
-			nodeoffset = 0;
-		} else {
-			nodeoffset = fdt_path_offset (fdt, argv[2]);
-			if (nodeoffset < 0) {
-				/*
-				 * Not found or something else bad happened.
-				 */
-				printf ("libfdt %s\n", fdt_strerror(nodeoffset));
-				return 1;
-			}
+		nodeoffset = findnodeoffset(argv[2]);
+		if (nodeoffset < 0) {
+			/*
+			 * Not found or something else bad happened.
+			 */
+			return 1;
 		}
 		/*
 		 * Do the delete.  A fourth parameter means delete a property,
@@ -430,13 +446,13 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 		if (argc > 3) {
 			err = fdt_delprop(fdt, nodeoffset, argv[3]);
 			if (err < 0) {
-				printf("fdt_delprop libfdt: %s\n", fdt_strerror(err));
+				printf("libfdt fdt_delprop():  %s\n", fdt_strerror(err));
 				return err;
 			}
 		} else {
 			err = fdt_del_node(fdt, nodeoffset);
 			if (err < 0) {
-				printf("fdt_del_node libfdt: %s\n", fdt_strerror(err));
+				printf("libfdt fdt_del_node():  %s\n", fdt_strerror(err));
 				return err;
 			}
 		}
@@ -444,19 +460,19 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 	/********************************************************************
 	 * Create a chosen node
 	 ********************************************************************/
-	} else if (op == 'c') {
+	} else if (argv[1][0] == 'c') {
 		fdt_chosen(fdt, 0, 0, 1);
 
 	/********************************************************************
 	 * Create a u-boot-env node
 	 ********************************************************************/
-	} else if (op == 'e') {
+	} else if (argv[1][0] == 'e') {
 		fdt_env(fdt);
 
 	/********************************************************************
 	 * Create a bd_t node
 	 ********************************************************************/
-	} else if (op == 'b') {
+	} else if (argv[1][0] == 'b') {
 		fdt_bd_t(fdt);
 
 	/********************************************************************
@@ -486,7 +502,7 @@ static int fdt_valid(void)
 		return 1;	/* valid */
 
 	if (err < 0) {
-		printf("libfdt: %s", fdt_strerror(err));
+		printf("libfdt fdt_check_header(): %s", fdt_strerror(err));
 		/*
 		 * Be more informative on bad version.
 		 */
@@ -630,7 +646,6 @@ U_BOOT_CMD(
 	"fdt bd_t   - Add/replace the \"/bd_t\" branch in the tree\n"
 #endif
 	"Hints:\n"
-	" * Set a larger length with the fdt addr command to add to the blob.\n"
 	" * If the property you are setting/printing has a '#' character,\n"
 	"     you MUST escape it with a \\ character or quote it with \" or\n"
 	"     it will be ignored as a comment.\n"
-- 
1.4.4.4





More information about the U-Boot mailing list