From ea97dc3792642fa8187a339cc258f9a5a7df4523 Mon Sep 17 00:00:00 2001 From: Kay Sievers Date: Tue, 20 May 2008 15:02:17 +0200 Subject: [PATCH] rename WAIT_FOR_SYSFS to WAIT_FOR and accept an absolute path This allows us to watch any file to appear, not only sysfs attributes. Files without a leading slash will be device sysfs attributes. The key WAIT_FOR_SYSFS still works for backwards compat, but is removed from the man page. --- udev.7 | 4 ++-- udev.xml | 5 ++--- udev_rules.c | 42 +++++++++++++++++++++++++----------------- udev_rules.h | 2 +- udev_rules_parse.c | 6 +++--- 5 files changed, 33 insertions(+), 26 deletions(-) diff --git a/udev.7 b/udev.7 index 79e61ea9f..a09bdf9ec 100644 --- a/udev.7 +++ b/udev.7 @@ -257,9 +257,9 @@ and based on the executable bit of the file permissions\. .RE .PP -\fBWAIT_FOR_SYSFS\fR +\fBWAIT_FOR\fR .RS 4 -Wait for the specified sysfs file of the device to be created\. Can be used to fight against kernel sysfs timing issues\. +Wait for a file to become available\. .RE .PP \fBOPTIONS\fR diff --git a/udev.xml b/udev.xml index 184457aa6..a7422e1ca 100644 --- a/udev.xml +++ b/udev.xml @@ -394,10 +394,9 @@ - + - Wait for the specified sysfs file of the device to be created. Can be used - to fight against kernel sysfs timing issues. + Wait for a file to become available. diff --git a/udev_rules.c b/udev_rules.c index f4ee11a56..a102e2da5 100644 --- a/udev_rules.c +++ b/udev_rules.c @@ -528,35 +528,40 @@ int udev_rules_run(struct udevice *udev) } #define WAIT_LOOP_PER_SECOND 50 -static int wait_for_sysfs(struct udevice *udev, const char *file, int timeout) +static int wait_for_file(struct udevice *udev, const char *file, int timeout) { - char devicepath[PATH_SIZE]; char filepath[PATH_SIZE]; + char devicepath[PATH_SIZE] = ""; struct stat stats; int loop = timeout * WAIT_LOOP_PER_SECOND; - strlcpy(devicepath, sysfs_path, sizeof(devicepath)); - strlcat(devicepath, udev->dev->devpath, sizeof(devicepath)); - strlcpy(filepath, devicepath, sizeof(filepath)); - strlcat(filepath, "/", sizeof(filepath)); - strlcat(filepath, file, sizeof(filepath)); + /* a relative path is a device attribute */ + if (file[0] != '/') { + strlcpy(devicepath, sysfs_path, sizeof(devicepath)); + strlcat(devicepath, udev->dev->devpath, sizeof(devicepath)); - dbg("will wait %i sec for '%s'\n", timeout, filepath); + strlcpy(filepath, devicepath, sizeof(filepath)); + strlcat(filepath, "/", sizeof(filepath)); + strlcat(filepath, file, sizeof(filepath)); + file = filepath; + } + + dbg("will wait %i sec for '%s'\n", timeout, file); while (--loop) { /* lookup file */ - if (stat(filepath, &stats) == 0) { - info("file '%s' appeared after %i loops\n", filepath, (timeout * WAIT_LOOP_PER_SECOND) - loop-1); + if (stat(file, &stats) == 0) { + info("file '%s' appeared after %i loops\n", file, (timeout * WAIT_LOOP_PER_SECOND) - loop-1); return 0; } /* make sure, the device did not disappear in the meantime */ - if (stat(devicepath, &stats) != 0) { - info("device disappeared while waiting for '%s'\n", filepath); + if (devicepath[0] != '\0' && stat(devicepath, &stats) != 0) { + info("device disappeared while waiting for '%s'\n", file); return -2; } - info("wait for '%s' for %i mseconds\n", filepath, 1000 / WAIT_LOOP_PER_SECOND); + info("wait for '%s' for %i mseconds\n", file, 1000 / WAIT_LOOP_PER_SECOND); usleep(1000 * 1000 / WAIT_LOOP_PER_SECOND); } - info("waiting for '%s' failed\n", filepath); + info("waiting for '%s' failed\n", file); return -1; } @@ -1110,11 +1115,14 @@ static int match_rule(struct udevice *udev, struct udev_rule *rule) dbg("TEST key is true\n"); } - if (rule->wait_for_sysfs.operation != KEY_OP_UNSET) { + if (rule->wait_for.operation != KEY_OP_UNSET) { + char filename[PATH_SIZE]; int found; - found = (wait_for_sysfs(udev, key_val(rule, &rule->wait_for_sysfs), 10) == 0); - if (!found && (rule->wait_for_sysfs.operation != KEY_OP_NOMATCH)) + strlcpy(filename, key_val(rule, &rule->wait_for), sizeof(filename)); + udev_rules_apply_format(udev, filename, sizeof(filename)); + found = (wait_for_file(udev, filename, 10) == 0); + if (!found && (rule->wait_for.operation != KEY_OP_NOMATCH)) goto nomatch; } diff --git a/udev_rules.h b/udev_rules.h index da5ac3ea1..fe0f9dfbb 100644 --- a/udev_rules.h +++ b/udev_rules.h @@ -84,7 +84,7 @@ struct udev_rule { struct key test; mode_t test_mode_mask; struct key run; - struct key wait_for_sysfs; + struct key wait_for; struct key label; struct key goto_label; diff --git a/udev_rules_parse.c b/udev_rules_parse.c index 5119b7e84..bdaf55bd4 100644 --- a/udev_rules_parse.c +++ b/udev_rules_parse.c @@ -495,8 +495,8 @@ static int add_to_rules(struct udev_rules *rules, char *line, const char *filena continue; } - if (strcasecmp(key, "WAIT_FOR_SYSFS") == 0) { - add_rule_key(rule, &rule->wait_for_sysfs, operation, value); + if (strcasecmp(key, "WAIT_FOR") == 0 || strcasecmp(key, "WAIT_FOR_SYSFS") == 0) { + add_rule_key(rule, &rule->wait_for, operation, value); valid = 1; continue; } @@ -629,7 +629,7 @@ static int add_to_rules(struct udev_rules *rules, char *line, const char *filena err("unknown key '%s' in %s:%u\n", key, filename, lineno); } - if (physdev && rule->wait_for_sysfs.operation == KEY_OP_UNSET) + if (physdev && rule->wait_for.operation == KEY_OP_UNSET) err("PHYSDEV* values are deprecated and will be removed from a future kernel, \n" "please fix it in %s:%u", filename, lineno); -- 2.30.2