summaryrefslogtreecommitdiffstats
path: root/sysfs.c
diff options
context:
space:
mode:
authorDan Williams <dan.j.williams@intel.com>2009-02-24 18:45:56 -0700
committerDan Williams <dan.j.williams@intel.com>2009-02-24 18:45:56 -0700
commitdab4a5134e8d946f3809163af6abb80a945c904c (patch)
tree74c51faa30b739d3449d00b691295332efffa747 /sysfs.c
parentdb575f3b9ebfdf0d7ac8dd5f9b1d4b4d0e446e80 (diff)
downloadmdadm-dab4a5134e8d946f3809163af6abb80a945c904c.tar.gz
mdadm-dab4a5134e8d946f3809163af6abb80a945c904c.tar.xz
mdadm-dab4a5134e8d946f3809163af6abb80a945c904c.zip
sysfs: allow sysfs_read to detect and drop removed disks
All operations that rely on loading from an existing container (like --add) will fail after a disk has been removed. Provide an option to skip missing / offline disks rather than abort. We attempt to do this in the load_super_{imsm,ddf}_all cases when mdmon is running i.e. we already have a consitent version of the metadata running in the system. Otherwise, we fail as normal and let the administrator fix up the container. Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Diffstat (limited to 'sysfs.c')
-rw-r--r--sysfs.c26
1 files changed, 21 insertions, 5 deletions
diff --git a/sysfs.c b/sysfs.c
index b9fd3da..2dad7d3 100644
--- a/sysfs.c
+++ b/sysfs.c
@@ -272,18 +272,34 @@ struct mdinfo *sysfs_read(int fd, int devnum, unsigned long options)
}
}
- dev->next = sra->devs;
- sra->devs = dev;
-
strcpy(dev->sys_name, de->d_name);
dev->disk.raid_disk = strtoul(buf, &ep, 10);
if (*ep) dev->disk.raid_disk = -1;
strcpy(dbase, "block/dev");
- if (load_sys(fname, buf))
- goto abort;
+ if (load_sys(fname, buf)) {
+ free(dev);
+ if (options & SKIP_GONE_DEVS)
+ continue;
+ else
+ goto abort;
+ }
sscanf(buf, "%d:%d", &dev->disk.major, &dev->disk.minor);
+ /* special case check for block devices that can go 'offline' */
+ if (options & SKIP_GONE_DEVS) {
+ strcpy(dbase, "block/device/state");
+ if (load_sys(fname, buf) == 0 &&
+ strncmp(buf, "offline", 7) == 0) {
+ free(dev);
+ continue;
+ }
+ }
+
+ /* finally add this disk to the array */
+ dev->next = sra->devs;
+ sra->devs = dev;
+
if (options & GET_OFFSET) {
strcpy(dbase, "offset");
if (load_sys(fname, buf))