dump_systemstate: Allow extra programs to be turned on/off based on a cmdline flag 83/226283/5
authorKarol Lewandowski <k.lewandowsk@samsung.com>
Fri, 28 Feb 2020 10:25:01 +0000 (11:25 +0100)
committerKarol Lewandowski <k.lewandowsk@samsung.com>
Tue, 3 Mar 2020 08:23:33 +0000 (09:23 +0100)
Change-Id: I287c46d5286e622c58d772b8063e62f66db82e51

src/dump_systemstate/dump_systemstate.c
src/dump_systemstate/extras.c
src/dump_systemstate/extras.h

index c4e56fe..e3824d5 100644 (file)
@@ -177,7 +177,7 @@ int main(int argc, char *argv[])
        fprintf_fd(out_fd, "\n");
 
        if (arg_extras)
-               exit_code |= handle_extra_dir(out_fd, DUMP_SYSTEMSTATE_CONFIG_DIR_FILES_PATH, handle_extra_file);
+               exit_code |= handle_extra_dir(out_fd, DUMP_SYSTEMSTATE_CONFIG_DIR_FILES_PATH, handle_extra_file, argc, argv);
 
 #define spawn_wait_checked(av, env) \
        do { \
@@ -259,7 +259,7 @@ int main(int argc, char *argv[])
        }
 
        if (arg_extras)
-               exit_code |= handle_extra_dir(out_fd, DUMP_SYSTEMSTATE_CONFIG_DIR_PROGRAMS_PATH, handle_extra_program);
+               exit_code |= handle_extra_dir(out_fd, DUMP_SYSTEMSTATE_CONFIG_DIR_PROGRAMS_PATH, handle_extra_program, argc, argv);
 
 #undef spawn_wait_checked
 
index 2e6939c..2d8fcb9 100644 (file)
@@ -49,6 +49,7 @@ enum ini_fields {
        INI_FIELD_PATH,
        INI_FIELD_ARGS,
        INI_FIELD_ENV,
+       INI_FIELD_FLAG,
        COUNT_INI_FIELDS,
 };
 
@@ -57,15 +58,36 @@ static const char *const INI_KEYS[COUNT_INI_FIELDS] = {
        [INI_FIELD_PATH]  = "path",
        [INI_FIELD_ARGS]  = "args",
        [INI_FIELD_ENV]   = "env",
+       [INI_FIELD_FLAG]  = "cmdflag",
 };
-static const size_t MAX_INI_KEY_LEN = 5;
+static const size_t MAX_INI_KEY_LEN = 7;
 
 struct extra_dump_item {
        // not separate named fields, for convenient iteration
        const char *fields[COUNT_INI_FIELDS];
 };
 
