struct name_entry {
struct list_head node;
char name[PATH_SIZE];
+ unsigned int ignore_error:1;
};
+
extern int log_priority(const char *priority);
-extern char *name_list_add(struct list_head *name_list, const char *name, int sort);
-extern char *name_list_key_add(struct list_head *name_list, const char *key, const char *value);
+extern struct name_entry *name_list_add(struct list_head *name_list, const char *name, int sort);
+extern struct name_entry *name_list_key_add(struct list_head *name_list, const char *key, const char *value);
extern int name_list_key_remove(struct list_head *name_list, const char *key);
extern void name_list_cleanup(struct list_head *name_list);
extern int add_matching_files(struct list_head *name_list, const char *dirname, const char *suffix);
unsetenv(key_name);
info("unset ENV '%s'", key_name);
} else {
- char *key_value = name_list_key_add(&udev->env_list, key_name, temp_value);
+ struct name_entry *entry;
- if (key_value == NULL)
+ entry = name_list_key_add(&udev->env_list, key_name, temp_value);
+ if (entry == NULL)
break;
- putenv(key_value);
- info("set ENV '%s'", key_value);
+ putenv(entry->name);
+ info("set ENV '%s'", entry->name);
}
}
}
}
if (!udev->run_final && rule->run.operation != KEY_OP_UNSET) {
+ struct name_entry *entry;
+
if (rule->run.operation == KEY_OP_ASSIGN_FINAL)
udev->run_final = 1;
if (rule->run.operation == KEY_OP_ASSIGN || rule->run.operation == KEY_OP_ASSIGN_FINAL) {
name_list_cleanup(&udev->run_list);
}
dbg("add run '%s'", key_val(rule, &rule->run));
- name_list_add(&udev->run_list, key_val(rule, &rule->run), 0);
+ entry = name_list_add(&udev->run_list, key_val(rule, &rule->run), 0);
+ if (rule->run_ignore_error)
+ entry->ignore_error = 1;
}
if (rule->last_rule) {
}
if (!udev->run_final && rule->run.operation != KEY_OP_UNSET) {
+ struct name_entry *entry;
+
if (rule->run.operation == KEY_OP_ASSIGN ||
rule->run.operation == KEY_OP_ASSIGN_FINAL) {
info("reset run list");
name_list_cleanup(&udev->run_list);
}
dbg("add run '%s'", key_val(rule, &rule->run));
- name_list_add(&udev->run_list, key_val(rule, &rule->run), 0);
+ entry = name_list_add(&udev->run_list, key_val(rule, &rule->run), 0);
+ if (rule->run_ignore_error)
+ entry->ignore_error = 1;
if (rule->run.operation == KEY_OP_ASSIGN_FINAL)
break;
}
unsigned int link_priority;
unsigned int partitions;
unsigned int last_rule:1,
+ run_ignore_error:1,
ignore_device:1,
ignore_remove:1;
continue;
}
- if (strcasecmp(key, "RUN") == 0) {
+ if (strncasecmp(key, "RUN", sizeof("RUN")-1) == 0) {
+ attr = get_key_attribute(key + sizeof("RUN")-1);
+ if (attr && strstr(attr, "ignore_error"))
+ rule->run_ignore_error = 1;
add_rule_key(rule, &rule->run, operation, value);
valid = 1;
continue;
return 0;
}
-char *name_list_add(struct list_head *name_list, const char *name, int sort)
+struct name_entry *name_list_add(struct list_head *name_list, const char *name, int sort)
{
struct name_entry *loop_name;
struct name_entry *new_name;
/* avoid doubles */
if (strcmp(loop_name->name, name) == 0) {
dbg("'%s' is already in the list", name);
- return loop_name->name;
+ return loop_name;
}
}
dbg("adding '%s'", new_name->name);
list_add_tail(&new_name->node, &loop_name->node);
- return new_name->name;
+ return new_name;
}
-char *name_list_key_add(struct list_head *name_list, const char *key, const char *value)
+struct name_entry *name_list_key_add(struct list_head *name_list, const char *key, const char *value)
{
struct name_entry *loop_name;
struct name_entry *new_name;
dbg("key already present '%s', replace it", loop_name->name);
snprintf(loop_name->name, sizeof(loop_name->name), "%s=%s", key, value);
loop_name->name[sizeof(loop_name->name)-1] = '\0';
- return loop_name->name;
+ return loop_name;
}
}
dbg("adding '%s'", new_name->name);
list_add_tail(&new_name->node, &loop_name->node);
- return new_name->name;
+ return new_name;
}
int name_list_key_remove(struct list_head *name_list, const char *key)
strlcpy(program, name_loop->name, sizeof(program));
udev_rules_apply_format(udev, program, sizeof(program));
if (run_program(program, udev->dev->subsystem, NULL, 0, NULL,
- (udev_log_priority >= LOG_INFO)))
- retval = -1;
+ (udev_log_priority >= LOG_INFO)) != 0)
+ if (!name_loop->ignore_error)
+ retval = -1;
}
}
}
setpriority(PRIO_PROCESS, 0, UDEV_PRIORITY);
retval = udev_event_process(msg);
- info("seq %llu finished", msg->seqnum);
+ info("seq %llu finished with %i", msg->seqnum, retval);
logging_close();
if (retval)