devicetree.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v6 1/2] Add fdtget utility to read property values from a device tree
@ 2012-01-21 18:14 Simon Glass
       [not found] ` <1327169688-7569-2-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
  0 siblings, 1 reply; 6+ messages in thread
From: Simon Glass @ 2012-01-21 18:14 UTC (permalink / raw)
  To: Devicetree Discuss

This simply utility makes it easy for scripts to read values from the device
tree. It is written in C and uses the same libfdt as the rest of the dtc
package.

What is it for:
- Reading fdt values from scripts
- Extracting fdt information within build systems
- Looking at particular values without having to dump the entire tree

To use it, specify the fdt binary file on command line followed by a list of
node, property pairs. The utility then looks up each node, finds the property
and displays the value.

Each value is printed on a new line.

fdtget tries to guess the type of each property based on its contents. This
is not always reliable, so you can use the -t option to force fdtget to decode
the value as a string, or byte, etc.

To read from stdin, use - as the file.

Usage:
	fdtget <options> <dt file> [<node> <property>]...
Options:
	-t <type>	Type of data
	-h		Print this help

<type>	s=string, i=int, u=unsigned, x=hex
	Optional modifier prefix:
		hh or b=byte, h=2 byte, l=4 byte (default)

Signed-off-by: Simon Glass <sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
---
Changes in v2:
- Adjust tests for new fdtget arguments
- Merge two related commits into this one
- Remove use of getopt_long()
- Separate arguments for node and property
- Use structure for storing display options

Changes in v3:
- Add a few more tests for 1- and 2-byte formats
- Add error checking for the property not being a multiple of value size
- Change format of -t argument to be more like printf
- Change help string and make part of it common
- Squash fdtget test commit into fdtget

Changes in v6:
- Another rebase to ToT

 .gitignore              |    1 +
 Makefile                |    4 +
 Makefile.utils          |    7 ++
 fdtget.c                |  226 +++++++++++++++++++++++++++++++++++++++++++++++
 tests/fdtget-runtest.sh |   35 +++++++
 tests/run_tests.sh      |   43 +++++++++-
 tests/tests.sh          |    1 +
 util.h                  |   10 ++
 8 files changed, 326 insertions(+), 1 deletions(-)
 create mode 100644 fdtget.c
 create mode 100755 tests/fdtget-runtest.sh

diff --git a/.gitignore b/.gitignore
index 74714cd..2d82b71 100644
--- a/.gitignore
+++ b/.gitignore
@@ -10,3 +10,4 @@ lex.yy.c
 /fdtdump
 /convert-dtsv0
 /version_gen.h
+/fdtget
diff --git a/Makefile b/Makefile
index 4582f5d..a54a209 100644
--- a/Makefile
+++ b/Makefile
@@ -110,6 +110,7 @@ include Makefile.utils
 BIN += convert-dtsv0
 BIN += dtc
 BIN += fdtdump
+BIN += fdtget
 
 SCRIPTS = dtdiff
 
@@ -120,6 +121,7 @@ ifneq ($(DEPTARGETS),)
 -include $(DTC_OBJS:%.o=%.d)
 -include $(CONVERT_OBJS:%.o=%.d)
 -include $(FDTDUMP_OBJS:%.o=%.d)
+-include $(FDTGET_OBJS:%.o=%.d)
 endif
 
 
@@ -180,6 +182,8 @@ convert-dtsv0: $(CONVERT_OBJS)
 
 fdtdump:	$(FDTDUMP_OBJS)
 
+fdtget:	$(FDTGET_OBJS) $(LIBFDT_archive)
+
 
 #
 # Testsuite rules
diff --git a/Makefile.utils b/Makefile.utils
index fae5b00..38efa3c 100644
--- a/Makefile.utils
+++ b/Makefile.utils
@@ -8,3 +8,10 @@ FDTDUMP_SRCS = \
 	util.c
 
 FDTDUMP_OBJS = $(FDTDUMP_SRCS:%.c=%.o)
+
+
+FDTGET_SRCS = \
+	fdtget.c \
+	util.c
+
+FDTGET_OBJS = $(FDTGET_SRCS:%.c=%.o)
diff --git a/fdtget.c b/fdtget.c
new file mode 100644
index 0000000..48ab615
--- /dev/null
+++ b/fdtget.c
@@ -0,0 +1,226 @@
+/*
+ * Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ */
+
+#include <ctype.h>
+#include <getopt.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <libfdt.h>
+
+#include "util.h"
+
+/* Holds information which controls our output and options */
+struct display_info {
+	int type;		/* data type (s/i/u/x or 0 for default) */
+	int size;		/* data size (1/2/4) */
+};
+
+static void report_error(const char *where, int err)
+{
+	fprintf(stderr, "Error at '%s': %s\n", where, fdt_strerror(err));
+}
+
+/**
+ * Displays data of a given length according to selected options
+ *
+ * If a specific data type is provided in disp, then this is used. Otherwise
+ * we try to guess the data type / size from the contents.
+ *
+ * @param disp		Display information / options
+ * @param data		Data to display
+ * @param len		Maximum length of buffer
+ * @return 0 if ok, -1 if data does not match format
+ */
+static int show_data(struct display_info *disp, const char *data, int len)
+{
+	int i, size;
+	const uint8_t *p = (const uint8_t *)data;
+	const char *s;
+	int value;
+	int is_string;
+	char fmt[3];
+
+	/* no data, don't print */
+	if (len == 0)
+		return 0;
+
+	is_string = (disp->type) == 's' ||
+		(!disp->type && util_is_printable_string(data, len));
+	if (is_string) {
+		if (data[len - 1] != '\0') {
+			fprintf(stderr, "Unterminated string\n");
+			return -1;
+		}
+		for (s = data; s - data < len; s += strlen(s) + 1) {
+			if (s != data)
+				printf(" ");
+			printf("%s", (const char *)s);
+		}
+		return 0;
+	}
+	size = disp->size;
+	if (size == -1)
+		size = (len % 4) == 0 ? 4 : 1;
+	else if (len % size) {
+		fprintf(stderr, "Property length must be a multiple of "
+				"selected data size\n");
+		return -1;
+	}
+	fmt[0] = '%';
+	fmt[1] = disp->type ? disp->type : 'd';
+	fmt[2] = '\0';
+	for (i = 0; i < len; i += size, p += size) {
+		if (i)
+			printf(" ");
+		value = size == 4 ? fdt32_to_cpu(*(const uint32_t *)p) :
+			size == 2 ? (*p << 8) | p[1] : *p;
+		printf(fmt, value);
+	}
+	return 0;
+}
+
+/**
+ * Show the data for a given node (and perhaps property) according to the
+ * display option provided.
+ *
+ * @param blob		FDT blob
+ * @param disp		Display information / options
+ * @param node		Node to display
+ * @param property	Name of property to display, or NULL if none
+ * @return 0 if ok, -ve on error
+ */
+static int show_data_for_item(const void *blob, struct display_info *disp,
+		int node, const char *property)
+{
+	const void *value = NULL;
+	int len, err = 0;
+
+	value = fdt_getprop(blob, node, property, &len);
+	if (value) {
+		if (show_data(disp, value, len))
+			err = -1;
+		else
+			printf("\n");
+	} else {
+		report_error(property, len);
+		err = -1;
+	}
+	return err;
+}
+
+/**
+ * Run the main fdtget operation, given a filename and valid arguments
+ *
+ * @param disp		Display information / options
+ * @param filename	Filename of blob file
+ * @param arg		List of arguments to process
+ * @param arg_count	Number of arguments
+ * @param return 0 if ok, -ve on error
+ */
+static int do_fdtget(struct display_info *disp, const char *filename,
+		     char **arg, int arg_count)
+{
+	char *blob;
+	int i, node;
+
+	blob = utilfdt_read(filename);
+	if (!blob)
+		return -1;
+
+	for (i = 0; i + 2 <= arg_count; i += 2) {
+		node = fdt_path_offset(blob, arg[0]);
+		if (node < 0) {
+			report_error(arg[0], node);
+			return -1;
+		}
+
+		if (show_data_for_item(blob, disp, node, arg[1]))
+			return -1;
+	}
+	return 0;
+}
+
+static const char *usage_msg =
+	"fdtget - read values from device tree\n"
+	"\n"
+	"Each value is printed on a new line.\n\n"
+	"Usage:\n"
+	"	fdtget <options> <dt file> [<node> <property>]...\n"
+	"Options:\n"
+	"\t-t <type>\tType of data\n"
+	"\t-h\t\tPrint this help\n\n"
+	USAGE_TYPE_MSG;
+
+static void usage(const char *msg)
+{
+	if (msg)
+		fprintf(stderr, "Error: %s\n\n", msg);
+
+	fprintf(stderr, "%s", usage_msg);
+	exit(2);
+}
+
+int main(int argc, char *argv[])
+{
+	char *filename = NULL;
+	struct display_info disp;
+
+	/* set defaults */
+	memset(&disp, '\0', sizeof(disp));
+	disp.size = -1;
+	for (;;) {
+		int c = getopt(argc, argv, "ht:");
+		if (c == -1)
+			break;
+
+		switch (c) {
+		case 'h':
+		case '?':
+			usage(NULL);
+
+		case 't':
+			if (utilfdt_decode_type(optarg, &disp.type,
+					&disp.size))
+				usage("Invalid type string");
+			break;
+		}
+	}
+
+	if (optind < argc)
+		filename = argv[optind++];
+	if (!filename)
+		usage("Missing filename");
+
+	argv += optind;
+	argc -= optind;
+
+	/* Allow no arguments, and silently succeed */
+	if (!argc)
+		return 0;
+
+	/* Check for node, property arguments */
+	if (argc % 2)
+		usage("Must have an even number of arguments");
+
+	if (do_fdtget(&disp, filename, argv, argc))
+		return 1;
+	return 0;
+}
diff --git a/tests/fdtget-runtest.sh b/tests/fdtget-runtest.sh
new file mode 100755
index 0000000..f38184f
--- /dev/null
+++ b/tests/fdtget-runtest.sh
@@ -0,0 +1,35 @@
+#! /bin/sh
+
+. ./tests.sh
+
+LOG="tmp.log.$$"
+EXPECT="tmp.expect.$$"
+
+rm -f $TMPFILE $LOG
+
+expect="$1"
+echo "$expect" >$EXPECT
+shift
+
+verbose_run_log "$LOG" $VALGRIND "$DTGET" "$@"
+ret="$?"
+
+if [ "$ret" -ne 0 -a "$expect" = "ERR" ]; then
+	PASS
+fi
+
+if [ "$ret" -gt 127 ]; then
+    signame=$(kill -l $[ret - 128])
+    FAIL "Killed by SIG$signame"
+fi
+
+diff $EXPECT $LOG
+ret="$?"
+
+rm -f $LOG $EXPECT
+
+if [ "$ret" -eq 0 ]; then
+	PASS
+else
+	FAIL
+fi
diff --git a/tests/run_tests.sh b/tests/run_tests.sh
index e42154b..e6184df 100755
--- a/tests/run_tests.sh
+++ b/tests/run_tests.sh
@@ -83,6 +83,13 @@ asm_to_so_test () {
     run_wrap_test asm_to_so "$@"
 }
 
+run_fdtget_test () {
+    # run_fdtget_test name expected_output dtb_file args...
+    echo -n "$1:	"
+    shift
+    base_run_test sh fdtget-runtest.sh "$@"
+}
+
 tree1_tests () {
     TREE=$1
 
@@ -402,6 +409,37 @@ dtbs_equal_tests () {
     cmp_tests test_tree1.dtb $WRONG_TREE1
 }
 
+fdtget_tests () {
+    file=label01.dtb
+    $DTC -O dtb -o $file ${file%.dtb}.dts 2>/dev/null
+
+    # run_fdtget_test <test-name> <expected-result> <args>...
+    run_fdtget_test "Simple string" "MyBoardName" $file / model
+    run_fdtget_test "Multiple string i" "77 121 66 111 \
+97 114 100 78 97 109 101 0 77 121 66 111 97 114 100 70 97 109 105 \
+108 121 78 97 109 101 0" $file / compatible
+    run_fdtget_test "Multiple string s" "MyBoardName MyBoardFamilyName" \
+	-t s $file / compatible
+    run_fdtget_test "Integer" "32768" $file /cpus/PowerPC,970@1 d-cache-size
+    run_fdtget_test "Integer hex" "8000" -tx $file \
+	/cpus/PowerPC,970@1 d-cache-size
+    run_fdtget_test "Integer list" "61 62 63 0" -tbx $file \
+	/randomnode tricky1
+    run_fdtget_test "Byte list short" "a b c d de ea ad be ef" -tbx \
+	$file /randomnode blob
+
+    # Here the property size is not a multiple of 4 bytes, so it should fail
+    run_fdtget_test "Integer list invalid" ERR -tlx \
+	$file /randomnode mixed
+    run_fdtget_test "Integer list halfword" "6162 6300 1234 0 a 0 b 0 c" -thx \
+	$file /randomnode mixed
+    run_fdtget_test "Integer list byte" \
+	"61 62 63 0 12 34 0 0 0 a 0 0 0 b 0 0 0 c" -thhx \
+	$file /randomnode mixed
+    run_fdtget_test "Missing property" ERR -ts \
+	$file /randomnode doctor-who
+}
+
 utilfdt_tests () {
     run_test utilfdt_test
 }
@@ -421,7 +459,7 @@ while getopts "vt:m" ARG ; do
 done
 
 if [ -z "$TESTSETS" ]; then
-    TESTSETS="libfdt utilfdt dtc dtbs_equal"
+    TESTSETS="libfdt utilfdt dtc dtbs_equal fdtget"
 fi
 
 # Make sure we don't have stale blobs lying around
@@ -441,6 +479,9 @@ for set in $TESTSETS; do
 	"dtbs_equal")
 	    dtbs_equal_tests
 	    ;;
+	"fdtget")
+	    fdtget_tests
+	    ;;
     esac
 done
 
diff --git a/tests/tests.sh b/tests/tests.sh
index 30ffead..d9a0524 100644
--- a/tests/tests.sh
+++ b/tests/tests.sh
@@ -11,6 +11,7 @@ FAIL () {
 }
 
 DTC=../dtc
+DTGET=../fdtget
 
 verbose_run () {
     if [ -z "$QUIET_TEST" ]; then
diff --git a/util.h b/util.h
index 730918e..c8eb45d 100644
--- a/util.h
+++ b/util.h
@@ -140,4 +140,14 @@ int utilfdt_write_err(const char *filename, const void *blob);
  */
 int utilfdt_decode_type(const char *fmt, int *type, int *size);
 
+/*
+ * This is a usage message fragment for the -t option. It is the format
+ * supported by utilfdt_decode_type.
+ */
+
+#define USAGE_TYPE_MSG \
+	"<type>\ts=string, i=int, u=unsigned, x=hex\n" \
+	"\tOptional modifier prefix:\n" \
+	"\t\thh or b=byte, h=2 byte, l=4 byte (default)\n";
+
 #endif /* _UTIL_H */
-- 
1.7.7.3

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v6 2/2] Add fdtput utility to write property values to a device tree
       [not found] ` <1327169688-7569-2-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
