Discussion:
[linux-lvm] unable to exclude LVs using global_filter
Gordon Messmer
2018-01-02 06:47:16 UTC
Permalink
I'd like to avoid scanning LVs, and I thought I'd set global_filter
appropriately.  The following logs show global_filter set to reject
^/dev/VolGroup/vm_, but the system is scanning
/dev/VolGroup/vm_wiki_data.  Any hints as to what I'm doing wrong?



Dec 06 13:08:37 kvm-test.private lvm[532]: Setting devices/global_filter
to global_filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:37 kvm-test.private lvm[534]: Setting devices/global_filter
to global_filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:38 kvm-test.private lvm[543]: Setting devices/global_filter
to global_filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:40 kvm-test.private lvm[648]: Setting devices/global_filter
to global_filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:40 kvm-test.private lvm[648]: Setting devices/filter to
filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:42 kvm-test.private lvm[751]: Setting devices/global_filter
to global_filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:42 kvm-test.private lvm[751]: Setting devices/filter to
filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting devices/global_filter
to global_filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting devices/filter to
filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Dec 06 13:08:44 kvm-test.private lvm[785]: Opened
/dev/VolGroup/vm_wiki_data RO O_DIRECT
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
size is 10485760 sectors
Dec 06 13:08:44 kvm-test.private lvm[785]: Closed /dev/VolGroup/vm_wiki_data
Dec 06 13:08:44 kvm-test.private lvm[785]: Opened
/dev/VolGroup/vm_wiki_data RO O_DIRECT
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
block size is 4096 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
physical block size is 512 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: Closed /dev/VolGroup/vm_wiki_data
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
using cached size 10485760 sectors
Dec 06 13:08:44 kvm-test.private lvm[785]: Opened
/dev/VolGroup/vm_wiki_data RO O_DIRECT
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
block size is 4096 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
physical block size is 512 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: Closed /dev/VolGroup/vm_wiki_data
Dec 06 13:08:44 kvm-test.private lvm[785]: Scanning dev 253:3 for
lvmetad cache.
Dec 06 13:08:44 kvm-test.private lvm[785]: Reading label from device
/dev/VolGroup/vm_wiki_data
Dec 06 13:08:44 kvm-test.private lvm[785]: Opened
/dev/VolGroup/vm_wiki_data RO O_DIRECT
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
block size is 4096 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
physical block size is 512 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
lvm2 label detected at sector 1
Dec 06 13:08:44 kvm-test.private lvm[785]: lvmcache
/dev/VolGroup/vm_wiki_data: now in VG #orphans_lvm2 (#orphans_lvm2) with
0 mda(s).
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
PV header extension version 2 found
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
Found metadata at 8704 size 1086 (in area at 4096 size 1044480) for
DataGroup (ZY69boAqK0Cz6TYGHdevNQfQ2O1sbJoG)
Dec 06 13:08:44 kvm-test.private lvm[785]: lvmcache has no info for
vgname "DataGroup" with VGID ZY69boAqK0Cz6TYGHdevNQfQ2O1sbJoG.
Dec 06 13:08:44 kvm-test.private lvm[785]: lvmcache has no info for
vgname "DataGroup".
Dec 06 13:08:44 kvm-test.private lvm[785]: lvmcache
/dev/VolGroup/vm_wiki_data: now in VG DataGroup with 1 mda(s).
Dec 06 13:08:44 kvm-test.private lvm[785]: lvmcache
/dev/VolGroup/vm_wiki_data: VG DataGroup: set VGID to
ZY69boAqK0Cz6TYGHdevNQfQ2O1sbJoG.
Dec 06 13:08:44 kvm-test.private lvm[785]: lvmcache
/dev/VolGroup/vm_wiki_data: VG DataGroup: set creation host to
localhost.localdomain.
Dec 06 13:08:44 kvm-test.private lvm[785]: lvmcache
/dev/VolGroup/vm_wiki_data: VG DataGroup: stored metadata checksum
0xf5731900 with size 1086.
Dec 06 13:08:44 kvm-test.private lvm[785]: Closed /dev/VolGroup/vm_wiki_data
Dec 06 13:08:44 kvm-test.private lvm[785]: Opened
/dev/VolGroup/vm_wiki_data RO O_DIRECT
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
block size is 4096 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
physical block size is 512 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: Allocated VG DataGroup at
0x560c70fc8bb0.
Dec 06 13:08:44 kvm-test.private lvm[785]: Importing logical volume
DataGroup/data.
Dec 06 13:08:44 kvm-test.private lvm[785]: Read DataGroup metadata (4)
from /dev/VolGroup/vm_wiki_data at 8704 size 1086
Dec 06 13:08:44 kvm-test.private lvm[785]: Closed /dev/VolGroup/vm_wiki_data
Dec 06 13:08:44 kvm-test.private lvm[785]: Opened
/dev/VolGroup/vm_wiki_data RO O_DIRECT
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
block size is 4096 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: /dev/VolGroup/vm_wiki_data:
physical block size is 512 bytes
Dec 06 13:08:44 kvm-test.private lvm[785]: Closed /dev/VolGroup/vm_wiki_data
Dec 06 13:08:44 kvm-test.private lvm[785]: Telling lvmetad to store PV
/dev/VolGroup/vm_wiki_data (NRKTXX-I9D8-Vxb1-hKcX-rjJX-GNhB-jgsXiW) in
VG DataGroup
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting response to OK
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting response to OK
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting response to OK
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting seqno_after to 4
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting seqno_after to 4
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting seqno_before to 4
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting status to complete
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting vgname to DataGroup
Dec 06 13:08:44 kvm-test.private lvm[785]: Setting changed to 1
Dec 06 13:08:44 kvm-test.private lvm[785]: VG DataGroup is complete in
lvmetad with dev /dev/VolGroup/vm_wiki_data.
Dec 06 13:08:44 kvm-test.private lvm[785]: VG DataGroup is changed in
lvmetad.
Dec 06 13:08:44 kvm-test.private lvm[785]: Freeing VG DataGroup at
0x560c70fc8bb0.
Marian Csontos
2018-01-02 11:03:01 UTC
Permalink
Post by Gordon Messmer
I'd like to avoid scanning LVs, and I thought I'd set global_filter
appropriately.  The following logs show global_filter set to reject
^/dev/VolGroup/vm_, but the system is scanning
/dev/VolGroup/vm_wiki_data.  Any hints as to what I'm doing wrong?
Dec 06 13:08:37 kvm-test.private lvm[532]: Setting devices/global_filter
to global_filter = [ "r|^/dev/VolGroup/vm_|", "r|^/dev/dm-|", "a|.*/|" ]
Hi Gordon, remove the last component in the filter: 'a|.*/|'.

