diff options
author | Zdenek Kabelac <zkabelac@redhat.com> | 2017-06-16 13:20:47 +0200 |
---|---|---|
committer | Zdenek Kabelac <zkabelac@redhat.com> | 2017-06-16 17:04:00 +0200 |
commit | 529dcaf6a3c4fea4a15baf13cf057d2333860c05 (patch) | |
tree | 27e69e1ca90b3fc0e003eae97339e3f5649123a3 /libdm/libdm-targets.c | |
parent | 40e0dcf70d5a719671916aa88adf9a8f18e096c6 (diff) | |
download | lvm2-529dcaf6a3c4fea4a15baf13cf057d2333860c05.tar.gz |
libdm: workarounds reported raid status info
Current existing kernels reports status sometimes in weird form.
Instead of showing what is the exact progress, we need to estimate
this in-sync state from several surrounding states.
Main reason here is to never report 100% sync state for a raid device
which will be undergoing i.e. recovery.
Diffstat (limited to 'libdm/libdm-targets.c')
-rw-r--r-- | libdm/libdm-targets.c | 18 |
1 files changed, 18 insertions, 0 deletions
diff --git a/libdm/libdm-targets.c b/libdm/libdm-targets.c index 1709c2b2c..6577f0744 100644 --- a/libdm/libdm-targets.c +++ b/libdm/libdm-targets.c @@ -99,6 +99,7 @@ int dm_get_status_raid(struct dm_pool *mem, const char *params, unsigned num_fields; const char *p, *pp, *msg_fields = ""; struct dm_status_raid *s = NULL; + unsigned a = 0; if ((num_fields = _count_fields(params)) < 4) goto_bad; @@ -168,6 +169,23 @@ int dm_get_status_raid(struct dm_pool *mem, const char *params, out: *status = s; + if (s->insync_regions == s->total_regions) { + /* FIXME: kernel gives misleading info here + * Trying to recognize a true state */ + while (i-- > 0) + if (s->dev_health[i] == 'a') + a++; /* Count number of 'a' */ + + if (a && a < s->dev_count) { + /* SOME legs are in 'a' */ + if (!strcasecmp(s->sync_action, "recover") + || !strcasecmp(s->sync_action, "idle")) + /* Kernel may possibly start some action + * in near-by future, do not report 100% */ + s->insync_regions--; + } + } + return 1; bad: |