The branch, master has been updated
       via  963a639101f ctdb-tests: Add tests for cmdline_add() api
       via  e469d6c1191 ctdb-common: Add api to add new section/commands to 
cmdline
       via  977a6f7fad8 ctdb-common: Change cmdline implementation to support 
multiple sections
       via  7a008c6b74e ctdb-tests: Update cmdline tests for section name
       via  b2b24c91fae ctdb-common: Add section to group commands in cmdline
       via  29948d7b1eb ctdb-common: Generate usage message from cmdline_parse()
      from  0361a26e395 libcli:auth Check return code of 
netlogon_creds_aes_encrypt()

https://git.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 963a639101f4c55467e33667a698fffb350a931f
Author: Amitay Isaacs <[email protected]>
Date:   Mon Nov 11 18:32:49 2019 +1100

    ctdb-tests: Add tests for cmdline_add() api
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>
    
    Autobuild-User(master): Martin Schwenke <[email protected]>
    Autobuild-Date(master): Thu Nov 14 12:03:46 UTC 2019 on sn-devel-184

commit e469d6c1191ab9fa78e1ced6d7aa7b37dce7c5a9
Author: Amitay Isaacs <[email protected]>
Date:   Mon Nov 11 17:32:50 2019 +1100

    ctdb-common: Add api to add new section/commands to cmdline
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 977a6f7fad8d2985e8e898bd8dc7d3d376164e9d
Author: Amitay Isaacs <[email protected]>
Date:   Mon Nov 11 17:29:26 2019 +1100

    ctdb-common: Change cmdline implementation to support multiple sections
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 7a008c6b74e559a3e677257be3ea57a5821e3e9c
Author: Amitay Isaacs <[email protected]>
Date:   Mon Nov 11 17:05:53 2019 +1100

    ctdb-tests: Update cmdline tests for section name
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit b2b24c91fae30edf797ed30e3c45c259aee00853
Author: Amitay Isaacs <[email protected]>
Date:   Mon Nov 11 17:01:43 2019 +1100

    ctdb-common: Add section to group commands in cmdline
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 29948d7b1eb1337c7e3d91dc53bb3e1e42de6dd3
Author: Amitay Isaacs <[email protected]>
Date:   Mon Jul 9 15:37:52 2018 +1000

    ctdb-common: Generate usage message from cmdline_parse()
    
    If any of the option parsing or command parsing fails, generate usage
    message.
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

-----------------------------------------------------------------------

Summary of changes:
 ctdb/common/cmdline.c                     | 168 ++++++++++++++++++++++--------
 ctdb/common/cmdline.h                     |  15 +++
 ctdb/common/conf_tool.c                   |   7 +-
 ctdb/common/path_tool.c                   |   7 +-
 ctdb/event/event_tool.c                   |   1 +
 ctdb/tests/UNIT/cunit/cmdline_test_001.sh |  42 +++++++-
 ctdb/tests/src/cmdline_test.c             | 161 +++++++++++++++++++++++++---
 ctdb/tests/src/db_test_tool.c             |   1 +
 8 files changed, 339 insertions(+), 63 deletions(-)


Changeset truncated at 500 lines:

diff --git a/ctdb/common/cmdline.c b/ctdb/common/cmdline.c
index f3768c068fe..fc4cb22f066 100644
--- a/ctdb/common/cmdline.c
+++ b/ctdb/common/cmdline.c
@@ -29,10 +29,16 @@
 
 #define CMDLINE_MAX_LEN                80
 
