mirror of
git://sourceware.org/git/lvm2.git
synced 2025-01-03 05:18:29 +03:00
lvmlockd: fix metadata validation when rescanning VG
When rescanning a VG from disk, the metadata read from each PV was compared as a sanity check. The comparison is done by exporting the vg metadata from each dev to a config tree, and then comparing the config trees. The function to create the config tree inserts extraneous information along with the actual VG metadata. This extra info includes creation_time. The config trees for two devs can easily be created one second apart in which case the different creation_times would cause the metadata comparison to fail. The fix is to exclude the extraneous info from the metadata comparison.
This commit is contained in:
parent
629059ee84
commit
d455300d7b
31
lib/cache/lvmetad.c
vendored
31
lib/cache/lvmetad.c
vendored
@ -1918,15 +1918,44 @@ scan_more:
|
|||||||
vgmeta_ret = vgmeta;
|
vgmeta_ret = vgmeta;
|
||||||
save_dev = devl->dev;
|
save_dev = devl->dev;
|
||||||
} else {
|
} else {
|
||||||
if (compare_config(vgmeta_ret->root, vgmeta->root)) {
|
struct dm_config_node *meta1 = vgmeta_ret->root;
|
||||||
|
struct dm_config_node *meta2 = vgmeta->root;
|
||||||
|
struct dm_config_node *sib1 = meta1->sib;
|
||||||
|
struct dm_config_node *sib2 = meta2->sib;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Do not compare the extraneous data that
|
||||||
|
* export_vg_to_config_tree() inserts next to the
|
||||||
|
* actual VG metadata. This includes creation_time
|
||||||
|
* which may not match since it is generated separately
|
||||||
|
* for each call to create the config tree.
|
||||||
|
*
|
||||||
|
* We're saving the sibling pointer and restoring it
|
||||||
|
* after the compare because we're unsure if anything
|
||||||
|
* later might want it.
|
||||||
|
*
|
||||||
|
* FIXME: make it clearer what we're doing here, e.g.
|
||||||
|
* pass a parameter to export_vg_to_config_tree()
|
||||||
|
* telling it to skip the extraneous data, or something.
|
||||||
|
* It's very non-obvious that setting sib=NULL does that.
|
||||||
|
*/
|
||||||
|
meta1->sib = NULL;
|
||||||
|
meta2->sib = NULL;
|
||||||
|
|
||||||
|
if (compare_config(meta1, meta2)) {
|
||||||
log_error("VG %s metadata comparison failed for device %s vs %s",
|
log_error("VG %s metadata comparison failed for device %s vs %s",
|
||||||
vg->name, dev_name(devl->dev), save_dev ? dev_name(save_dev) : "none");
|
vg->name, dev_name(devl->dev), save_dev ? dev_name(save_dev) : "none");
|
||||||
_log_debug_inequality(vg->name, vgmeta_ret->root, vgmeta->root);
|
_log_debug_inequality(vg->name, vgmeta_ret->root, vgmeta->root);
|
||||||
|
|
||||||
|
meta1->sib = sib1;
|
||||||
|
meta2->sib = sib2;
|
||||||
dm_config_destroy(vgmeta);
|
dm_config_destroy(vgmeta);
|
||||||
dm_config_destroy(vgmeta_ret);
|
dm_config_destroy(vgmeta_ret);
|
||||||
release_vg(baton.vg);
|
release_vg(baton.vg);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
meta1->sib = sib1;
|
||||||
|
meta2->sib = sib2;
|
||||||
dm_config_destroy(vgmeta);
|
dm_config_destroy(vgmeta);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user