From b3b4e8a7a229cccca915421329a5319f996b0842 Mon Sep 17 00:00:00 2001 From: NeilBrown Date: Wed, 30 Jun 2010 17:20:38 +1000 Subject: [PATCH] Avoid skipping devices where removing all faulty/detached devices. When using 0.90 metadata, devices can be renumbered when earlier devices are removed. So when iterating all devices looking for 'failed' or 'detached' devices, we need to re-check the same slot we checked last time to see if maybe it has a different device now. Reported-by: Jim Paris Resolves-Debian-Bug: 587550 Signed-off-by: NeilBrown --- Manage.c | 23 +++++++++++++++++++---- 1 file changed, 19 insertions(+), 4 deletions(-) diff --git a/Manage.c b/Manage.c index 6bc5d0a..edf41e9 100644 --- a/Manage.c +++ b/Manage.c @@ -376,6 +376,7 @@ int Manage_subdevs(char *devname, int fd, return 1; } + stb.st_rdev = 0; for (dv = devlist, j=0 ; dv; dv = next, j = jnext) { unsigned long long ldsize; char dvname[20]; @@ -394,6 +395,7 @@ int Manage_subdevs(char *devname, int fd, return 1; } for (; j < array.raid_disks + array.nr_disks ; j++) { + int dev; disc.number = j; if (ioctl(fd, GET_DISK_INFO, &disc)) continue; @@ -401,9 +403,15 @@ int Manage_subdevs(char *devname, int fd, continue; if ((disc.state & 1) == 0) /* faulty */ continue; - stb.st_rdev = makedev(disc.major, disc.minor); + dev = makedev(disc.major, disc.minor); + if (stb.st_rdev == dev) + /* already did that one */ + continue; + stb.st_rdev = dev; next = dv; - jnext = j+1; + /* same slot again next time - things might + * have reshuffled */ + jnext = j; sprintf(dvname,"%d:%d", disc.major, disc.minor); dnprintable = dvname; break; @@ -419,6 +427,7 @@ int Manage_subdevs(char *devname, int fd, } for (; j < array.raid_disks + array.nr_disks; j++) { int sfd; + int dev; disc.number = j; if (ioctl(fd, GET_DISK_INFO, &disc)) continue; @@ -435,9 +444,15 @@ int Manage_subdevs(char *devname, int fd, continue; if (errno != ENXIO) continue; - stb.st_rdev = makedev(disc.major, disc.minor); + dev = makedev(disc.major, disc.minor); + if (stb.st_rdev == dev) + /* already did that one */ + continue; + stb.st_rdev = dev; next = dv; - jnext = j+1; + /* same slot again next time - things might + * have reshuffled */ + jnext = j; dnprintable = dvname; break; }