-int handle_extra_program(int out_fd, struct extra_dump_item *item)
+bool check_cmdflag(const char *const flag, int argc, char **argv)
+{
+       if (!flag)
+               return true;
+
+       for (int i = 1; i < argc; i++) {
+               char *p = argv[i];
+               if (*p != '-')
+                       continue;
+               for (++p; *p; p++) {
+                       if (*p == '-')
+                               break;
+                       if (*p == flag[0])
+                               return true;
+               }
+       }
+
+       return false;
+}
+
+int handle_extra_program(int out_fd, struct extra_dump_item *item, int argc, char **argv)
 {
        assert(out_fd >= 0);
        assert(item);
@@ -74,6 +96,10 @@ int handle_extra_program(int out_fd, struct extra_dump_item *item)
        const char *const path  = item->fields[INI_FIELD_PATH];
        const char *const args  = item->fields[INI_FIELD_ARGS] ?: "";
        const char *const env   = item->fields[INI_FIELD_ENV] ?: "";
+       const char *const flag  = item->fields[INI_FIELD_FLAG];
+
+       if (!check_cmdflag(flag, argc, argv))
+               return 0;
 
        if (!title || !path) {
                fprintf_fd(out_fd, "\nNo title or path in extra program config");
@@ -94,17 +120,17 @@ int handle_extra_program(int out_fd, struct extra_dump_item *item)
         * an array of char pointers. Splitting isn't trivial (consider a brutal set
         * of arguments using " or `) and I don't want to reinvent the wheel so I'm
         * delegating the splitting to the shell. */
-       char *argv[] = {"/bin/sh", "-c", command_line, NULL};
+       char *av[] = {"/bin/sh", "-c", command_line, NULL};
 
        int err;
        spawn_param_s param = { .fn = spawn_setstdout, .u.int_val = out_fd };
-       bool failed = !spawn_wait(argv, NULL, &param, DEFAULT_COMMAND_TIMEOUT_MS, &err) || err != 0;
+       bool failed = !spawn_wait(av, NULL, &param, DEFAULT_COMMAND_TIMEOUT_MS, &err) || err != 0;
 
        free(command_line);
        return failed ? EXIT_CMDERR : 0;
 }
 
-int handle_extra_file(int out_fd, struct extra_dump_item *item)
+int handle_extra_file(int out_fd, struct extra_dump_item *item, int argc, char **argv)
 {
        assert(out_fd >= 0);
        assert(item);
@@ -125,9 +151,9 @@ int handle_extra_file(int out_fd, struct extra_dump_item *item)
        return 0;
 }
 
-typedef int (*handle_ini_section_t)(int out_fd, struct extra_dump_item *);
+typedef int (*handle_ini_section_t)(int out_fd, struct extra_dump_item *, int argc, char **argv);
 
-static int handle_ini_Nth_section(int out_fd, const dictionary *ini, int n, handle_ini_section_t handle_ini_section)
+static int handle_ini_Nth_section(int out_fd, const dictionary *ini, int n, handle_ini_section_t handle_ini_section, int argc, char **argv)
 {
        assert(out_fd >= 0);
        assert(ini);
@@ -150,10 +176,10 @@ static int handle_ini_Nth_section(int out_fd, const dictionary *ini, int n, hand
                item.fields[i] = iniparser_getstring(ini, key_buf, NULL);
        }
 
-       return handle_ini_section(out_fd, &item);
+       return handle_ini_section(out_fd, &item, argc, argv);
 }
 
-static int handle_extra_ini(int out_fd, const char *ini_path, handle_ini_section_t handle_ini_section)
+static int handle_extra_ini(int out_fd, const char *ini_path, handle_ini_section_t handle_ini_section, int argc, char **argv)
 {
        assert(out_fd >= 0);
        assert(ini_path);
@@ -170,7 +196,7 @@ static int handle_extra_ini(int out_fd, const char *ini_path, handle_ini_section
 
        int ret = 0;
        for (int i = 0; i < nsec; ++i)
-               ret |= handle_ini_Nth_section(out_fd, ini, i, handle_ini_section);
+               ret |= handle_ini_Nth_section(out_fd, ini, i, handle_ini_section, argc, argv);
        return ret;
 }
 
@@ -180,7 +206,7 @@ static int config_entry_filter(const struct dirent *de)
        return de->d_type == DT_REG && string_ends_with(de->d_name, ".conf");
 }
 
-int handle_extra_dir(int out_fd, char *dir_path, handle_ini_section_t handle_ini_section)
+int handle_extra_dir(int out_fd, char *dir_path, handle_ini_section_t handle_ini_section, int argc, char **argv)
 {
        assert(out_fd >= 0);
        assert(dir_path);
@@ -212,7 +238,7 @@ int handle_extra_dir(int out_fd, char *dir_path, handle_ini_section_t handle_ini
                snprintf(ini_path, sizeof ini_path, "%s/%s", dir_path, de->d_name);
                free(de);
 
-               ret |= handle_extra_ini(out_fd, ini_path, handle_ini_section);
+               ret |= handle_extra_ini(out_fd, ini_path, handle_ini_section, argc, argv);
        }
        free(entries);
        close(dir_fd);
index c6d78de..392bff0 100644 (file)
@@ -27,9 +27,9 @@
 
 struct extra_dump_item;
 
-typedef int (*handle_ini_section_t)(int out_fd, struct extra_dump_item *);
+typedef int (*handle_ini_section_t)(int out_fd, struct extra_dump_item *, int argc, char **argv);
 
-int handle_extra_dir(int out_fd, char *dir_path, handle_ini_section_t handle_ini_section);
-int handle_extra_file(int out_fd, struct extra_dump_item *item);
-int handle_extra_program(int out_fd, struct extra_dump_item *item);
+int handle_extra_dir(int out_fd, char *dir_path, handle_ini_section_t handle_ini_section, int argc, char **argv);
+int handle_extra_file(int out_fd, struct extra_dump_item *item, int argc, char **argv);
+int handle_extra_program(int out_fd, struct extra_dump_item *item, int argc, char **argv);