From 9b95a5a9390b8fb21664ecfbc6126d570284852a Mon Sep 17 00:00:00 2001 From: Alasdair Kergon Date: Fri, 2 Jul 2010 02:09:57 +0000 Subject: [PATCH] Always pass unsuspended dm devices through persistent filter to other filters. Move test for suspended dm devices ahead of other filters. --- WHATS_NEW | 2 ++ doc/example.conf.in | 16 +++++++++------- lib/commands/toolcontext.c | 1 + lib/filters/filter-persistent.c | 28 +++++++++++++++++++++++----- lib/filters/filter.c | 13 +++++-------- lib/filters/filter.h | 1 + 6 files changed, 41 insertions(+), 20 deletions(-) diff --git a/WHATS_NEW b/WHATS_NEW index 735f885ac..28dbbae0f 100644 --- a/WHATS_NEW +++ b/WHATS_NEW @@ -1,5 +1,7 @@ Version 2.02.70 - ================================ + Always pass unsuspended dm devices through persistent filter to other filters. + Move test for suspended dm devices ahead of other filters. Fix another segfault in clvmd -R if no response from daemon received. (2.02.68) Remove superfluous suspended device counter from clvmd. Fix lvm shell crash when input is entirely whitespace. diff --git a/doc/example.conf.in b/doc/example.conf.in index d5af31593..850b7e23e 100644 --- a/doc/example.conf.in +++ b/doc/example.conf.in @@ -457,13 +457,15 @@ activation { # pvmetadatacopies = 1 # Default number of copies of metadata to maintain for each VG. - # If set to a non-zero value, LVM automatically manages the PV - # 'metadataignore' flags (see pvchange) to achieve the requested - # copies of metadata. You may set a value larger than the - # the sum of all metadata areas on all physical volumes. This value - # can be overridden on the command line of various commands. The - # default value of 0 indicates that LVM should not automatically - # manage the 'metadataignore' flags. + # If set to a non-zero value, LVM automatically chooses which of + # the available metadata areas to use to achieve the requested + # number of copies of the VG metadata. If you set a value larger + # than the the total number of metadata areas available then + # metadata is stored in them all. + # The default value of 0 ("unmanaged") disables this automatic + # management and allows you to control which metadata areas + # are used at the individual PV level using 'pvchange + # --metadataignore y/n'. # vgmetadatacopies = 0 diff --git a/lib/commands/toolcontext.c b/lib/commands/toolcontext.c index 7c5e37943..788236dac 100644 --- a/lib/commands/toolcontext.c +++ b/lib/commands/toolcontext.c @@ -24,6 +24,7 @@ #include "filter-md.h" #include "filter-persistent.h" #include "filter-regex.h" +#include "filter-suspended.h" #include "filter-sysfs.h" #include "label.h" #include "lvm-file.h" diff --git a/lib/filters/filter-persistent.c b/lib/filters/filter-persistent.c index 6574d6983..5a016f84d 100644 --- a/lib/filters/filter-persistent.c +++ b/lib/filters/filter-persistent.c @@ -16,9 +16,11 @@ #include "lib.h" #include "config.h" #include "dev-cache.h" +#include "filter.h" #include "filter-persistent.h" #include "lvm-file.h" #include "lvm-string.h" +#include "activate.h" #include #include @@ -266,15 +268,31 @@ static int _lookup_p(struct dev_filter *f, struct device *dev) void *l = dm_hash_lookup(pf->devices, dev_name(dev)); struct str_list *sl; + /* Cached BAD? */ + if (l == PF_BAD_DEVICE) { + log_debug("%s: Skipping (cached)", dev_name(dev)); + return 0; + } + + /* Test dm devices every time, so cache them as GOOD. */ + if (MAJOR(dev->dev) == dm_major()) { + if (!l) + dm_list_iterate_items(sl, &dev->aliases) + dm_hash_insert(pf->devices, sl->str, PF_GOOD_DEVICE); + if (ignore_suspended_devices() && !device_is_usable(dev)) { + log_debug("%s: Skipping (suspended/internal)", dev_name(dev)); + return 0; + } + return pf->real->passes_filter(pf->real, dev); + } + + /* Uncached */ if (!l) { - l = pf->real->passes_filter(pf->real, dev) ? - PF_GOOD_DEVICE : PF_BAD_DEVICE; + l = pf->real->passes_filter(pf->real, dev) ? PF_GOOD_DEVICE : PF_BAD_DEVICE; dm_list_iterate_items(sl, &dev->aliases) dm_hash_insert(pf->devices, sl->str, l); - - } else if (l == PF_BAD_DEVICE) - log_debug("%s: Skipping (cached)", dev_name(dev)); + } return (l == PF_BAD_DEVICE) ? 0 : 1; } diff --git a/lib/filters/filter.c b/lib/filters/filter.c index 889cb0db9..eafa72608 100644 --- a/lib/filters/filter.c +++ b/lib/filters/filter.c @@ -42,6 +42,11 @@ static int _blkext_major = -1; static int _drbd_major = -1; static int _device_mapper_major = -1; +int dm_major(void) +{ + return _device_mapper_major; +} + int md_major(void) { return _md_major; @@ -130,14 +135,6 @@ static int _passes_lvm_type_device_filter(struct dev_filter *f __attribute((unus return 0; } - /* FIXME Always check 'layer' regardless of ignore_suspended_devices */ - /* Skip suspended devices */ - if (MAJOR(dev->dev) == _device_mapper_major && - ignore_suspended_devices() && !device_is_usable(dev)) { - log_debug("%s: Skipping: Suspended or internal dm device", name); - return 0; - } - /* Check it's accessible */ if (!dev_open_flags(dev, O_RDONLY, 0, 1)) { log_debug("%s: Skipping: open failed", name); diff --git a/lib/filters/filter.h b/lib/filters/filter.h index 4da332528..07611f9eb 100644 --- a/lib/filters/filter.h +++ b/lib/filters/filter.h @@ -35,6 +35,7 @@ struct dev_filter *lvm_type_filter_create(const char *proc, void lvm_type_filter_destroy(struct dev_filter *f); +int dm_major(void); int md_major(void); int blkext_major(void); int max_partitions(int major); -- 2.43.5