@ 2012-01-21 18:14   ` Simon Glass
       [not found]     ` <1327169688-7569-3-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
  2012-01-21 21:26   ` [PATCH v6 1/2] Add fdtget utility to read property values from " Jon Loeliger
  2012-01-22 10:30   ` David Gibson
  2 siblings, 1 reply; 6+ messages in thread
From: Simon Glass @ 2012-01-21 18:14 UTC (permalink / raw)
  To: Devicetree Discuss

This simple utility allows writing of values into a device tree from the
command line. It aimes to be the opposite of fdtget.

What is it for:
- Updating fdt values when a binary blob already exists
   (even though source may be available it might be easier to use this
    utility rather than sed, etc.)
- Writing machine-specific fdt values within a build system

To use it, specify the fdt binary file on command line followed by the node
and property to set. Then, provide a list of values to put into that
property. Often there will be just one, but fdtput also supports arrays and
string lists.

fdtput does not try to guess the type of the property based on looking at
the arguments. Instead it always assumes that an integer is provided. To
indicate that you want to write a string, use -ts. You can also provide
hex values with -tx.

The command line arguments are joined together into a single value. For
strings, a nul terminator is placed between each string when it is packed
into the property. To avoid this, pass the string as a single argument.

Usage:
	fdtput <options> <dt file> <<node> <property> [<value>...]