Filters accept any device if any of it's "names" (all symbolic links) is
matched by an a pattern ("a|.*/|" in your case) and matches no previous
r pattern - for example anything in /dev/mapper/ is accepted.

When used as a blacklist filter(s) must contain only "r" paterns.

BTW it is usually better to use white list: list "a" patterns for all
disks you wish to accept and add "r|.*|" at the end.

-- Martian
Gordon Messmer
2018-01-02 15:35:50 UTC
Permalink
Post by Marian Csontos
Filters accept any device if any of it's "names" (all symbolic links)
is matched by an a pattern ("a|.*/|" in your case) and matches no
previous r pattern
I don't follow you.  The name being processed in that log *does* match a
previous r pattern.
Post by Marian Csontos
for example anything in /dev/mapper/ is accepted.
Yes, I'd considered that might be an issue, but that's not the block
device name that the logs indicate is being used.  A path that I've
specifically rejected is being processed.  If a second path to the block
device might be processed, then I can see the need to make additional
changes, but I can't solve that problem without understanding the basic
logic of the filter system.

The documentation in lvm.conf says "The first regex in the list to match
the path is used, producing the 'a' or 'r' result for the device." but
that doesn't seem to be correct.
Marian Csontos
2018-01-02 18:17:12 UTC
Permalink
Post by Marian Csontos
Filters accept any device if any of it's "names" (all symbolic links)
is matched by an a pattern ("a|.*/|" in your case) and matches no
previous r pattern
I don't follow you.  The name being processed in that log *does* match a
previous r pattern.
I do not think that log shows what is processed. LVM displays device
names according to different option - preferred_names it is.

