Re: [PATCH] fdtput: add delete node and property function

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]



Hi Wang,

On 13 January 2015 at 19:53, Wang Long <long.wanglong@xxxxxxxxxx> wrote:
> add the delete node and property function for fdtput.
>
> usage:
> 1) delete a node
>  # fdtput test.dtb -d node /chosen/son
> 2) delete a property
>  # fdtput test.dtb -d prop /chosen/ prop_name

This is a great addition!

I know David is keen on single character flags. But would it be better
to have a separate delete option, e.g.

-r to remove a node
-d to delete a property

>
> Signed-off-by: Wang Long <long.wanglong@xxxxxxxxxx>
> ---
>  fdtput.c           | 94 ++++++++++++++++++++++++++++++++++++++++++++++++++++--
>  tests/run_tests.sh | 17 ++++++++++
>  2 files changed, 108 insertions(+), 3 deletions(-)
>
> diff --git a/fdtput.c b/fdtput.c
> index 2a8d674..28e1f55 100644
> --- a/fdtput.c
> +++ b/fdtput.c
> @@ -32,6 +32,8 @@
>  enum oper_type {
>         OPER_WRITE_PROP,                /* Write a property in a node */
>         OPER_CREATE_NODE,               /* Create a new node */
> +       OPER_DELETE_NODE,               /* Delete a node */
> +       OPER_DELETE_PROP,               /* Delete a property in a node */
>  };
>
>  struct display_info {
> @@ -270,6 +272,60 @@ static int create_node(char **blob, const char *node_name)
>         return 0;
>  }
>
> +/**
> + * Delete a property of a node in the fdt.
> + *
> + * @param blob         FDT blob to write into
> + * @param node_name    Name of node which the delete property belongs to
> + * @param prop_name    Name of property to delete
> + * @return 0 on success, or -1 on failure
> + */
> +static int delete_prop(char **blob, const char *node_name, const char *prop_name)

Can you just pass char *blob? Why the double pointer? Same with the
next function.