Options:
	-t <type>	Type of data
	-v		Verbose: display each value decoded from command line
	-h		Print this help

<type>	s=string, i=int, u=unsigned, x=hex
	Optional modifier prefix:
		hh or b=byte, h=2 byte, l=4 byte (default)

To read from stdin and write to stdout, use - as the file. So you can do:

cat somefile.dtb | fdtput -ts - /node prop "My string value" > newfile.dtb

This commit also adds basic tests to verify the major features.

Signed-off-by: Simon Glass <sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
---
Changes in v2:
- Add test for exhausting fdt space
- Add test for multiple strings
- Adjust tests for new fdtput arguments
- Remove limits on data size of property writting to fdt
- Remove use of getopt_long()
- Separate arguments for node and property

Changes in v3:
- Squash fdtput tests into fdtput commit

Changes in v4:
- Rebase to ToT

Changes in v5:
- Rebase to ToT

Changes in v6:
- Another rebase to ToT

 .gitignore              |    1 +
 Makefile                |    4 +
 Makefile.utils          |    7 ++
 fdtput.c                |  235 +++++++++++++++++++++++++++++++++++++++++++++++
 tests/fdtput-runtest.sh |   55 +++++++++++
 tests/run_tests.sh      |   73 ++++++++++++++-
 tests/tests.sh          |    1 +
 7 files changed, 375 insertions(+), 1 deletions(-)
 create mode 100644 fdtput.c
 create mode 100644 tests/fdtput-runtest.sh

diff --git a/.gitignore b/.gitignore
index 2d82b71..5074980 100644
--- a/.gitignore
+++ b/.gitignore
@@ -11,3 +11,4 @@ lex.yy.c
 /convert-dtsv0
 /version_gen.h
 /fdtget
+/fdtput
diff --git a/Makefile b/Makefile
index a54a209..510caa6 100644
--- a/Makefile
+++ b/Makefile
@@ -111,6 +111,7 @@ BIN += convert-dtsv0
 BIN += dtc
 BIN += fdtdump
 BIN += fdtget
+BIN += fdtput
 
 SCRIPTS = dtdiff
 
@@ -122,6 +123,7 @@ ifneq ($(DEPTARGETS),)
 -include $(CONVERT_OBJS:%.o=%.d)
 -include $(FDTDUMP_OBJS:%.o=%.d)
 -include $(FDTGET_OBJS:%.o=%.d)
+-include $(FDTPUT_OBJS:%.o=%.d)
 endif
 
 
@@ -184,6 +186,8 @@ fdtdump:	$(FDTDUMP_OBJS)
 
 fdtget:	$(FDTGET_OBJS) $(LIBFDT_archive)
 
