mirror of
git://sourceware.org/git/lvm2.git
synced 2025-01-02 01:18:26 +03:00
raid: Tidy dm_get_status_raid. [HM]
This commit is contained in:
parent
cf39346697
commit
1056894f1f
@ -66,6 +66,23 @@ static const char *_skip_fields(const char *p, unsigned nr)
|
|||||||
return p;
|
return p;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Count number of single-space delimited fields.
|
||||||
|
* Number of fields is number of spaces plus one.
|
||||||
|
*/
|
||||||
|
static unsigned _count_fields(const char *p)
|
||||||
|
{
|
||||||
|
unsigned nr = 1;
|
||||||
|
|
||||||
|
if (!p || !*p)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
while ((p = _skip_fields(p, 1)))
|
||||||
|
nr++;
|
||||||
|
|
||||||
|
return nr;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Various RAID status versions include:
|
* Various RAID status versions include:
|
||||||
* Versions < 1.5.0 (4 fields):
|
* Versions < 1.5.0 (4 fields):
|
||||||
@ -77,69 +94,71 @@ int dm_get_status_raid(struct dm_pool *mem, const char *params,
|
|||||||
struct dm_status_raid **status)
|
struct dm_status_raid **status)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
const char *pp, *p;
|
unsigned num_fields;
|
||||||
struct dm_status_raid *s;
|
const char *p, *pp, *msg_fields = "";
|
||||||
|
struct dm_status_raid *s = NULL;
|
||||||
|
|
||||||
if (!params || !(p = strchr(params, ' '))) {
|
if ((num_fields = _count_fields(params)) < 4)
|
||||||
log_error("Failed to parse invalid raid params.");
|
goto_bad;
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
p++;
|
|
||||||
|
|
||||||
/* second field holds the device count */
|
/* Second field holds the device count */
|
||||||
if (sscanf(p, "%d", &i) != 1)
|
msg_fields = "<#devs> ";
|
||||||
return_0;
|
if (!(p = _skip_fields(params, 1)) || (sscanf(p, "%d", &i) != 1))
|
||||||
|
goto_bad;
|
||||||
|
|
||||||
|
msg_fields = "";
|
||||||
if (!(s = dm_pool_zalloc(mem, sizeof(struct dm_status_raid))))
|
if (!(s = dm_pool_zalloc(mem, sizeof(struct dm_status_raid))))
|
||||||
return_0;
|
goto_bad;
|
||||||
|
|
||||||
if (!(s->raid_type = dm_pool_zalloc(mem, p - params)))
|
if (!(s->raid_type = dm_pool_zalloc(mem, p - params)))
|
||||||
goto_bad; /* memory is freed when pool is destroyed */
|
goto_bad; /* memory is freed when pool is destroyed */
|
||||||
|
|
||||||
if (!(s->dev_health = dm_pool_zalloc(mem, i + 1)))
|
if (!(s->dev_health = dm_pool_zalloc(mem, i + 1))) /* Space for health chars */
|
||||||
goto_bad;
|
goto_bad;
|
||||||
|
|
||||||
|
msg_fields = "<raid_type> <#devices> <health_chars> and <sync_ratio> ";
|
||||||
if (sscanf(params, "%s %u %s %" PRIu64 "/%" PRIu64,
|
if (sscanf(params, "%s %u %s %" PRIu64 "/%" PRIu64,
|
||||||
s->raid_type,
|
s->raid_type,
|
||||||
&s->dev_count,
|
&s->dev_count,
|
||||||
s->dev_health,
|
s->dev_health,
|
||||||
&s->insync_regions,
|
&s->insync_regions,
|
||||||
&s->total_regions) != 5) {
|
&s->total_regions) != 5)
|
||||||
log_error("Failed to parse raid params: %s", params);
|
goto_bad;
|
||||||
goto bad;
|
|
||||||
}
|
|
||||||
|
|
||||||
*status = s;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* All pre-1.5.0 version parameters are read. Now we check
|
* All pre-1.5.0 version parameters are read. Now we check
|
||||||
* for additional 1.5.0+ parameters.
|
* for additional 1.5.0+ parameters (i.e. num_fields at least 6).
|
||||||
*
|
*
|
||||||
* Note that 'sync_action' will be NULL (and mismatch_count
|
* Note that 'sync_action' will be NULL (and mismatch_count
|
||||||
* will be 0) if the kernel returns a pre-1.5.0 status.
|
* will be 0) if the kernel returns a pre-1.5.0 status.
|
||||||
*/
|
*/
|
||||||
for (p = params, i = 0; i < 4; i++, p++)
|
if (num_fields < 6)
|
||||||
if (!(p = strchr(p, ' ')))
|
goto out;
|
||||||
return 1; /* return pre-1.5.0 status */
|
|
||||||
|
|
||||||
pp = p;
|
msg_fields = "<sync_action> and <mismatch_cnt> ";
|
||||||
if (!(p = strchr(p, ' '))) {
|
|
||||||
log_error(INTERNAL_ERROR "Bad RAID status received.");
|
|
||||||
goto bad;
|
|
||||||
}
|
|
||||||
p++;
|
|
||||||
|
|
||||||
if (!(s->sync_action = dm_pool_zalloc(mem, p - pp)))
|
/* Skip pre-1.5.0 params */
|
||||||
|
if (!(p = _skip_fields(params, 4)) || !(pp = _skip_fields(p, 1)))
|
||||||
goto_bad;
|
goto_bad;
|
||||||
|
|
||||||
if (sscanf(pp, "%s %" PRIu64, s->sync_action, &s->mismatch_count) != 2) {
|
if (!(s->sync_action = dm_pool_zalloc(mem, pp - p)))
|
||||||
log_error("Failed to parse raid params: %s", params);
|
goto_bad;
|
||||||
goto bad;
|
|
||||||
}
|
if (sscanf(p, "%s %" PRIu64, s->sync_action, &s->mismatch_count) != 2)
|
||||||
|
goto_bad;
|
||||||
|
|
||||||
|
out:
|
||||||
|
*status = s;
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
bad:
|
bad:
|
||||||
dm_pool_free(mem, s);
|
log_error("Failed to parse %sraid params: %s", msg_fields, params);
|
||||||
|
|
||||||
|
if (s)
|
||||||
|
dm_pool_free(mem, s);
|
||||||
|
|
||||||
|
*status = NULL;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user