]> git.ipfire.org Git - thirdparty/mdadm.git/commitdiff
Get failed disk count from array state
authorTomasz Majchrzak <tomasz.majchrzak@intel.com>
Wed, 31 May 2017 10:46:57 +0000 (12:46 +0200)
committerJes Sorensen <jsorensen@fb.com>
Mon, 5 Jun 2017 15:11:36 +0000 (11:11 -0400)
Recent commit has changed the way failed disks are counted. It breaks
recovery for external metadata arrays as failed disks are not part of
the array and have no corresponding entries is sysfs (they are only
reported for containers) so degraded arrays show no failed disks.

Recent commit overwrites GET_DEGRADED result prior to GET_STATE and it
is not set again if GET_STATE has not been requested. As GET_STATE
provides the same information as GET_DEGRADED, the latter is not needed
anymore. Remove GET_DEGRADED option and replace it with GET_STATE
option.

Don't count number of failed disks looking at sysfs entries but
calculate it at the end. Do it only for arrays as containers report
no disks, just spares.

Signed-off-by: Tomasz Majchrzak <tomasz.majchrzak@intel.com>
Signed-off-by: Jes Sorensen <jsorensen@fb.com>
Incremental.c
Monitor.c
managemon.c
mdadm.h
raid6check.c
sysfs.c

