udev: introduce enum ResolveNameTiming for --resolve-names argument
authorYu Watanabe <watanabe.yu+github@gmail.com>
Thu, 25 Oct 2018 06:30:51 +0000 (15:30 +0900)
committerYu Watanabe <watanabe.yu+github@gmail.com>
Mon, 12 Nov 2018 14:20:53 +0000 (23:20 +0900)
src/test/test-udev.c
src/udev/udev-rules.c
src/udev/udev.h
src/udev/udevadm-test.c
src/udev/udevd.c

index 102da4a..7c70336 100644 (file)
@@ -84,7 +84,7 @@ int main(int argc, char *argv[]) {
         action = argv[1];
         devpath = argv[2];
 
-        rules = udev_rules_new(1);
+        rules = udev_rules_new(RESOLVE_NAME_EARLY);
 
         const char *syspath = strjoina("/sys", devpath);
         r = device_new_from_synthetic_event(&dev, syspath, action);
index ad4b32a..c8b905a 100644 (file)
@@ -30,6 +30,7 @@
 #include "stat-util.h"
 #include "stdio-util.h"
 #include "strbuf.h"
+#include "string-table.h"
 #include "string-util.h"
 #include "strv.h"
 #include "sysctl-util.h"
@@ -57,7 +58,7 @@ static const char* const rules_dirs[] = {
 
 struct udev_rules {
         usec_t dirs_ts_usec;
-        int resolve_names;
+        ResolveNameTiming resolve_name_timing;
 
         /* every key in the rules file becomes a token */
         struct token *tokens;
@@ -1335,10 +1336,10 @@ static void add_rule(struct udev_rules *rules, char *line,
                         uid = strtoul(value, &endptr, 10);
                         if (endptr[0] == '\0')
                                 rule_add_key(&rule_tmp, TK_A_OWNER_ID, op, NULL, &uid);
-                        else if (rules->resolve_names > 0 && strchr("$%", value[0]) == NULL) {
+                        else if (rules->resolve_name_timing == RESOLVE_NAME_EARLY && strchr("$%", value[0]) == NULL) {
                                 uid = add_uid(rules, value);
                                 rule_add_key(&rule_tmp, TK_A_OWNER_ID, op, NULL, &uid);
-                        } else if (rules->resolve_names >= 0)
+                        } else if (rules->resolve_name_timing != RESOLVE_NAME_NEVER)
                                 rule_add_key(&rule_tmp, TK_A_OWNER, op, value, NULL);
 
                         rule_tmp.rule.rule.can_set_name = true;
@@ -1353,10 +1354,10 @@ static void add_rule(struct udev_rules *rules, char *line,
                         gid = strtoul(value, &endptr, 10);
                         if (endptr[0] == '\0')
                                 rule_add_key(&rule_tmp, TK_A_GROUP_ID, op, NULL, &gid);
-                        else if ((rules->resolve_names > 0) && strchr("$%", value[0]) == NULL) {
+                        else if ((rules->resolve_name_timing == RESOLVE_NAME_EARLY) && strchr("$%", value[0]) == NULL) {
                                 gid = add_gid(rules, value);
                                 rule_add_key(&rule_tmp, TK_A_GROUP_ID, op, NULL, &gid);
-                        } else if (rules->resolve_names >= 0)
+                        } else if (rules->resolve_name_timing != RESOLVE_NAME_NEVER)
                                 rule_add_key(&rule_tmp, TK_A_GROUP, op, value, NULL);
 
                         rule_tmp.rule.rule.can_set_name = true;
@@ -1512,18 +1513,20 @@ static int parse_file(struct udev_rules *rules, const char *filename) {
         return 0;
 }
 
-struct udev_rules *udev_rules_new(int resolve_names) {
+struct udev_rules *udev_rules_new(ResolveNameTiming resolve_name_timing) {
         struct udev_rules *rules;
         struct token end_token;
         char **files, **f;
         int r;
 
+        assert(resolve_name_timing >= 0 && resolve_name_timing < _RESOLVE_NAME_TIMING_MAX);
+
         rules = new(struct udev_rules, 1);
         if (!rules)
                 return NULL;
 
         *rules = (struct udev_rules) {
-                .resolve_names = resolve_names,
+                .resolve_name_timing = resolve_name_timing,
         };
 
         /* init token array and string buffer */
@@ -2598,3 +2601,11 @@ finish:
 
         return 0;
 }
+
+static const char* const resolve_name_timing_table[_RESOLVE_NAME_TIMING_MAX] = {
+        [RESOLVE_NAME_NEVER] = "never",
+        [RESOLVE_NAME_LATE] = "late",
+        [RESOLVE_NAME_EARLY] = "early",
+};
+
+DEFINE_STRING_TABLE_LOOKUP(resolve_name_timing, ResolveNameTiming);
index fb2c681..5c6ca6b 100644 (file)
@@ -48,9 +48,17 @@ struct udev_event {
         bool run_final;
 };
 
+typedef enum ResolveNameTiming {
+        RESOLVE_NAME_NEVER,
+        RESOLVE_NAME_LATE,
+        RESOLVE_NAME_EARLY,
+        _RESOLVE_NAME_TIMING_MAX,
+        _RESOLVE_NAME_TIMING_INVALID = -1,
+} ResolveNameTiming;
+
 /* udev-rules.c */
 struct udev_rules;
-struct udev_rules *udev_rules_new(int resolve_names);
+struct udev_rules *udev_rules_new(ResolveNameTiming resolve_name_timing);
 struct udev_rules *udev_rules_unref(struct udev_rules *rules);
 bool udev_rules_check_timestamp(struct udev_rules *rules);
 int udev_rules_apply_to_event(struct udev_rules *rules, struct udev_event *event,
@@ -58,6 +66,9 @@ int udev_rules_apply_to_event(struct udev_rules *rules, struct udev_event *event
                               Hashmap *properties_list);
 int udev_rules_apply_static_dev_perms(struct udev_rules *rules);
 
+ResolveNameTiming resolve_name_timing_from_string(const char *s) _pure_;
+const char *resolve_name_timing_to_string(ResolveNameTiming i) _const_;
+
 /* udev-event.c */
 struct udev_event *udev_event_new(sd_device *dev, usec_t exec_delay_usec, sd_netlink *rtnl);
 struct udev_event *udev_event_free(struct udev_event *event);
index cfaaf03..dd0fc4f 100644 (file)
@@ -22,7 +22,7 @@
 #include "udevadm.h"
 
 static const char *arg_action = "add";
-static int arg_resolve_names = 1;
+static ResolveNameTiming arg_resolve_name_timing = RESOLVE_NAME_EARLY;
 static char arg_syspath[UTIL_PATH_SIZE] = {};
 
 static int help(void) {
@@ -55,14 +55,9 @@ static int parse_argv(int argc, char *argv[]) {
                         arg_action = optarg;
                         break;
                 case 'N':
-                        if (streq (optarg, "early")) {
-                                arg_resolve_names = 1;
-                        } else if (streq (optarg, "late")) {
-                                arg_resolve_names = 0;
-                        } else if (streq (optarg, "never")) {
-                                arg_resolve_names = -1;
-                        } else {
-                                log_error("resolve-names must be early, late or never");
+                        arg_resolve_name_timing = resolve_name_timing_from_string(optarg);
+                        if (arg_resolve_name_timing < 0) {
+                                log_error("--resolve-names= must be early, late or never");
                                 return -EINVAL;
                         }
                         break;
@@ -115,7 +110,7 @@ int test_main(int argc, char *argv[], void *userdata) {
 
         udev_builtin_init();
 
-        rules = udev_rules_new(arg_resolve_names);
+        rules = udev_rules_new(arg_resolve_name_timing);
         if (!rules) {
                 log_error("Failed to read udev rules.");
                 r = -ENOMEM;
index c97e873..4f93ec4 100644 (file)
@@ -61,7 +61,7 @@
 
 static bool arg_debug = false;
 static int arg_daemonize = false;
-static int arg_resolve_names = 1;
+static ResolveNameTiming arg_resolve_name_timing = RESOLVE_NAME_EARLY;
 static unsigned arg_children_max = 0;
 static usec_t arg_exec_delay_usec = 0;
 static usec_t arg_event_timeout_usec = 180 * USEC_PER_SEC;
@@ -851,7 +851,7 @@ static void event_queue_start(Manager *manager) {
         udev_builtin_init();
 
         if (!manager->rules) {
-                manager->rules = udev_rules_new(arg_resolve_names);
+                manager->rules = udev_rules_new(arg_resolve_name_timing);
                 if (!manager->rules)
                         return;
         }
@@ -1565,18 +1565,16 @@ static int parse_argv(int argc, char *argv[]) {
                 case 'D':
                         arg_debug = true;
                         break;
-                case 'N':
-                        if (streq(optarg, "early")) {
-                                arg_resolve_names = 1;
-                        } else if (streq(optarg, "late")) {
-                                arg_resolve_names = 0;
-                        } else if (streq(optarg, "never")) {
-                                arg_resolve_names = -1;
-                        } else {
-                                log_error("resolve-names must be early, late or never");
-                                return 0;
-                        }
+                case 'N': {
+                        ResolveNameTiming t;
+
+                        t = resolve_name_timing_from_string(optarg);
+                        if (t < 0)
+                                log_warning("Invalid --resolve-names= value '%s', ignoring.", optarg);
+                        else
+                                arg_resolve_name_timing = t;
                         break;
+                }
                 case 'h':
                         return help();
                 case 'V':
@@ -1611,7 +1609,7 @@ static int manager_new(Manager **ret, int fd_ctrl, int fd_uevent, const char *cg
 
         udev_builtin_init();
 
-        manager->rules = udev_rules_new(arg_resolve_names);
+        manager->rules = udev_rules_new(arg_resolve_name_timing);
         if (!manager->rules)
                 return log_error_errno(ENOMEM, "error reading rules");