]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
udev-node: add random delay on conflict in updating device node symlink
authorYu Watanabe <watanabe.yu+github@gmail.com>
Tue, 31 Aug 2021 19:34:48 +0000 (04:34 +0900)
committerYu Watanabe <watanabe.yu+github@gmail.com>
Thu, 2 Sep 2021 00:06:24 +0000 (09:06 +0900)
To make multiple workers not update the same device node symlink
simultaneously.

src/udev/udev-node.c

index 2e7df899e4e5b55304fca387d92e8f44c1f8633e..675e6ce3134de8736103ae831541e3de94af1a10 100644 (file)
 #include "mkdir.h"
 #include "parse-util.h"
 #include "path-util.h"
+#include "random-util.h"
 #include "selinux-util.h"
 #include "smack-util.h"
 #include "stat-util.h"
 #include "stdio-util.h"
 #include "string-util.h"
 #include "strxcpyx.h"
+#include "time-util.h"
 #include "udev-node.h"
 #include "user-util.h"
 
@@ -33,6 +35,8 @@
 #define LINK_UPDATE_MAX_RETRIES        128
 #define CREATE_STACK_LINK_MAX_RETRIES  128
 #define UPDATE_TIMESTAMP_MAX_RETRIES   128
+#define MAX_RANDOM_DELAY (250 * USEC_PER_MSEC)
+#define MIN_RANDOM_DELAY ( 50 * USEC_PER_MSEC)
 #define UDEV_NODE_HASH_KEY SD_ID128_MAKE(b9,6a,f1,ce,40,31,44,1a,9e,19,ec,8b,ae,f3,e3,2f)
 
 static int create_symlink(const char *target, const char *slink) {
@@ -447,6 +451,14 @@ static int link_update(sd_device *dev, const char *slink_in, bool add) {
                 _cleanup_free_ char *target = NULL;
                 struct stat st1 = {}, st2 = {};
 
+                if (i > 0) {
+                        usec_t delay = MIN_RANDOM_DELAY + random_u64_range(MAX_RANDOM_DELAY - MIN_RANDOM_DELAY);
+
+                        log_device_debug(dev, "Directory %s was updated, retrying to update devlink %s after %s.",
+                                         dirname, slink, FORMAT_TIMESPAN(delay, USEC_PER_MSEC));
+                        (void) usleep(delay);
+                }
+
                 if (stat(dirname, &st1) < 0 && errno != ENOENT)
                         return log_device_debug_errno(dev, errno, "Failed to stat %s: %m", dirname);