+fdtput:	$(FDTPUT_OBJS) $(LIBFDT_archive)
+
 
 #
 # Testsuite rules
diff --git a/Makefile.utils b/Makefile.utils
index 38efa3c..48ece49 100644
--- a/Makefile.utils
+++ b/Makefile.utils
@@ -15,3 +15,10 @@ FDTGET_SRCS = \
 	util.c
 
 FDTGET_OBJS = $(FDTGET_SRCS:%.c=%.o)
+
+
+FDTPUT_SRCS = \
+	fdtput.c \
+	util.c
+
+FDTPUT_OBJS = $(FDTPUT_SRCS:%.c=%.o)
diff --git a/fdtput.c b/fdtput.c
new file mode 100644
index 0000000..f6ebd24
--- /dev/null
+++ b/fdtput.c
@@ -0,0 +1,235 @@
+/*
+ * Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ */
+
+#include <assert.h>
+#include <ctype.h>
+#include <getopt.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <libfdt.h>
+
+#include "util.h"
+
+struct display_info {
+	int type;		/* data type (s/i/u/x or 0 for default) */
+	int size;		/* data size (1/2/4) */
+	int verbose;		/* verbose output */
+};
+
+static void report_error(const char *where, int err)
+{
+	fprintf(stderr, "Error at '%s': %s\n", where, fdt_strerror(err));
+}
+
+/**
+ * Encode a series of arguments in a property value.
+ *
+ * @param disp		Display information / options
+ * @param arg		List of arguments from command line
+ * @param arg_count	Number of arguments (may be 0)
+ * @param valuep	Returns buffer containing value
+ * @param *value_len	Returns length of value encoded
+ */
+static int encode_value(struct display_info *disp, char **arg, int arg_count,
+			char **valuep, int *value_len)
+{
+	char *value = NULL;	/* holding area for value */
+	int value_size = 0;	/* size of holding area */
+	char *ptr;		/* pointer to current value position */
+	int len;		/* length of this cell/string/byte */
+	int ival;
+	int upto;	/* the number of bytes we have written to buf */
+	char fmt[3];
+
+	upto = 0;
+
+	if (disp->verbose)
+		fprintf(stderr, "Decoding value:\n");
+
+	fmt[0] = '%';
+	fmt[1] = disp->type ? disp->type : 'd';
+	fmt[2] = '\0';
+	for (; arg_count > 0; arg++, arg_count--, upto += len) {
+		/* assume integer unless told otherwise */
+		if (disp->type == 's')
+			len = strlen(*arg) + 1;
+		else
+			len = disp->size == -1 ? 4 : disp->size;
+
+		/* enlarge our value buffer by a suitable margin if needed */
+		if (upto + len > value_size) {
+			value_size = (upto + len) + 500;
+			value = realloc(value, value_size);
+			if (!value) {
+				fprintf(stderr, "Out of mmory: cannot alloc "
+					"%d bytes\n", value_size);
+				return -1;
+			}
+		}
+
+		ptr = value + upto;
+		if (disp->type == 's') {
+			memcpy(ptr, *arg, len);
+			if (disp->verbose)
+				fprintf(stderr, "\tstring: '%s'\n", ptr);
+		} else {
+			int *iptr = (int *)ptr;
+			sscanf(*arg, fmt, &ival);
+			if (len == 4)
+				*iptr = cpu_to_fdt32(ival);
+			else
+				*ptr = (uint8_t)ival;
+			if (disp->verbose) {
+				fprintf(stderr, "\t%s: %d\n",
+					disp->size == 1 ? "byte" :
+					disp->size == 2 ? "short" : "int",
+					ival);
+			}
+		}
+	}
+	*value_len = upto;
+	*valuep = value;
+	if (disp->verbose)
+		fprintf(stderr, "Value size %d\n", upto);
+	return 0;
+}
+
+static int store_key_value(void *blob, const char *node_name,
+		const char *property, const char *buf, int len)
+{
+	int node;
+	int err;
+
+	node = fdt_path_offset(blob, node_name);
+	if (node < 0) {
+		report_error(node_name, node);
+		return -1;
+	}
+
+	err = fdt_setprop(blob, node, property, buf, len);
+	if (err) {
+		report_error(property, err);
+		return -1;
+	}
+	return 0;
+}
+
+static int do_fdtput(struct display_info *disp, const char *filename,
+		    char **arg, int arg_count)
+{
+	char *value;
+	char *blob;
+	int len, ret = 0;
+
+	blob = utilfdt_read(filename);
+	if (!blob)
+		return -1;
+
+	/* convert the arguments into a single binary value, then store */
+	assert(arg_count >= 2);
+	if (encode_value(disp, arg + 2, arg_count - 2, &value, &len) ||
+		store_key_value(blob, *arg, arg[1], value, len))
+		ret = -1;
+
+	if (!ret)
+		ret = utilfdt_write(filename, blob);
+
+	free(blob);
+	return ret;
+}
+
+static const char *usage_msg =
+	"fdtput - write a property value to a device tree\n"
+	"\n"
+	"The command line arguments are joined together into a single value.\n"
+	"\n"
+	"Usage:\n"
+	"	fdtput <options> <dt file> <<node> <property> [<value>...]\n"
+	"Options:\n"
+	"\t-t <type>\tType of data\n"
+	"\t-v\t\tVerbose: display each value decoded from command line\n"
+	"\t-h\t\tPrint this help\n\n"
+	USAGE_TYPE_MSG;
+
+static void usage(const char *msg)
+{
+	if (msg)
+		fprintf(stderr, "Error: %s\n\n", msg);
+
+	fprintf(stderr, "%s", usage_msg);
+	exit(2);
+}
+
+int main(int argc, char *argv[])
+{
+	struct display_info disp;
+	char *filename = NULL;
+
+	memset(&disp, '\0', sizeof(disp));
+	disp.size = -1;
+	for (;;) {
+		int c = getopt(argc, argv, "ht:v");
+		if (c == -1)
+			break;
+
+		/*
+		 * TODO: add options to:
+		 * - delete property
+		 * - delete node (optionally recursively)
+		 * - rename node
+		 * - pack fdt before writing
+		 * - set amount of free space when writing
+		 * - expand fdt if value doesn't fit
+		 */
+		switch (c) {
+		case 'h':
+		case '?':
+			usage(NULL);
+
+		case 't':
+			if (utilfdt_decode_type(optarg, &disp.type,
+					&disp.size))
+				usage("Invalid type string");
+			break;
+
+		case 'v':
+			disp.verbose = 1;
+			break;
+		}
+	}
+
+	if (optind < argc)
+		filename = argv[optind++];
+	if (!filename)
+		usage("Missing filename");
+
+	argv += optind;
+	argc -= optind;
+
+	if (argc < 1)
+		usage("Missing node");
+	if (argc < 2)
+		usage("Missing property");
+
+	if (do_fdtput(&disp, filename, argv, argc))
+		return 1;
+	return 0;
+}
diff --git a/tests/fdtput-runtest.sh b/tests/fdtput-runtest.sh
new file mode 100644
index 0000000..ea51569
--- /dev/null
+++ b/tests/fdtput-runtest.sh
@@ -0,0 +1,55 @@
+#! /bin/sh
+
+# Run script for fdtput tests
+# We run fdtput to update the device tree, thn fdtget to check it
+
+# Usage
+#    fdtput-runtest.sh name expected_output dtb_file node property flags value
+
+. ./tests.sh
+
+LOG="tmp.log.$$"
+EXPECT="tmp.expect.$$"
+
+rm -f $TMPFILE $LOG
+
+expect="$1"
+echo "$expect" >$EXPECT
+dtb="$2"
+node="$3"
+property="$4"
+flags="$5"
+shift 5
+value="$@"
+
+# First run fdtput
+verbose_run $VALGRIND "$DTPUT" "$dtb" "$node" "$property" $value $flags
+ret="$?"
+
+if [ "$ret" -ne 0 -a "$expect" = "ERR" ]; then
+	PASS
+fi
+if [ "$ret" -gt 127 ]; then
+    signame=$(kill -l $[ret - 128])
+    FAIL "Killed by SIG$signame"
+fi
+
+# Now fdtget to read the value
+verbose_run_log "$LOG" $VALGRIND "$DTGET" "$dtb" "$node" "$property" $flags
+ret="$?"
+
+if [ "$ret" -gt 127 ]; then
+    signame=$(kill -l $[ret - 128])
+    FAIL "Killed by SIG$signame"
+fi
+
+diff $EXPECT $LOG
+ret="$?"
+
+rm -f $LOG $EXPECT
+
+if [ "$ret" -eq 0 ]; then
+	PASS
+else
+	FAIL
+fi
diff --git a/tests/run_tests.sh b/tests/run_tests.sh
index e6184df..2650559 100755
--- a/tests/run_tests.sh
+++ b/tests/run_tests.sh
@@ -90,6 +90,21 @@ run_fdtget_test () {
     base_run_test sh fdtget-runtest.sh "$@"
 }
 