+struct cmdline_section {
+       const char *name;
+       struct cmdline_command *commands;
+};
+
 struct cmdline_context {
        const char *prog;
        struct poptOption *options;
-       struct cmdline_command *commands;
+       struct cmdline_section *section;
+       int num_sections;
        int max_len;
        poptContext pc;
        int argc, arg0;
@@ -206,15 +212,51 @@ static bool cmdline_commands_check(struct cmdline_command 
*commands,
 
 static int cmdline_context_destructor(struct cmdline_context *cmdline);
 
+static int cmdline_section_add(struct cmdline_context *cmdline,
+                              const char *name,
+                              struct cmdline_command *commands)
+{
+       struct cmdline_section *section;
+       size_t max_len = 0;
+       bool ok;
+
+       ok = cmdline_commands_check(commands, &max_len);
+       if (!ok) {
+               return EINVAL;
+       }
+
+       section = talloc_realloc(cmdline,
+                                cmdline->section,
+                                struct cmdline_section,
+                                cmdline->num_sections + 1);
+       if (section == NULL) {
+               return ENOMEM;
+       }
+
+       section[cmdline->num_sections] = (struct cmdline_section) {
+               .name = name,
+               .commands = commands,
+       };
+
+       if (max_len > cmdline->max_len) {
+               cmdline->max_len = max_len;
+       }
+
+       cmdline->section = section;
+       cmdline->num_sections += 1;
+
+       return 0;
+}
+
 int cmdline_init(TALLOC_CTX *mem_ctx,
                 const char *prog,
                 struct poptOption *options,
+                const char *name,
                 struct cmdline_command *commands,
                 struct cmdline_context **result)
 {
        struct cmdline_context *cmdline;
        int ret;
-       size_t max_len = 0;
        bool ok;
 
        if (prog == NULL) {
@@ -226,11 +268,6 @@ int cmdline_init(TALLOC_CTX *mem_ctx,
                return EINVAL;
        }
 
-       ok = cmdline_commands_check(commands, &max_len);
-       if (!ok) {
-               return EINVAL;
-       }
-
        cmdline = talloc_zero(mem_ctx, struct  cmdline_context);
        if (cmdline == NULL) {
                return ENOMEM;
@@ -247,8 +284,12 @@ int cmdline_init(TALLOC_CTX *mem_ctx,
                talloc_free(cmdline);
                return ret;
        }
-       cmdline->commands = commands;
-       cmdline->max_len = max_len;
+
+       ret = cmdline_section_add(cmdline, name, commands);
+       if (ret != 0) {
+               talloc_free(cmdline);
+               return ret;
+       }
 
        cmdline->argc = 1;
        cmdline->argv = talloc_array(cmdline, const char *, 2);
@@ -285,6 +326,13 @@ static int cmdline_context_destructor(struct 
cmdline_context *cmdline)
        return 0;
 }
 
+int cmdline_add(struct cmdline_context *cmdline,
+               const char *name,
+               struct cmdline_command *commands)
+{
+       return cmdline_section_add(cmdline, name, commands);
+}
+
 static int cmdline_parse_options(struct cmdline_context *cmdline,
                                 int argc,
                                 const char **argv)
@@ -323,16 +371,12 @@ static int cmdline_parse_options(struct cmdline_context 
*cmdline,
        return 0;
 }
 
-static int cmdline_match(struct cmdline_context *cmdline)
+static int cmdline_match_section(struct cmdline_context *cmdline,
+                                struct cmdline_section *section)
 {
        int i;
 
-       if (cmdline->argc == 0 || cmdline->argv == NULL) {
-               cmdline->match_cmd = NULL;
-               return EINVAL;
-       }
-
-       for (i=0; cmdline->commands[i].name != NULL; i++) {
+       for (i=0; section->commands[i].name != NULL; i++) {
                struct cmdline_command *cmd;
                char name[CMDLINE_MAX_LEN+1];
                size_t len;
@@ -340,7 +384,7 @@ static int cmdline_match(struct cmdline_context *cmdline)
                int n = 0;
                bool match = false;
 
-               cmd = &cmdline->commands[i];
+               cmd = &section->commands[i];
                len = strlcpy(name, cmd->name, sizeof(name));
                if (len >= sizeof(name)) {
                        D_ERR("Skipping long command '%s'\n", cmd->name);
@@ -379,6 +423,25 @@ static int cmdline_match(struct cmdline_context *cmdline)
        return ENOENT;
 }
 
+static int cmdline_match(struct cmdline_context *cmdline)
+{
+       int i, ret = ENOENT;
+
+       if (cmdline->argc == 0 || cmdline->argv == NULL) {
+               cmdline->match_cmd = NULL;
+               return EINVAL;
+       }
+
+       for (i=0; i<cmdline->num_sections; i++) {
+               ret = cmdline_match_section(cmdline, &cmdline->section[i]);
+               if (ret == 0) {
+                       break;
+               }
+       }
+
+       return ret;
+}
+
 int cmdline_parse(struct cmdline_context *cmdline,
                  int argc,
                  const char **argv,
@@ -387,6 +450,7 @@ int cmdline_parse(struct cmdline_context *cmdline,
        int ret;
 
        if (argc < 2) {
+               cmdline_usage(cmdline, NULL);
                return EINVAL;
        }
 
@@ -395,6 +459,7 @@ int cmdline_parse(struct cmdline_context *cmdline,
        if (parse_options) {
                ret = cmdline_parse_options(cmdline, argc, argv);
                if (ret != 0) {
+                       cmdline_usage(cmdline, NULL);
                        return ret;
                }
        } else {
@@ -403,11 +468,22 @@ int cmdline_parse(struct cmdline_context *cmdline,
        }
 
        ret = cmdline_match(cmdline);
-       if (!cmdline_show_help && ret != 0) {
-               return ret;
+
+       if (ret != 0 || cmdline_show_help) {
+               const char *name = NULL;
+
+               if (cmdline->match_cmd != NULL) {
+                       name = cmdline->match_cmd->name;
+               }
+
+               cmdline_usage(cmdline, name);
+
+               if (cmdline_show_help) {
+                       ret = EAGAIN;
+               }
        }
 
-       return 0;
+       return ret;
 }
 
 static void cmdline_usage_command(struct cmdline_context *cmdline,
@@ -429,6 +505,23 @@ static void cmdline_usage_command(struct cmdline_context 
*cmdline,
        printf("     %s\n", cmd->msg_help);
 }
 
+static void cmdline_usage_section(struct cmdline_context *cmdline,
+                                 struct cmdline_section *section)
+{
+       int i;
+
+       printf("\n");
+
+       if (section->name != NULL) {
+               printf("%s ", section->name);
+       }
+       printf("Commands:\n");
+       for (i=0; section->commands[i].name != NULL; i++) {
+               cmdline_usage_command(cmdline, &section->commands[i], true);
+
+       }
+}
+
 static void cmdline_usage_full(struct cmdline_context *cmdline)
 {
        int i;
@@ -436,27 +529,29 @@ static void cmdline_usage_full(struct cmdline_context 
*cmdline)
        poptSetOtherOptionHelp(cmdline->pc, "[<options>] <command> [<args>]");
        poptPrintHelp(cmdline->pc, stdout, 0);
 
-       printf("\nCommands:\n");
-       for (i=0; cmdline->commands[i].name != NULL; i++) {
-               cmdline_usage_command(cmdline, &cmdline->commands[i], true);
-
+       for (i=0; i<cmdline->num_sections; i++) {
+               cmdline_usage_section(cmdline, &cmdline->section[i]);
        }
 }
 
 void cmdline_usage(struct cmdline_context *cmdline, const char *cmd_name)
 {
        struct cmdline_command *cmd = NULL;
-       int i;
+       int i, j;
 
        if (cmd_name == NULL) {
                cmdline_usage_full(cmdline);
                return;
        }
 
-       for (i=0; cmdline->commands[i].name != NULL; i++) {
-               if (strcmp(cmdline->commands[i].name, cmd_name) == 0) {
-                       cmd = &cmdline->commands[i];
-                       break;
+       for (j=0; j<cmdline->num_sections; j++) {
+               struct cmdline_section *section = &cmdline->section[j];
+
+               for (i=0; section->commands[i].name != NULL; i++) {
+                       if (strcmp(section->commands[i].name, cmd_name) == 0) {
+                               cmd = &section->commands[i];
+                               break;
+                       }
                }
        }
 
@@ -480,21 +575,6 @@ int cmdline_run(struct cmdline_context *cmdline,
        TALLOC_CTX *tmp_ctx;
        int ret;
 
-       if (cmdline_show_help) {
-               const char *name = NULL;
-
-               if (cmd != NULL) {
-                       name = cmdline->match_cmd->name;
-               }
-
-               cmdline_usage(cmdline, name);
-
-               if (result != NULL) {
-                       *result = 0;
-               }
-               return EAGAIN;
-       }
-
        if (cmd == NULL) {
                return ENOENT;
        }
diff --git a/ctdb/common/cmdline.h b/ctdb/common/cmdline.h
index 1e11c66c76e..b9a128c2cc4 100644
--- a/ctdb/common/cmdline.h
+++ b/ctdb/common/cmdline.h
@@ -85,6 +85,7 @@ struct cmdline_command {
  * @param[in] mem_ctx Talloc memory context
  * @param[in] prog Program name
  * @param[in] options Command-line options
+ * @param[in] section Name of section grouping specified commands
  * @param[in] commands Commands array
  * @param[out] result New cmdline context
  * @return 0 on success, errno on failure
@@ -94,9 +95,23 @@ struct cmdline_command {
 int cmdline_init(TALLOC_CTX *mem_ctx,
                 const char *prog,
                 struct poptOption *options,
+                const char *section,
                 struct cmdline_command *commands,
                 struct cmdline_context **result);
 
+
+/**
+ * @brief Add command line section/commands
+ *
+ * @param[in] cmdline Cmdline context
+ * @param[in] section Name of section grouping specified commands
+ * @param[in] commands Commands array
+ * @return 0 on success, errno on failure
+ */
+int cmdline_add(struct cmdline_context *cmdline,
+               const char *section,
+               struct cmdline_command *commands);
+
 /**
  * @brief Parse command line options and commands/arguments
  *
diff --git a/ctdb/common/conf_tool.c b/ctdb/common/conf_tool.c
index 8e0753eb787..2d0543d643e 100644
--- a/ctdb/common/conf_tool.c
+++ b/ctdb/common/conf_tool.c
@@ -205,7 +205,12 @@ int conf_tool_init(TALLOC_CTX *mem_ctx,
                return ENOMEM;
        }
 
-       ret = cmdline_init(ctx, prog, options, conf_commands, &ctx->cmdline);
+       ret = cmdline_init(ctx,
+                          prog,
+                          options,
+                          NULL,
+                          conf_commands,
+                          &ctx->cmdline);
        if (ret != 0) {
                D_ERR("Failed to initialize cmdline, ret=%d\n", ret);
                talloc_free(ctx);
diff --git a/ctdb/common/path_tool.c b/ctdb/common/path_tool.c
index a19afa9b0c3..44d29b6b00f 100644
--- a/ctdb/common/path_tool.c
+++ b/ctdb/common/path_tool.c
@@ -315,7 +315,12 @@ int path_tool_init(TALLOC_CTX *mem_ctx,
                return ENOMEM;
        }
 
-       ret = cmdline_init(ctx, prog, options, path_commands, &ctx->cmdline);
+       ret = cmdline_init(ctx,
+                          prog,
+                          options,
+                          NULL,
+                          path_commands,
+                          &ctx->cmdline);
        if (ret != 0) {
                D_ERR("Failed to initialize cmdline, ret=%d\n", ret);
                talloc_free(ctx);
diff --git a/ctdb/event/event_tool.c b/ctdb/event/event_tool.c
index 9c95e6d9553..46dc25e6c30 100644
--- a/ctdb/event/event_tool.c
+++ b/ctdb/event/event_tool.c
@@ -699,6 +699,7 @@ int event_tool_init(TALLOC_CTX *mem_ctx,
        ret = cmdline_init(mem_ctx,
                           prog,
                           options,
+                          NULL,
                           event_commands,
                           &ctx->cmdline);
        if (ret != 0) {
diff --git a/ctdb/tests/UNIT/cunit/cmdline_test_001.sh 
b/ctdb/tests/UNIT/cunit/cmdline_test_001.sh
index 527b1143e7e..e95900087ec 100755
--- a/ctdb/tests/UNIT/cunit/cmdline_test_001.sh
+++ b/ctdb/tests/UNIT/cunit/cmdline_test_001.sh
@@ -46,7 +46,23 @@ Usage: test5 [<options>] <command> [<args>]
 Help Options:
   -h, --help     Show this help message
 
-Commands:
+Action Commands:
+  action one      action one help
+  action two      action two help
+Usage: test5 [<options>] <command> [<args>]
+
+Help Options:
+  -h, --help     Show this help message
+
+Action Commands:
+  action one      action one help
+  action two      action two help
+Usage: test5 [<options>] <command> [<args>]
+
+Help Options:
+  -h, --help     Show this help message
+
+Action Commands:
   action one      action one help
   action two      action two help
 EOF
@@ -56,3 +72,27 @@ ok <<EOF
 arg1
 EOF
 unit_test cmdline_test 6
+
+ok <<EOF
+Usage: test7 [<options>] <command> [<args>]
+
+Help Options:
+  -h, --help     Show this help message
+
+Basic Commands:
+  cmd1      command one help
+  cmd2      command two help
+
+Advanced Commands:
+  cmd3      command three help
+  cmd4      command four help
+
+Ultimate Commands:
+  cmd5      command five help
+  cmd6      command six help
+
+one
+three
+six
+EOF
+unit_test cmdline_test 7
diff --git a/ctdb/tests/src/cmdline_test.c b/ctdb/tests/src/cmdline_test.c
index 8f5b6028fe4..916d820553b 100644
--- a/ctdb/tests/src/cmdline_test.c
+++ b/ctdb/tests/src/cmdline_test.c
@@ -51,13 +51,18 @@ static void test1(void)
        mem_ctx = talloc_new(NULL);
        assert(mem_ctx != NULL);
 
-       ret = cmdline_init(mem_ctx, NULL, NULL, NULL, &cmdline);
+       ret = cmdline_init(mem_ctx, NULL, NULL, NULL, NULL, &cmdline);
        assert(ret == EINVAL);
 
-       ret = cmdline_init(mem_ctx, "test1", NULL, NULL, &cmdline);
+       ret = cmdline_init(mem_ctx, "test1", NULL, NULL, NULL, &cmdline);
        assert(ret == EINVAL);
 
-       ret = cmdline_init(mem_ctx, "test1", dummy_options, NULL, &cmdline);
+       ret = cmdline_init(mem_ctx,
+                          "test1",
+                          dummy_options,
+                          NULL,
+                          NULL,
+                          &cmdline);
        assert(ret == EINVAL);
 
        talloc_free(mem_ctx);
@@ -102,19 +107,44 @@ static void test2(void)
        mem_ctx = talloc_new(NULL);
        assert(mem_ctx != NULL);
 
-       ret = cmdline_init(mem_ctx, "test2", NULL, test2_nofunc, &cmdline);
+       ret = cmdline_init(mem_ctx,
+                          "test2",
+                          NULL,
+                          NULL,
+                          test2_nofunc,
+                          &cmdline);
        assert(ret == EINVAL);
 
-       ret = cmdline_init(mem_ctx, "test2", NULL, test2_nohelp, &cmdline);
+       ret = cmdline_init(mem_ctx,
+                          "test2",
+                          NULL,
+                          NULL,
+                          test2_nohelp,
+                          &cmdline);
        assert(ret == EINVAL);
 
-       ret = cmdline_init(mem_ctx, "test2", NULL, test2_long, &cmdline);
+       ret = cmdline_init(mem_ctx,
+                          "test2",
+                          NULL,
+                          NULL,
+                          test2_long,
+                          &cmdline);
        assert(ret == EINVAL);
 
-       ret = cmdline_init(mem_ctx, "test2", NULL, test2_longhelp, &cmdline);
+       ret = cmdline_init(mem_ctx,
+                          "test2",
+                          NULL,


-- 
Samba Shared Repository

Reply via email to