If lvmetad is in use, which by default it is, run `pvscan -vvvv --cache
$DEV_MAJOR:$DEV_MINOR` - that should be more helpful WRT which devices
are scanned and accepted as Physical Volumes.
Post by Marian Csontos
for example anything in /dev/mapper/ is accepted.
^ THIS! In your case the /dev/mapper/vm_* link IS accepted by the
"a|.*/|" in global_filter. And /dev/disk/by-*/* too. And maybe others...
Yes, I'd considered that might be an issue, but that's not the block
device name that the logs indicate is being used.  A path that I've
specifically rejected is being processed.  If a second path to the block
device might be processed, then I can see the need to make additional
changes, but I can't solve that problem without understanding the basic
logic of the filter system.
The documentation in lvm.conf says "The first regex in the list to match
the path is used, producing the 'a' or 'r' result for the device." but
that doesn't seem to be correct.
IMHO the documentation is confusing if not straight incorrect. I hate
that and IMHO we should fix how the filtering works, but that would be
an incompatible change, and those are not loved. :-(

How it actually works is: if ANY path is accepted, the device is. In
upstream the lvm.conf also says (emphasis mine):

"When multiple path names exist for a block device, if *any path* name
matches an 'a' pattern before an 'r' pattern, then the device is
accepted. If all the path names match an 'r' pattern first, then the
device is rejected."

May be we should replace the "device" in the last sentence by "path" so
it would say:

"The first regex in the list to match the path is used, producing the
'a' or 'r' result for *that path*."

And:

"When multiple path names exist for a block device"

could be safely discarded - as it is true most of if not all the time
(or replaced by "Keep in mind devices nowadays are linked from many
places in the /dev tree, and")

So we would have the following:

"If any path name matches an 'a' pattern before an 'r' pattern, then the
device is accepted."

I am not a native speaker, but to me that is consistent with current
behavior which is unlikely to change. I will send a patch to see if it
is opposed by anyone...

-- Martian
_______________________________________________
linux-lvm mailing list
https://www.redhat.com/mailman/listinfo/linux-lvm
read the LVM HOW-TO at http://tldp.org/HOWTO/LVM-HOWTO/
Alasdair G Kergon
2018-01-02 18:43:34 UTC
Permalink
The key concept to grasp is that LVM works with devices (i.e. major
number + minor number pairs) rather than filesystem paths and it makes a
single "use or ignore" decision for each device (not for each path).

One device might be reachable through more than one filesystem path that
lvm has been configured to check and, if so, all the paths are checked
against the filter independently and the results feed into that single
decision according to the rules described.

Alasdair
Alasdair G Kergon
2018-01-02 18:47:42 UTC
Permalink
Also there is no special handling for |.*| - a match against it gets treated as
a positive deliberate match, just the same way as a match against |/dev/sda2|.

Alasdair
Gordon Messmer
2018-01-02 19:16:34 UTC
Permalink
Post by Alasdair G Kergon
The key concept to grasp is that LVM works with devices (i.e. major
number + minor number pairs) rather than filesystem paths and it makes a
single "use or ignore" decision for each device (not for each path).
That seems even more misleading than the original documentation, since
the filters are applied to each path, and not to the device.

I understand what you mean, now, but I don't think that explaining the
system that way is likely to help users understand.

I'll send a patch later which might be more clear.  Should I send it to
this list?  Martian (or Marian?  Signature didn't match the From header
on an earlier message) said that they'd also send a patch, but I'm not
sure where it will be sent.

BTW, simply removing the "a" filter solved my problem.  My vm_*_data LVs
are no longer processed, but the md device that backs the primary VG is,
so everything works as I expect it to. Thanks, again.
Gordon Messmer
2018-01-03 21:18:05 UTC
Permalink
Post by Gordon Messmer
I'll send a patch later which might be more clear.
Submitted for consideration:


diff --git a/conf/example.conf.in b/conf/example.conf.in
index aab274d74..2aed631e5 100644
--- a/conf/example.conf.in
+++ b/conf/example.conf.in
@@ -114,16 +114,20 @@ devices {
        # device path names. Each regex is delimited by a vertical bar '|'
        # (or any character) and is preceded by 'a' to accept the path, or
        # by 'r' to reject the path. The first regex in the list to
match the
-       # path is used, producing the 'a' or 'r' result for the device.
-       # When multiple path names exist for a block device, if any path
name
-       # matches an 'a' pattern before an 'r' pattern, then the device is
-       # accepted. If all the path names match an 'r' pattern first,
then the
-       # device is rejected. Unmatching path names do not affect the accept
-       # or reject decision. If no path names for a device match a pattern,
-       # then the device is accepted. Be careful mixing 'a' and 'r'
patterns,
-       # as the combination might produce unexpected results (test
changes.)
-       # Run vgscan after changing the filter to regenerate the cache.
-       # See the use_lvmetad comment for a special case regarding filters.
+       # path is used, producing the 'a' or 'r' result for the path.
+       #
+       # Typically, multiple paths will exist for a block device.  If
any path
+       # to a block device is accepted by the filter list, the block device
+       # will be processed.  If no path is accepted, and at least one is
+       # rejected, the block device will not be processed.  If no path
matches
+       # any entry in the filter list, the block device will be processed.
+       #
+       # Be careful mixing 'a' and 'r' patterns, as the combination might
+       # produce unexpected results (test changes.)  It may be best to
use only
+       # 'r' patterns if your goal is to prevent processing specific block
+       # devices.  Run vgscan after changing the filter to regenerate the
+       # cache.  See the use_lvmetad comment for a special case regarding
+       # filters.
        #
        # Example
        # Accept every block device:
Gordon Messmer
2018-01-11 04:51:16 UTC
Permalink
Did anyone have any comments on this patch?  Martian said they'd try to
reword the documentation, but I don't see any recent changes in git...
Gordon Messmer
2018-01-02 18:58:10 UTC
Permalink
Post by Marian Csontos
I do not think that log shows what is processed. LVM displays device
names according to different option - preferred_names it is.
I see.  It seems to me that, for the purpose of troubleshooting filter
processing, the literal path that matches a filter option should be logged.
Post by Marian Csontos
If lvmetad is in use, which by default it is, run `pvscan -vvvv
--cache $DEV_MAJOR:$DEV_MINOR` - that should be more helpful WRT which
devices are scanned and accepted as Physical Volumes.
I see the following in the ouptut:

#device/dev-cache.c:356         /dev/dm-3: Added to device cache (253:3)
#device/dev-cache.c:352         /dev/VolGroup/vm_wiki_data: Aliased to
/dev/dm-3 in device cache (preferred name) (253:3)
#device/dev-cache.c:352 /dev/disk/by-id/dm-name-VolGroup-vm_wiki_data:
Aliased to /dev/VolGroup/vm_wiki_data in device cache (253:3)
#device/dev-cache.c:352
/dev/disk/by-id/dm-uuid-LVM-LaE2AjV9UKn6sAhmbduHGzY0TsRtfr9fwKOoFpMNpYX98umwKoXfH0qQb2MG7bCx:
Aliased to /dev/VolGroup/vm_wiki_data in device cache (253:3)
#device/dev-cache.c:352
/dev/disk/by-id/lvm-pv-uuid-NRKTXX-I9D8-Vxb1-hKcX-rjJX-GNhB-jgsXiW:
Aliased to /dev/VolGroup/vm_wiki_data in device cache (253:3)
#device/dev-cache.c:352         /dev/mapper/VolGroup-vm_wiki_data:
Aliased to /dev/VolGroup/vm_wiki_data in device cache (253:3)

...understanding that all of those paths are filtered individually was
the bit I was missing.
Post by Marian Csontos
IMHO the documentation is confusing if not straight incorrect. I hate
that and IMHO we should fix how the filtering works, but that would be
an incompatible change, and those are not loved. :-(
How it actually works is: if ANY path is accepted, the device is. In
"When multiple path names exist for a block device, if *any path* name
matches an 'a' pattern before an 'r' pattern, then the device is
accepted. If all the path names match an 'r' pattern first, then the
device is rejected."
The description of filtering is... maybe a touch long, and that specific
bit is very important and easy to miss.  It might be more clear to move
that statement to a paragraph of its own.

Alternatively, if devices are accepted when no pattern matches, maybe
emptying the default filter would be a better approach.  That way the
default configuration would accept all devices.  If someone introduces
an r filter, it will actually work as expected.  It's nearly impossible
to effectively blacklist a device if the default "a" filter is retained,
and it doesn't appear to serve a function if the system accepts block
devices that match no path.
Post by Marian Csontos
May be we should replace the "device" in the last sentence by "path"
"The first regex in the list to match the path is used, producing the
'a' or 'r' result for *that path*."
I'm not sure that really conveys the bit that I, personally, missed,
which is that in order to reject a device, you must reject all of the
paths by which it is referenced.  If the default "a" filter is retained,
then you'd probably want to be clear about that, and possibly describe
at least one way to get a list of all of the paths that lead to a given
block device.

Thanks for the help understanding the filter system.  I'll work with
this a bit and come back if my understanding is still incorrect.
Loading...