+run_fdtput_test () {
+    # run_fdtput_test name expected_output dtb_file node property flags value...
+    echo -n "$1:	"
+    shift
+    output="$1"
+    dtb="$2"
+    node="$3"
+    property="$4"
+    flags="$5"
+    shift 5
+    base_run_test sh fdtput-runtest.sh "$output" "$dtb" "$node" "$property" \
+		"$flags" $@
+#     base_run_test sh fdtput-runtest.sh "$@"
+}
+
 tree1_tests () {
     TREE=$1
 
@@ -440,6 +455,59 @@ fdtget_tests () {
 	$file /randomnode doctor-who
 }
 
+fdtput_tests () {
+    file=label01.dtb
+    src=label01.dts
+
+    # Create some test files containing useful strings
+    base=tmp.test0
+    file1=tmp.test1
+    file2=tmp.test2
+    bigfile1=tmp.test3
+    bigfile2=tmp.test4
+
+    # Filter out anything the shell might not like
+    cat $src | tr -d "'\"\n\;/\.\*{}\-" | tr -s "[:blank:]" " " >$base
+
+    # Make two small files
+    head -5 $base >$file1
+    cat $file1 | tr a-z A-Z | cut -c10-30 | sort -r >$file2
+
+    # and two larger ones
+    cat $base > $bigfile1
+    tac $base | tr a-z A-Z | sort -r >$bigfile2
+
+    # Allow just enough space for both file1 and file2
+    (( space = $(stat -c %s $file1) + $(stat -c %s $file2) ))
+    $DTC -O dtb -p $space -o $file ${file%.dtb}.dts 2>/dev/null
+
+    # run_fdtput_test <test-name> <expected-result> <file> <key> <flags>
+    #		<args>...
+    run_fdtput_test "Simple string" "a_model" $file / model -ts "a_model"
+    run_fdtput_test "Multiple string s" "board1 board2" \
+	$file / compatible -ts board1 board2
+    run_fdtput_test "Single string with spaces" "board1 board2" \
+	$file / compatible -ts "board1 board2"
+    run_fdtput_test "Integer" "32768" \
+	$file /cpus/PowerPC,970@1 d-cache-size "" "32768"
+    run_fdtput_test "Integer hex" "8001" \
+	$file /cpus/PowerPC,970@1 d-cache-size -tx 0x8001
+    run_fdtput_test "Integer list" "2 3 12" \
+	$file /randomnode tricky1 -tbi "02 003 12"
+    run_fdtput_test "Byte list short" "a b c ea ad be ef" \
+	$file /randomnode blob -tbx "a b c ea ad be ef"
+    run_fdtput_test "Integer list short" "a0b0c0d deeaae ef000000" \
+	$file /randomnode blob -tx "a0b0c0d deeaae ef000000"
+    run_fdtput_test "Large string list" "`cat $file1 $file2`" \
+	$file /randomnode blob -ts "`cat $file1`" "`cat $file2`"
+
+    # This should be larger than available space in the fdt ($space)
+    run_fdtput_test "Enormous string list" ERR \
+	$file /randomnode blob -ts "`cat $bigfile1`" "`cat $bigfile2`"
+
+    # TODO: Add tests for verbose mode?
+}
+
 utilfdt_tests () {
     run_test utilfdt_test
 }
@@ -459,7 +527,7 @@ while getopts "vt:m" ARG ; do
 done
 
 if [ -z "$TESTSETS" ]; then
-    TESTSETS="libfdt utilfdt dtc dtbs_equal fdtget"
+    TESTSETS="libfdt utilfdt dtc dtbs_equal fdtget fdtput"
 fi
 
 # Make sure we don't have stale blobs lying around
@@ -482,6 +550,9 @@ for set in $TESTSETS; do
 	"fdtget")
 	    fdtget_tests
 	    ;;
+	"fdtput")
+	    fdtput_tests
+	    ;;
     esac
 done
 
