diff options
author | Jonathan Brassow <jbrassow@redhat.com> | 2008-02-07 21:11:39 -0500 |
---|---|---|
committer | Alasdair G Kergon <agk@redhat.com> | 2008-02-07 21:11:39 -0500 |
commit | af195ac82e38ba802fd86b5a014ed05ef6dd88bb (patch) | |
tree | 661e5848dd970f6213cbcf181818f234cef2c571 /drivers/md/dm-raid1.c | |
parent | 06386bbfd2441416875d0403d405c56822f6ebac (diff) |
dm raid1: report fault status
This patch adds extra information to the mirror status output, so that
it can be determined which device(s) have failed. For each mirror device,
a character is printed indicating the most severe error encountered. The
characters are:
* A => Alive - No failures
* D => Dead - A write failure occurred leaving mirror out-of-sync
* S => Sync - A sychronization failure occurred, mirror out-of-sync
* R => Read - A read failure occurred, mirror data unaffected
This allows userspace to properly reconfigure the mirror set.
Signed-off-by: Jonathan Brassow <jbrassow@redhat.com>
Signed-off-by: Alasdair G Kergon <agk@redhat.com>
Diffstat (limited to 'drivers/md/dm-raid1.c')
-rw-r--r-- | drivers/md/dm-raid1.c | 44 |
1 files changed, 36 insertions, 8 deletions
diff --git a/drivers/md/dm-raid1.c b/drivers/md/dm-raid1.c index 38efa7071dd7..edc057f5cdcc 100644 --- a/drivers/md/dm-raid1.c +++ b/drivers/md/dm-raid1.c | |||
@@ -1781,29 +1781,57 @@ static void mirror_resume(struct dm_target *ti) | |||
1781 | rh_start_recovery(&ms->rh); | 1781 | rh_start_recovery(&ms->rh); |
1782 | } | 1782 | } |
1783 | 1783 | ||
1784 | /* | ||
1785 | * device_status_char | ||
1786 | * @m: mirror device/leg we want the status of | ||
1787 | * | ||
1788 | * We return one character representing the most severe error | ||
1789 | * we have encountered. | ||
1790 | * A => Alive - No failures | ||
1791 | * D => Dead - A write failure occurred leaving mirror out-of-sync | ||
1792 | * S => Sync - A sychronization failure occurred, mirror out-of-sync | ||
1793 | * R => Read - A read failure occurred, mirror data unaffected | ||
1794 | * | ||
1795 | * Returns: <char> | ||
1796 | */ | ||
1797 | static char device_status_char(struct mirror *m) | ||
1798 | { | ||
1799 | if (!atomic_read(&(m->error_count))) | ||
1800 | return 'A'; | ||
1801 | |||
1802 | return (test_bit(DM_RAID1_WRITE_ERROR, &(m->error_type))) ? 'D' : | ||
1803 | (test_bit(DM_RAID1_SYNC_ERROR, &(m->error_type))) ? 'S' : | ||
1804 | (test_bit(DM_RAID1_READ_ERROR, &(m->error_type))) ? 'R' : 'U'; | ||
1805 | } | ||
1806 | |||
1807 | |||
1784 | static int mirror_status(struct dm_target *ti, status_type_t type, | 1808 | static int mirror_status(struct dm_target *ti, status_type_t type, |
1785 | char *result, unsigned int maxlen) | 1809 | char *result, unsigned int maxlen) |
1786 | { | 1810 | { |
1787 | unsigned int m, sz = 0; | 1811 | unsigned int m, sz = 0; |
1788 | struct mirror_set *ms = (struct mirror_set *) ti->private; | 1812 | struct mirror_set *ms = (struct mirror_set *) ti->private; |
1813 | struct dirty_log *log = ms->rh.log; | ||
1814 | char buffer[ms->nr_mirrors + 1]; | ||
1789 | 1815 | ||
1790 | switch (type) { | 1816 | switch (type) { |
1791 | case STATUSTYPE_INFO: | 1817 | case STATUSTYPE_INFO: |
1792 | DMEMIT("%d ", ms->nr_mirrors); | 1818 | DMEMIT("%d ", ms->nr_mirrors); |
1793 | for (m = 0; m < ms->nr_mirrors; m++) | 1819 | for (m = 0; m < ms->nr_mirrors; m++) { |
1794 | DMEMIT("%s ", ms->mirror[m].dev->name); | 1820 | DMEMIT("%s ", ms->mirror[m].dev->name); |
1821 | buffer[m] = device_status_char(&(ms->mirror[m])); | ||
1822 | } | ||
1823 | buffer[m] = '\0'; | ||
1795 | 1824 | ||
1796 | DMEMIT("%llu/%llu 0 ", | 1825 | DMEMIT("%llu/%llu 1 %s ", |
1797 | (unsigned long long)ms->rh.log->type-> | 1826 | (unsigned long long)log->type->get_sync_count(ms->rh.log), |
1798 | get_sync_count(ms->rh.log), | 1827 | (unsigned long long)ms->nr_regions, buffer); |
1799 | (unsigned long long)ms->nr_regions); | ||
1800 | 1828 | ||
1801 | sz += ms->rh.log->type->status(ms->rh.log, type, result+sz, maxlen-sz); | 1829 | sz += log->type->status(ms->rh.log, type, result+sz, maxlen-sz); |
1802 | 1830 | ||
1803 | break; | 1831 | break; |
1804 | 1832 | ||
1805 | case STATUSTYPE_TABLE: | 1833 | case STATUSTYPE_TABLE: |
1806 | sz = ms->rh.log->type->status(ms->rh.log, type, result, maxlen); | 1834 | sz = log->type->status(ms->rh.log, type, result, maxlen); |
1807 | 1835 | ||
1808 | DMEMIT("%d", ms->nr_mirrors); | 1836 | DMEMIT("%d", ms->nr_mirrors); |
1809 | for (m = 0; m < ms->nr_mirrors; m++) | 1837 | for (m = 0; m < ms->nr_mirrors; m++) |
@@ -1819,7 +1847,7 @@ static int mirror_status(struct dm_target *ti, status_type_t type, | |||
1819 | 1847 | ||
1820 | static struct target_type mirror_target = { | 1848 | static struct target_type mirror_target = { |
1821 | .name = "mirror", | 1849 | .name = "mirror", |
1822 | .version = {1, 0, 3}, | 1850 | .version = {1, 0, 20}, |
1823 | .module = THIS_MODULE, | 1851 | .module = THIS_MODULE, |
1824 | .ctr = mirror_ctr, | 1852 | .ctr = mirror_ctr, |
1825 | .dtr = mirror_dtr, | 1853 | .dtr = mirror_dtr, |