mirror of
git://sourceware.org/git/lvm2.git
synced 2024-12-21 13:34:40 +03:00
metadata: allow reading metadata with invalid creation_time
lvm2 till version 2.02.169 (commit78d004efa8
) was printing invalid creation_time argument into metadata on 32bit arch. However with commitba9820b142
we started to properly validate all input numbers and thus we refused to accept invalid metadata with 'garbage' string - but this results in the situation where metadata produced on older lvm2 on 32 bit architecture will become unreadable after upgrade. To fix this case - extend libdm parser in a way, that whenever we find error integer value, we also check if the parsed value is not for creation_time node and in this case we let the metadata pass through with made-up date 2018-05-24 (release date of 2.02.169).
This commit is contained in:
parent
1f7c9da554
commit
85dbcda150
@ -51,6 +51,8 @@ struct parser {
|
||||
|
||||
struct dm_pool *mem;
|
||||
int no_dup_node_check; /* whether to disable dup node checking */
|
||||
const char *key; /* last obtained key */
|
||||
unsigned ignored_creation_time;
|
||||
};
|
||||
|
||||
struct config_output {
|
||||
@ -176,7 +178,7 @@ static int _do_dm_config_parse(struct dm_config_tree *cft, const char *start, co
|
||||
/* TODO? if (start == end) return 1; */
|
||||
|
||||
struct parser *p;
|
||||
if (!(p = dm_pool_alloc(cft->mem, sizeof(*p))))
|
||||
if (!(p = dm_pool_zalloc(cft->mem, sizeof(*p))))
|
||||
return_0;
|
||||
|
||||
p->mem = cft->mem;
|
||||
@ -615,6 +617,7 @@ static struct dm_config_node *_section(struct parser *p, struct dm_config_node *
|
||||
match(TOK_SECTION_E);
|
||||
} else {
|
||||
match(TOK_EQ);
|
||||
p->key = root->key;
|
||||
if (!(value = _value(p)))
|
||||
return_NULL;
|
||||
if (root->v)
|
||||
@ -682,9 +685,18 @@ static struct dm_config_value *_type(struct parser *p)
|
||||
errno = 0;
|
||||
v->v.i = strtoll(p->tb, NULL, 0); /* FIXME: check error */
|
||||
if (errno) {
|
||||
if (errno == ERANGE && p->key &&
|
||||
strcmp("creation_time", p->key) == 0) {
|
||||
/* Due to a bug in some older 32bit builds (<2.02.169),
|
||||
* lvm was able to produce invalid creation_time string */
|
||||
v->v.i = 1527120000; /* Pick 2018-05-24 day instead */
|
||||
if (!p->ignored_creation_time++)
|
||||
log_warn("WARNING: Invalid creation_time found in metadata (repaired with next metadata update).");
|
||||
} else {
|
||||
log_error("Failed to read int token.");
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
match(TOK_INT);
|
||||
break;
|
||||
|
||||
|
@ -51,6 +51,8 @@ struct parser {
|
||||
|
||||
struct dm_pool *mem;
|
||||
int no_dup_node_check; /* whether to disable dup node checking */
|
||||
const char *key; /* last obtained key */
|
||||
unsigned ignored_creation_time;
|
||||
};
|
||||
|
||||
struct config_output {
|
||||
@ -176,7 +178,7 @@ static int _do_dm_config_parse(struct dm_config_tree *cft, const char *start, co
|
||||
/* TODO? if (start == end) return 1; */
|
||||
|
||||
struct parser *p;
|
||||
if (!(p = dm_pool_alloc(cft->mem, sizeof(*p))))
|
||||
if (!(p = dm_pool_zalloc(cft->mem, sizeof(*p))))
|
||||
return_0;
|
||||
|
||||
p->mem = cft->mem;
|
||||
@ -615,6 +617,7 @@ static struct dm_config_node *_section(struct parser *p, struct dm_config_node *
|
||||
match(TOK_SECTION_E);
|
||||
} else {
|
||||
match(TOK_EQ);
|
||||
p->key = root->key;
|
||||
if (!(value = _value(p)))
|
||||
return_NULL;
|
||||
if (root->v)
|
||||
@ -682,9 +685,18 @@ static struct dm_config_value *_type(struct parser *p)
|
||||
errno = 0;
|
||||
v->v.i = strtoll(p->tb, NULL, 0); /* FIXME: check error */
|
||||
if (errno) {
|
||||
if (errno == ERANGE && p->key &&
|
||||
strcmp("creation_time", p->key) == 0) {
|
||||
/* Due to a bug in some older 32bit builds (<2.02.169),
|
||||
* lvm was able to produce invalid creation_time string */
|
||||
v->v.i = 1527120000; /* Pick 2018-05-24 day instead */
|
||||
if (!p->ignored_creation_time++)
|
||||
log_warn("WARNING: Invalid creation_time found in metadata (repaired with next metadata update).");
|
||||
} else {
|
||||
log_error("Failed to read int token.");
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
match(TOK_INT);
|
||||
break;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user