diff --git a/tests/tests.sh b/tests/tests.sh
index d9a0524..6e5e76a 100644
--- a/tests/tests.sh
+++ b/tests/tests.sh
@@ -12,6 +12,7 @@ FAIL () {
 
 DTC=../dtc
 DTGET=../fdtget
+DTPUT=../fdtput
 
 verbose_run () {
     if [ -z "$QUIET_TEST" ]; then
-- 
1.7.7.3

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH v6 1/2] Add fdtget utility to read property values from a device tree
       [not found] ` <1327169688-7569-2-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
  2012-01-21 18:14   ` [PATCH v6 2/2] Add fdtput utility to write property values to " Simon Glass
@ 2012-01-21 21:26   ` Jon Loeliger
  2012-01-22 10:30   ` David Gibson
  2 siblings, 0 replies; 6+ messages in thread
From: Jon Loeliger @ 2012-01-21 21:26 UTC (permalink / raw)
  To: Simon Glass; +Cc: Devicetree Discuss

> This simply utility makes it easy for scripts to read values from the device
> tree. It is written in C and uses the same libfdt as the rest of the dtc
> package.
> 
> What is it for:
> - Reading fdt values from scripts
> - Extracting fdt information within build systems
> - Looking at particular values without having to dump the entire tree
> 
> To use it, specify the fdt binary file on command line followed by a list of
> node, property pairs. The utility then looks up each node, finds the property
> and displays the value.
> 
> Each value is printed on a new line.
> 
> fdtget tries to guess the type of each property based on its contents. This
> is not always reliable, so you can use the -t option to force fdtget to decode
> the value as a string, or byte, etc.
> 
> To read from stdin, use - as the file.
> 
> Usage:
> 	fdtget <options> <dt file> [<node> <property>]...
> Options:
> 	-t <type>	Type of data
> 	-h		Print this help
> 
> <type>	s=string, i=int, u=unsigned, x=hex
> 	Optional modifier prefix:
> 		hh or b=byte, h=2 byte, l=4 byte (default)
> 
> Signed-off-by: Simon Glass <sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>

Applied.

jdl

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v6 2/2] Add fdtput utility to write property values to a device tree
       [not found]     ` <1327169688-7569-3-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
@ 2012-01-21 21:28       ` Jon Loeliger
  2012-01-22 11:23       ` David Gibson
  1 sibling, 0 replies; 6+ messages in thread
From: Jon Loeliger @ 2012-01-21 21:28 UTC (permalink / raw)
  To: Simon Glass; +Cc: Devicetree Discuss

> This simple utility allows writing of values into a device tree from the
> command line. It aimes to be the opposite of fdtget.
> 
> What is it for:
> - Updating fdt values when a binary blob already exists
>    (even though source may be available it might be easier to use this
>     utility rather than sed, etc.)
> - Writing machine-specific fdt values within a build system
> 
> To use it, specify the fdt binary file on command line followed by the node
> and property to set. Then, provide a list of values to put into that
> property. Often there will be just one, but fdtput also supports arrays and
> string lists.
> 
> fdtput does not try to guess the type of the property based on looking at
> the arguments. Instead it always assumes that an integer is provided. To
> indicate that you want to write a string, use -ts. You can also provide
> hex values with -tx.
> 
> The command line arguments are joined together into a single value. For
> strings, a nul terminator is placed between each string when it is packed
> into the property. To avoid this, pass the string as a single argument.
> 
> Usage:
> 	fdtput <options> <dt file> <<node> <property> [<value>...]
> Options:
> 	-t <type>	Type of data
> 	-v		Verbose: display each value decoded from command line
> 	-h		Print this help
> 
> <type>	s=string, i=int, u=unsigned, x=hex
> 	Optional modifier prefix:
> 		hh or b=byte, h=2 byte, l=4 byte (default)
> 
> To read from stdin and write to stdout, use - as the file. So you can do:
> 
> cat somefile.dtb | fdtput -ts - /node prop "My string value" > newfile.dtb
> 
> This commit also adds basic tests to verify the major features.
> 
> Signed-off-by: Simon Glass <sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>

Applied.

Also, "make check" didn't know to build fdtput nor fdtget.  So I added
a new ${TEST_BIN} in the top level Makefile to track which executables
are tested.

Thanks,
jdl

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v6 1/2] Add fdtget utility to read property values from a device tree
       [not found] ` <1327169688-7569-2-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
  2012-01-21 18:14   ` [PATCH v6 2/2] Add fdtput utility to write property values to " Simon Glass
  2012-01-21 21:26   ` [PATCH v6 1/2] Add fdtget utility to read property values from " Jon Loeliger