> +{
> +       int node = 0;
> +
> +       node = fdt_path_offset(*blob, node_name);
> +       if (node < 0) {
> +               report_error(node_name, -1, node);
> +               return -1;
> +       }
> +
> +       node = fdt_delprop(*blob, node, prop_name);
> +
> +       if (node < 0) {
> +               report_error(node_name, -1, node);
> +               return -1;
> +       }
> +
> +       return 0;
> +}
> +
> +/**
> + * Delete a node in the fdt.
> + *
> + * @param blob         FDT blob to write into
> + * @param node_name    Name of node to delete
> + * @return the delete node offset if found, or -1 on failure
> + */
> +static int delete_node(char **blob, const char *node_name)
> +{
> +       int node = 0;
> +
> +       node = fdt_path_offset(*blob, node_name);
> +       if (node < 0) {
> +               report_error(node_name, -1, node);
> +               return -1;
> +       }
> +
> +       node = fdt_del_node(*blob, node);
> +       if (node < 0) {
> +               report_error(node_name, -1, node);
> +               return -1;
> +       }
> +
> +       return 0;
> +}
> +
>  static int do_fdtput(struct display_info *disp, const char *filename,
>                     char **arg, int arg_count)
>  {
> @@ -302,6 +358,13 @@ static int do_fdtput(struct display_info *disp, const char *filename,
>                                 ret = create_node(&blob, *arg);
>                 }
>                 break;
> +       case OPER_DELETE_NODE:
> +               for (; ret >= 0 && arg_count--; arg++)
> +                       ret = delete_node(&blob, *arg);
> +               break;
> +       case OPER_DELETE_PROP:
> +               ret = delete_prop(&blob, *arg, arg[1]);
> +               break;
>         }
>         if (ret >= 0) {
>                 fdt_pack(blob);
> @@ -312,17 +375,29 @@ static int do_fdtput(struct display_info *disp, const char *filename,
>         return ret;
>  }
>
> +/*
> + * This is a usage message fragment for the -d option.
> + *
> + */
> +#define USAGE_DELETE_MSG \
> +        "<delete>  node, prop\n" \
> +       "\t  node: delete node\n" \
> +       "\t  prop: delete property\n"
> +
>  /* Usage related data. */
>  static const char usage_synopsis[] =
>         "write a property value to a device tree\n"
>         "       fdtput <options> <dt file> <node> <property> [<value>...]\n"
>         "       fdtput -c <options> <dt file> [<node>...]\n"
> +       "       fdtput -d <options> <dt file> <node> <property>\n"
>         "\n"
>         "The command line arguments are joined together into a single value.\n"
> -       USAGE_TYPE_MSG;
> -static const char usage_short_opts[] = "cpt:v" USAGE_COMMON_SHORT_OPTS;
> +       USAGE_DELETE_MSG
> +       USAGE_TYPE_MSG
> +static const char usage_short_opts[] = "cd:pt:v" USAGE_COMMON_SHORT_OPTS;
>  static struct option const usage_long_opts[] = {
>         {"create",           no_argument, NULL, 'c'},
> +       {"delete",            a_argument, NULL, 'd'},
>         {"auto-path",        no_argument, NULL, 'p'},
>         {"type",              a_argument, NULL, 't'},
>         {"verbose",          no_argument, NULL, 'v'},
> @@ -330,6 +405,7 @@ static struct option const usage_long_opts[] = {
>  };
>  static const char * const usage_opts_help[] = {
>         "Create nodes if they don't already exist",
> +       "Delete nodes or property if they already exist",
>         "Automatically create nodes as needed for the node path",
>         "Type of data",
>         "Display each value decoded from command line",
> @@ -348,7 +424,6 @@ int main(int argc, char *argv[])
>         while ((opt = util_getopt_long()) != EOF) {
>                 /*
>                  * TODO: add options to:
> -                * - delete property
>                  * - delete node (optionally recursively)
>                  * - rename node
>                  * - pack fdt before writing
> @@ -360,6 +435,14 @@ int main(int argc, char *argv[])
>                 case 'c':
>                         disp.oper = OPER_CREATE_NODE;
>                         break;
> +               case 'd':
> +                       if (strcmp(optarg, "node") == 0)
> +                               disp.oper = OPER_DELETE_NODE;
> +                       else if (strcmp(optarg, "prop") == 0)
> +                               disp.oper = OPER_DELETE_PROP;
> +                       else
> +                               usage("Invalid delete string");
> +                       break;
>                 case 'p':
>                         disp.auto_path = 1;
>                         break;
> @@ -390,6 +473,11 @@ int main(int argc, char *argv[])
>                         usage("missing property");
>         }
>
> +       if (disp.oper == OPER_DELETE_NODE || disp.oper == OPER_DELETE_PROP) {
> +               if (argc < 1)
> +                       usage("missing node or property");
> +       }
> +
>         if (do_fdtput(&disp, filename, argv, argc))
>                 return 1;
>         return 0;
> diff --git a/tests/run_tests.sh b/tests/run_tests.sh
> index ace6e4f..f633e62 100755
> --- a/tests/run_tests.sh
> +++ b/tests/run_tests.sh
> @@ -610,6 +610,23 @@ fdtput_tests () {
>      run_wrap_test $DTPUT $dtb -cp /chosen
>      run_wrap_test $DTPUT $dtb -cp /chosen/son
>
> +    # Start again with a fresh dtb
> +    run_dtc_test -O dtb -p $(stat -c %s $text) -o $dtb $dts

Do you need to do this?

> +
> +    # Node delete
> +    run_wrap_test $DTPUT $dtb -c /chosen/son /chosen/daughter

These tests seems sufficient, but a few ideas:

Perhaps here you could list the node properties to make sure the node
has been created?

> +    run_wrap_test $DTPUT $dtb -d node  /chosen/son /chosen/daughter
> +
> +    # Delete the not exist node
> +    run_wrap_error_test $DTPUT $dtb -d node  /not/exist/node
> +
> +    # Property delete
> +    run_fdtput_test "eva" $dtb /chosen/ name "" -ts "eva"
> +    run_wrap_test $DTPUT $dtb -d prop /chosen/ name

Here you could list the properties to make suere there is none?

> +
> +    # Delete the not exist property

nit: s/not exist/non-existent/

> +    run_wrap_error_test $DTPUT $dtb -d prop  /chosen   notexistprop
> +
>      # TODO: Add tests for verbose mode?
>  }
>
> --

Regards,
Simon
--
To unsubscribe from this list: send the line "unsubscribe devicetree-compiler" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html



[Index of Archives]     [Device Tree]     [Device Tree Spec]     [Linux Driver Backports]     [Video for Linux]     [Linux USB Devel]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Yosemite Backpacking]

  Powered by Linux