DDF: ddf_set_disk: move status logic to separate function
Moved code to determine RAID status to a separate function get_bvd_status(). I need this to account for secondary RAID level. Signed-off-by: Martin Wilck <mwilck@arcor.de> Signed-off-by: NeilBrown <neilb@suse.de>
This commit is contained in:
parent
baba3f4e81
commit
5ec636b7ad
94
super-ddf.c
94
super-ddf.c
|
@ -1515,7 +1515,7 @@ bad:
|
|||
}
|
||||
#endif
|
||||
|
||||
static int find_phys(struct ddf_super *ddf, __u32 phys_refnum)
|
||||
static int find_phys(const struct ddf_super *ddf, __u32 phys_refnum)
|
||||
{
|
||||
/* Find the entry in phys_disk which has the given refnum
|
||||
* and return it's index
|
||||
|
@ -3812,9 +3812,55 @@ static int ddf_set_array_state(struct active_array *a, int consistent)
|
|||
return consistent;
|
||||
}
|
||||
|
||||
#define container_of(ptr, type, member) ({ \
|
||||
const typeof( ((type *)0)->member ) *__mptr = (ptr); \
|
||||
(type *)( (char *)__mptr - offsetof(type,member) );})
|
||||
static int get_bvd_state(const struct ddf_super *ddf,
|
||||
const struct vd_config *vc)
|
||||
{
|
||||
unsigned int i, n_bvd, working = 0;
|
||||
unsigned int n_prim = __be16_to_cpu(vc->prim_elmnt_count);
|
||||
int pd, st, state;
|
||||
for (i = 0; i < n_prim; i++) {
|
||||
if (!find_index_in_bvd(ddf, vc, i, &n_bvd))
|
||||
continue;
|
||||
pd = find_phys(ddf, vc->phys_refnum[n_bvd]);
|
||||
if (pd < 0)
|
||||
continue;
|
||||
st = __be16_to_cpu(ddf->phys->entries[pd].state);
|
||||
if ((st & (DDF_Online|DDF_Failed|DDF_Rebuilding))
|
||||
== DDF_Online)
|
||||
working++;
|
||||
}
|
||||
|
||||
state = DDF_state_degraded;
|
||||
if (working == n_prim)
|
||||
state = DDF_state_optimal;
|
||||
else
|
||||
switch (vc->prl) {
|
||||
case DDF_RAID0:
|
||||
case DDF_CONCAT:
|
||||
case DDF_JBOD:
|
||||
state = DDF_state_failed;
|
||||
break;
|
||||
case DDF_RAID1:
|
||||
if (working == 0)
|
||||
state = DDF_state_failed;
|
||||
else if (working >= 2)
|
||||
state = DDF_state_part_optimal;
|
||||
break;
|
||||
case DDF_RAID4:
|
||||
case DDF_RAID5:
|
||||
if (working < n_prim - 1)
|
||||
state = DDF_state_failed;
|
||||
break;
|
||||
case DDF_RAID6:
|
||||
if (working < n_prim - 2)
|
||||
state = DDF_state_failed;
|
||||
else if (working == n_prim - 1)
|
||||
state = DDF_state_part_optimal;
|
||||
break;
|
||||
}
|
||||
return state;
|
||||
}
|
||||
|
||||
/*
|
||||
* The state of each disk is stored in the global phys_disk structure
|
||||
* in phys_disk.entries[n].state.
|
||||
|
@ -3837,7 +3883,6 @@ static void ddf_set_disk(struct active_array *a, int n, int state)
|
|||
struct vd_config *vc = find_vdcr(ddf, inst, (unsigned int)n,
|
||||
&n_bvd, &vcl);
|
||||
int pd;
|
||||
int i, st, working;
|
||||
struct mdinfo *mdi;
|
||||
struct dl *dl;
|
||||
|
||||
|
@ -3901,43 +3946,10 @@ static void ddf_set_disk(struct active_array *a, int n, int state)
|
|||
* It needs to be one of "optimal", "degraded", "failed".
|
||||
* I don't understand 'deleted' or 'missing'.
|
||||
*/
|
||||
working = 0;
|
||||
for (i=0; i < a->info.array.raid_disks; i++) {
|
||||
pd = find_phys(ddf, vc->phys_refnum[i]);
|
||||
if (pd < 0)
|
||||
continue;
|
||||
st = __be16_to_cpu(ddf->phys->entries[pd].state);
|
||||
if ((st & (DDF_Online|DDF_Failed|DDF_Rebuilding))
|
||||
== DDF_Online)
|
||||
working++;
|
||||
state = get_bvd_state(ddf, vc);
|
||||
if (vc->sec_elmnt_count > 1) {
|
||||
/* treat secondary level */
|
||||
}
|
||||
state = DDF_state_degraded;
|
||||
if (working == a->info.array.raid_disks)
|
||||
state = DDF_state_optimal;
|
||||
else switch(vc->prl) {
|
||||
case DDF_RAID0:
|
||||
case DDF_CONCAT:
|
||||
case DDF_JBOD:
|
||||
state = DDF_state_failed;
|
||||
break;
|
||||
case DDF_RAID1:
|
||||
if (working == 0)
|
||||
state = DDF_state_failed;
|
||||
else if (working == 2 && state == DDF_state_degraded)
|
||||
state = DDF_state_part_optimal;
|
||||
break;
|
||||
case DDF_RAID4:
|
||||
case DDF_RAID5:
|
||||
if (working < a->info.array.raid_disks-1)
|
||||
state = DDF_state_failed;
|
||||
break;
|
||||
case DDF_RAID6:
|
||||
if (working < a->info.array.raid_disks-2)
|
||||
state = DDF_state_failed;
|
||||
else if (working == a->info.array.raid_disks-1)
|
||||
state = DDF_state_part_optimal;
|
||||
break;
|
||||
}
|
||||
|
||||
if (ddf->virt->entries[inst].state !=
|
||||
((ddf->virt->entries[inst].state & ~DDF_state_mask)
|
||||
|
|
Loading…
Reference in New Issue