@ 2012-01-22 10:30   ` David Gibson
  2 siblings, 0 replies; 6+ messages in thread
From: David Gibson @ 2012-01-22 10:30 UTC (permalink / raw)
  To: Simon Glass; +Cc: Devicetree Discuss

On Sat, Jan 21, 2012 at 10:14:47AM -0800, Simon Glass wrote:
> This simply utility makes it easy for scripts to read values from the device
> tree. It is written in C and uses the same libfdt as the rest of the dtc
> package.
> 
> What is it for:
> - Reading fdt values from scripts
> - Extracting fdt information within build systems
> - Looking at particular values without having to dump the entire tree
> 
> To use it, specify the fdt binary file on command line followed by a list of
> node, property pairs. The utility then looks up each node, finds the property
> and displays the value.
> 
> Each value is printed on a new line.
> 
> fdtget tries to guess the type of each property based on its contents. This
> is not always reliable, so you can use the -t option to force fdtget to decode
> the value as a string, or byte, etc.
> 
> To read from stdin, use - as the file.
> 
> Usage:
> 	fdtget <options> <dt file> [<node> <property>]...
> Options:
> 	-t <type>	Type of data
> 	-h		Print this help
> 
> <type>	s=string, i=int, u=unsigned, x=hex
> 	Optional modifier prefix:
> 		hh or b=byte, h=2 byte, l=4 byte (default)
> 
> Signed-off-by: Simon Glass <sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>

Um.. there are a bunch of small problems here.

[snip]
> +	if (size == -1)
> +		size = (len % 4) == 0 ? 4 : 1;

If you have braces on one path of an if/else, please put them on both.

> +	else if (len % size) {
> +		fprintf(stderr, "Property length must be a multiple of "
> +				"selected data size\n");
> +		return -1;
> +	}

[snip]
> diff --git a/tests/fdtget-runtest.sh b/tests/fdtget-runtest.sh
> new file mode 100755
> index 0000000..f38184f
> --- /dev/null
> +++ b/tests/fdtget-runtest.sh
> @@ -0,0 +1,35 @@
> +#! /bin/sh
> +
> +. ./tests.sh
> +
> +LOG="tmp.log.$$"
> +EXPECT="tmp.expect.$$"
> +
> +rm -f $TMPFILE $LOG

TMPFILE doesn't appear to be defined here.

> +
> +expect="$1"
> +echo "$expect" >$EXPECT
> +shift
> +
> +verbose_run_log "$LOG" $VALGRIND "$DTGET" "$@"
> +ret="$?"
> +
> +if [ "$ret" -ne 0 -a "$expect" = "ERR" ]; then
> +	PASS

Ugh, ugly.  I'd prefer a different option to the script, or a
different script entirely for checking expected errors.

> +fi
> +
> +if [ "$ret" -gt 127 ]; then
> +    signame=$(kill -l $[ret - 128])

$[] for math expressions is a bashism.  We want the test scripts to be
plain Bourne shell.

> +    FAIL "Killed by SIG$signame"
> +fi
> +
> +diff $EXPECT $LOG

Please use diff -u, it's much easier to read.  Also the output should
go to null unless running in verbose mode.

> +ret="$?"
> +
> +rm -f $LOG $EXPECT
> +
> +if [ "$ret" -eq 0 ]; then
> +	PASS
> +else
> +	FAIL
> +fi
> diff --git a/tests/run_tests.sh b/tests/run_tests.sh
> index e42154b..e6184df 100755
> --- a/tests/run_tests.sh
> +++ b/tests/run_tests.sh
> @@ -83,6 +83,13 @@ asm_to_so_test () {
>      run_wrap_test asm_to_so "$@"
>  }
>  
> +run_fdtget_test () {
> +    # run_fdtget_test name expected_output dtb_file args...
> +    echo -n "$1:	"
> +    shift
> +    base_run_test sh fdtget-runtest.sh "$@"

Ugh.  I hate the way you've overriden the displayed test name with a
message.  The headings in the test output are intentionally the
commands you need to run the tests individually, to make tracking
things down easier in the case of failures.

As it is the labels don't even distinguish between fdtget and later
corresponding fdtput tests.

> +}
> +
>  tree1_tests () {
>      TREE=$1
>  
> @@ -402,6 +409,37 @@ dtbs_equal_tests () {
>      cmp_tests test_tree1.dtb $WRONG_TREE1
>  }
>  
> +fdtget_tests () {
> +    file=label01.dtb
> +    $DTC -O dtb -o $file ${file%.dtb}.dts 2>/dev/null

Should be a run_dtc_test here to catch an error in this command.
Also, I think ${%} is a bashism.

> +
> +    # run_fdtget_test <test-name> <expected-result> <args>...
> +    run_fdtget_test "Simple string" "MyBoardName" $file / model
> +    run_fdtget_test "Multiple string i" "77 121 66 111 \
> +97 114 100 78 97 109 101 0 77 121 66 111 97 114 100 70 97 109 105 \
> +108 121 78 97 109 101 0" $file / compatible
> +    run_fdtget_test "Multiple string s" "MyBoardName MyBoardFamilyName" \
> +	-t s $file / compatible
> +    run_fdtget_test "Integer" "32768" $file /cpus/PowerPC,970@1 d-cache-size
> +    run_fdtget_test "Integer hex" "8000" -tx $file \
> +	/cpus/PowerPC,970@1 d-cache-size
> +    run_fdtget_test "Integer list" "61 62 63 0" -tbx $file \
> +	/randomnode tricky1
> +    run_fdtget_test "Byte list short" "a b c d de ea ad be ef" -tbx \
> +	$file /randomnode blob
> +
> +    # Here the property size is not a multiple of 4 bytes, so it should fail
> +    run_fdtget_test "Integer list invalid" ERR -tlx \
> +	$file /randomnode mixed
> +    run_fdtget_test "Integer list halfword" "6162 6300 1234 0 a 0 b 0 c" -thx \
> +	$file /randomnode mixed
> +    run_fdtget_test "Integer list byte" \
> +	"61 62 63 0 12 34 0 0 0 a 0 0 0 b 0 0 0 c" -thhx \
> +	$file /randomnode mixed
> +    run_fdtget_test "Missing property" ERR -ts \
> +	$file /randomnode doctor-who
> +}
> +
>  utilfdt_tests () {
>      run_test utilfdt_test
>  }
> @@ -421,7 +459,7 @@ while getopts "vt:m" ARG ; do
>  done
>  
>  if [ -z "$TESTSETS" ]; then
> -    TESTSETS="libfdt utilfdt dtc dtbs_equal"
> +    TESTSETS="libfdt utilfdt dtc dtbs_equal fdtget"
>  fi
>  
>  # Make sure we don't have stale blobs lying around
> @@ -441,6 +479,9 @@ for set in $TESTSETS; do
>  	"dtbs_equal")
>  	    dtbs_equal_tests
>  	    ;;
> +	"fdtget")
> +	    fdtget_tests
> +	    ;;
>      esac
>  done
>  
> diff --git a/tests/tests.sh b/tests/tests.sh
> index 30ffead..d9a0524 100644
> --- a/tests/tests.sh
> +++ b/tests/tests.sh
> @@ -11,6 +11,7 @@ FAIL () {
>  }
>  
>  DTC=../dtc
> +DTGET=../fdtget
>  
>  verbose_run () {
>      if [ -z "$QUIET_TEST" ]; then
> diff --git a/util.h b/util.h
> index 730918e..c8eb45d 100644
> --- a/util.h
> +++ b/util.h
> @@ -140,4 +140,14 @@ int utilfdt_write_err(const char *filename, const void *blob);
>   */
>  int utilfdt_decode_type(const char *fmt, int *type, int *size);
>  
> +/*
> + * This is a usage message fragment for the -t option. It is the format
> + * supported by utilfdt_decode_type.
> + */
> +
> +#define USAGE_TYPE_MSG \
> +	"<type>\ts=string, i=int, u=unsigned, x=hex\n" \
> +	"\tOptional modifier prefix:\n" \
> +	"\t\thh or b=byte, h=2 byte, l=4 byte (default)\n";
> +
>  #endif /* _UTIL_H */

-- 
David Gibson			| I'll have my music baroque, and my code
david AT gibson.dropbear.id.au	| minimalist, thank you.  NOT _the_ _other_
				| _way_ _around_!
http://www.ozlabs.org/~dgibson

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v6 2/2] Add fdtput utility to write property values to a device tree
       [not found]     ` <1327169688-7569-3-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
  2012-01-21 21:28       ` Jon Loeliger
@ 2012-01-22 11:23       ` David Gibson
  1 sibling, 0 replies; 6+ messages in thread