index 30dc7a2fd82ba58d78bf899851f3af68dc6eacea..6cf217420e8e0e01c8a9e18a6751db322b96bf18 100644 (file)
@@ -886,16 +886,10 @@ static int array_try_spare(char *devname, int *dfdp, struct dev_policy *pol,
                }
                sra = sysfs_read(-1, mp->devnm,
                                 GET_DEVS|GET_OFFSET|GET_SIZE|GET_STATE|
                }
                sra = sysfs_read(-1, mp->devnm,
                                 GET_DEVS|GET_OFFSET|GET_SIZE|GET_STATE|
-                                GET_DEGRADED|GET_COMPONENT|GET_VERSION);
-               if (!sra) {
-                       /* Probably a container - no degraded info */
-                       sra = sysfs_read(-1, mp->devnm,
-                                        GET_DEVS|GET_OFFSET|GET_SIZE|GET_STATE|
-                                        GET_COMPONENT|GET_VERSION);
-                       if (sra)
-                               sra->array.failed_disks = -1;
-               }
-               if (!sra)
+                                GET_COMPONENT|GET_VERSION);
+               if (sra)
+                       sra->array.failed_disks = -1;
+               else
                        continue;
                if (st == NULL) {
                        int i;
                        continue;
                if (st == NULL) {
                        int i;
index 725f47db564e87f4afb4c3cd5cb0f5469034239a..bef2f1be4469b7c2a7a079fe66d8d79ed6d852c2 100644 (file)
--- a/Monitor.c
+++ b/Monitor.c
@@ -485,8 +485,8 @@ static int check_array(struct state *st, struct mdstat_ent *mdstat,
        if (st->devnm[0] == 0)
                strcpy(st->devnm, fd2devnm(fd));
 
        if (st->devnm[0] == 0)
                strcpy(st->devnm, fd2devnm(fd));
 
-       sra = sysfs_read(-1, st->devnm, GET_LEVEL | GET_DISKS | GET_DEGRADED |
-                        GET_MISMATCH | GET_DEVS | GET_STATE);
+       sra = sysfs_read(-1, st->devnm, GET_LEVEL | GET_DISKS | GET_MISMATCH |
+                        GET_DEVS | GET_STATE);
        if (!sra)
                goto disappeared;
 
        if (!sra)
                goto disappeared;
 
index a8df6664cb464ec1a9987fce95a59cdb045a1448..68f0c2d3f1a5873b8ecd9bf084afd6695002eac3 100644 (file)
@@ -685,8 +685,8 @@ static void manage_new(struct mdstat_ent *mdstat,
 
        mdi = sysfs_read(-1, mdstat->devnm,
                         GET_LEVEL|GET_CHUNK|GET_DISKS|GET_COMPONENT|
 
        mdi = sysfs_read(-1, mdstat->devnm,
                         GET_LEVEL|GET_CHUNK|GET_DISKS|GET_COMPONENT|
-                        GET_DEGRADED|GET_SAFEMODE|
-                        GET_DEVS|GET_OFFSET|GET_SIZE|GET_STATE|GET_LAYOUT);
+                        GET_SAFEMODE|GET_DEVS|GET_OFFSET|GET_SIZE|GET_STATE|
+                        GET_LAYOUT);
 
        if (!mdi)
                return;
 
        if (!mdi)
                return;
diff --git a/mdadm.h b/mdadm.h
index ec0a39e8b6e7051bed8551e56aff37d552b80139..ee9b8373ac253c1aa9fbe32d292bcff8c94d4887 100644 (file)
--- a/mdadm.h
+++ b/mdadm.h
@@ -637,7 +637,6 @@ enum sysfs_read_flags {
        GET_MISMATCH    = (1 << 5),
        GET_VERSION     = (1 << 6),
        GET_DISKS       = (1 << 7),
        GET_MISMATCH    = (1 << 5),
        GET_VERSION     = (1 << 6),
        GET_DISKS       = (1 << 7),
-       GET_DEGRADED    = (1 << 8),
        GET_SAFEMODE    = (1 << 9),
        GET_BITMAP_LOCATION = (1 << 10),
 
        GET_SAFEMODE    = (1 << 9),
        GET_BITMAP_LOCATION = (1 << 10),
 
index 551f8355bd69d45275ba443695883838e94f5870..a8e6005bc1be5f6936cd4242b0921156578390b3 100644 (file)
@@ -562,7 +562,7 @@ int main(int argc, char *argv[])
                          GET_LEVEL|
                          GET_LAYOUT|
                          GET_DISKS|
                          GET_LEVEL|
                          GET_LAYOUT|
                          GET_DISKS|
-                         GET_DEGRADED |
+                         GET_STATE |
                          GET_COMPONENT|
                          GET_CHUNK|
                          GET_DEVS|
                          GET_COMPONENT|
                          GET_CHUNK|
                          GET_DEVS|
diff --git a/sysfs.c b/sysfs.c
index e47f5e483cdd9423a9e8dc899270985778958f81..78d2b5264db119858c601824f44f047847b864e8 100644 (file)
--- a/sysfs.c
+++ b/sysfs.c
@@ -162,18 +162,12 @@ struct mdinfo *sysfs_read(int fd, char *devnm, unsigned long options)
                        goto abort;
                sra->array.layout = strtoul(buf, NULL, 0);
        }
                        goto abort;
                sra->array.layout = strtoul(buf, NULL, 0);
        }
-       if (options & GET_DISKS) {
+       if (options & (GET_DISKS|GET_STATE)) {
                strcpy(base, "raid_disks");
                if (load_sys(fname, buf, sizeof(buf)))
                        goto abort;
                sra->array.raid_disks = strtoul(buf, NULL, 0);
        }
                strcpy(base, "raid_disks");
                if (load_sys(fname, buf, sizeof(buf)))
                        goto abort;
                sra->array.raid_disks = strtoul(buf, NULL, 0);
        }
-       if (options & GET_DEGRADED) {
-               strcpy(base, "degraded");
-               if (load_sys(fname, buf, sizeof(buf)))
-                       goto abort;
-               sra->array.failed_disks = strtoul(buf, NULL, 0);
-       }
        if (options & GET_COMPONENT) {
                strcpy(base, "component_size");
                if (load_sys(fname, buf, sizeof(buf)))
        if (options & GET_COMPONENT) {
                strcpy(base, "component_size");
                if (load_sys(fname, buf, sizeof(buf)))
@@ -359,10 +353,9 @@ struct mdinfo *sysfs_read(int fd, char *devnm, unsigned long options)
                        strcpy(dbase, "state");
                        if (load_sys(fname, buf, sizeof(buf)))
                                goto abort;
                        strcpy(dbase, "state");
                        if (load_sys(fname, buf, sizeof(buf)))
                                goto abort;
-                       if (strstr(buf, "faulty")) {
+                       if (strstr(buf, "faulty"))
                                dev->disk.state |= (1<<MD_DISK_FAULTY);
                                dev->disk.state |= (1<<MD_DISK_FAULTY);
-                               sra->array.failed_disks++;
-                       } else {
+                       else {
                                sra->array.working_disks++;
                                if (strstr(buf, "in_sync")) {
                                        dev->disk.state |= (1<<MD_DISK_SYNC);
                                sra->array.working_disks++;
                                if (strstr(buf, "in_sync")) {
                                        dev->disk.state |= (1<<MD_DISK_SYNC);
@@ -379,6 +372,11 @@ struct mdinfo *sysfs_read(int fd, char *devnm, unsigned long options)
                        dev->errors = strtoul(buf, NULL, 0);
                }
        }
                        dev->errors = strtoul(buf, NULL, 0);
                }
        }
+
+       if ((options & GET_STATE) && sra->array.raid_disks)
+               sra->array.failed_disks = sra->array.raid_disks -
+                       sra->array.active_disks - sra->array.spare_disks;
+
        closedir(dir);
        return sra;
 
        closedir(dir);
        return sra;