summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNeilBrown <neilb@suse.de>2013-06-25 15:56:22 +1000
committerNeilBrown <neilb@suse.de>2013-06-25 15:56:22 +1000
commit399e0b9709311bebde461c57f5622be68e15c6a0 (patch)
treee00b0f607125cb1b21869aa16fc1baf23fefec7b
parent8010806baba901e6e903ba4167c0ed88bf6e1294 (diff)
Subject: Make wait_for and open_dev_excl faster
When we crete or assemble an array, we wait for udev to create the device file in /dev so that as soon as mdadm complete, the device can be used. This waiting is performed in multiples of 200ms, which can sometimes be too long to wait. So change to an exponential backoff. Wait 1, then 2, then 4 msec etc. Once we get to 256msec, stop backing off and continue waiting 256ms at a time until we reach the limit which is now 4.608sec rather than 5sec which it was before. Ditto for open_dev_excl. Signed-off-by: NeilBrown <neilb@suse.de>
-rw-r--r--util.c10
1 files changed, 8 insertions, 2 deletions
diff --git a/util.c b/util.c
index 90b63eb3..a9aaea48 100644
--- a/util.c
+++ b/util.c
@@ -962,6 +962,7 @@ int open_dev_excl(char *devnm)
int i;
int flags = O_RDWR;
int devid = devnm2devid(devnm);
+ long delay = 1000;
sprintf(buf, "%d:%d", major(devid), minor(devid));
for (i = 0 ; i < 25 ; i++) {
@@ -974,7 +975,9 @@ int open_dev_excl(char *devnm)
}
if (errno != EBUSY)
return fd;
- usleep(200000);
+ usleep(delay);
+ if (delay < 200000)
+ delay *= 2;
}
return -1;
}
@@ -997,6 +1000,7 @@ void wait_for(char *dev, int fd)
{
int i;
struct stat stb_want;
+ long delay = 1000;
if (fstat(fd, &stb_want) != 0 ||
(stb_want.st_mode & S_IFMT) != S_IFBLK)
@@ -1008,7 +1012,9 @@ void wait_for(char *dev, int fd)
(stb.st_mode & S_IFMT) == S_IFBLK &&
(stb.st_rdev == stb_want.st_rdev))
return;
- usleep(200000);
+ usleep(delay);
+ if (delay < 200000)
+ delay *= 2;
}
if (i == 25)
dprintf("%s: timeout waiting for %s\n", __func__, dev);