From: David Gibson @ 2012-01-22 11:23 UTC (permalink / raw)
  To: Simon Glass; +Cc: Devicetree Discuss

On Sat, Jan 21, 2012 at 10:14:48AM -0800, Simon Glass wrote:
> This simple utility allows writing of values into a device tree from the
> command line. It aimes to be the opposite of fdtget.

[snip]
> diff --git a/tests/fdtput-runtest.sh b/tests/fdtput-runtest.sh
> new file mode 100644
> index 0000000..ea51569
> --- /dev/null
> +++ b/tests/fdtput-runtest.sh
> @@ -0,0 +1,55 @@
> +#! /bin/sh
> +
> +# Run script for fdtput tests
> +# We run fdtput to update the device tree, thn fdtget to check it
> +
> +# Usage
> +#    fdtput-runtest.sh name expected_output dtb_file node property flags value
> +
> +. ./tests.sh
> +
> +LOG="tmp.log.$$"
> +EXPECT="tmp.expect.$$"
> +
> +rm -f $TMPFILE $LOG

TMPFILE does not appear to be set here.

> +expect="$1"
> +echo "$expect" >$EXPECT
> +dtb="$2"
> +node="$3"
> +property="$4"
> +flags="$5"
> +shift 5
> +value="$@"
> +
> +# First run fdtput
> +verbose_run $VALGRIND "$DTPUT" "$dtb" "$node" "$property" $value $flags
> +ret="$?"
> +
> +if [ "$ret" -ne 0 -a "$expect" = "ERR" ]; then
> +	PASS
> +fi
> +if [ "$ret" -gt 127 ]; then
> +    signame=$(kill -l $[ret - 128])

$[] bashism again.

> +    FAIL "Killed by SIG$signame"
> +fi
> +
> +# Now fdtget to read the value
> +verbose_run_log "$LOG" $VALGRIND "$DTGET" "$dtb" "$node" "$property" $flags
> +ret="$?"
> +
> +if [ "$ret" -gt 127 ]; then
> +    signame=$(kill -l $[ret - 128])
> +    FAIL "Killed by SIG$signame"
> +fi

So, doing an fdtget to extract the value for checking is one way.  I
would have thought the more obvious way to check results would be to
do a dtbs_ordered_equal or dtbs_unordered_equal on the output.  That
then checks the fdtput behaviour independent of the fdtget behaviour.

[snip]
> +fdtput_tests () {
> +    file=label01.dtb
> +    src=label01.dts
> +
> +    # Create some test files containing useful strings
> +    base=tmp.test0
> +    file1=tmp.test1
> +    file2=tmp.test2
> +    bigfile1=tmp.test3
> +    bigfile2=tmp.test4
> +
> +    # Filter out anything the shell might not like
> +    cat $src | tr -d "'\"\n\;/\.\*{}\-" | tr -s "[:blank:]" " " >$base
> +
> +    # Make two small files
> +    head -5 $base >$file1
> +    cat $file1 | tr a-z A-Z | cut -c10-30 | sort -r >$file2
> +
> +    # and two larger ones
> +    cat $base > $bigfile1
> +    tac $base | tr a-z A-Z | sort -r >$bigfile2

This seems a really convoluted way of just generating some testdata.
And misleading since AFAICT the fact that this testdata is derived
from a dts is not actually relevant in any way.

> +    # Allow just enough space for both file1 and file2
> +    (( space = $(stat -c %s $file1) + $(stat -c %s $file2) ))

Ugh, several bashisms here, and I'm not entirely sure what they are.
I got it not to produce errors with /bin/dash, but it still didn't
seem to work quite right.  In particular spaces around an assignment
won't work in most shells.

> +    $DTC -O dtb -p $space -o $file ${file%.dtb}.dts 2>/dev/null
> +
> +    # run_fdtput_test <test-name> <expected-result> <file> <key> <flags>
> +    #		<args>...
> +    run_fdtput_test "Simple string" "a_model" $file / model -ts "a_model"
> +    run_fdtput_test "Multiple string s" "board1 board2" \
> +	$file / compatible -ts board1 board2
> +    run_fdtput_test "Single string with spaces" "board1 board2" \
> +	$file / compatible -ts "board1 board2"
> +    run_fdtput_test "Integer" "32768" \
> +	$file /cpus/PowerPC,970@1 d-cache-size "" "32768"
> +    run_fdtput_test "Integer hex" "8001" \
> +	$file /cpus/PowerPC,970@1 d-cache-size -tx 0x8001
> +    run_fdtput_test "Integer list" "2 3 12" \
> +	$file /randomnode tricky1 -tbi "02 003 12"
> +    run_fdtput_test "Byte list short" "a b c ea ad be ef" \
> +	$file /randomnode blob -tbx "a b c ea ad be ef"
> +    run_fdtput_test "Integer list short" "a0b0c0d deeaae ef000000" \
> +	$file /randomnode blob -tx "a0b0c0d deeaae ef000000"
> +    run_fdtput_test "Large string list" "`cat $file1 $file2`" \
> +	$file /randomnode blob -ts "`cat $file1`" "`cat $file2`"

So, this test fails for me.  I suspect it is because one of the
bashisms means it isn't executing quite right, but I haven't pinned it
down yet.

-- 
David Gibson			| I'll have my music baroque, and my code
david AT gibson.dropbear.id.au	| minimalist, thank you.  NOT _the_ _other_
				| _way_ _around_!
http://www.ozlabs.org/~dgibson

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2012-01-22 11:23 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2012-01-21 18:14 [PATCH v6 1/2] Add fdtget utility to read property values from a device tree Simon Glass
     [not found] ` <1327169688-7569-2-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
2012-01-21 18:14   ` [PATCH v6 2/2] Add fdtput utility to write property values to " Simon Glass
     [not found]     ` <1327169688-7569-3-git-send-email-sjg-F7+t8E8rja9g9hUCZPvPmw@public.gmane.org>
2012-01-21 21:28       ` Jon Loeliger
2012-01-22 11:23       ` David Gibson
2012-01-21 21:26   ` [PATCH v6 1/2] Add fdtget utility to read property values from " Jon Loeliger
2012-01-22 10:30   ` David Gibson

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).