summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/commands/toolcontext.h1
-rw-r--r--lib/filters/filter-regex.c46
-rw-r--r--lib/filters/filter.h2
-rw-r--r--lib/label/label.c17
4 files changed, 66 insertions, 0 deletions
diff --git a/lib/commands/toolcontext.h b/lib/commands/toolcontext.h
index 4069b6116..b5c1d8a90 100644
--- a/lib/commands/toolcontext.h
+++ b/lib/commands/toolcontext.h
@@ -194,6 +194,7 @@ struct cmd_context {
unsigned create_edit_devices_file:1; /* command expects to create and/or edit devices file */
unsigned edit_devices_file:1; /* command expects to edit devices file */
unsigned filter_deviceid_skip:1; /* don't use filter-deviceid */
+ unsigned filter_regex_skip:1; /* don't use filter-regex */
unsigned filter_regex_with_devices_file:1; /* use filter-regex even when devices file is enabled */
unsigned filter_nodata_only:1; /* only use filters that do not require data from the dev */
unsigned run_by_dmeventd:1; /* command is being run by dmeventd */
diff --git a/lib/filters/filter-regex.c b/lib/filters/filter-regex.c
index d9ed0104c..40dc8aa1b 100644
--- a/lib/filters/filter-regex.c
+++ b/lib/filters/filter-regex.c
@@ -161,6 +161,9 @@ static int _accept_p(struct cmd_context *cmd, struct dev_filter *f, struct devic
if (cmd->enable_devices_list)
return 1;
+ if (cmd->filter_regex_skip)
+ return 1;
+
if (cmd->enable_devices_file && !cmd->filter_regex_with_devices_file) {
/* can't warn in create_filter because enable_devices_file is set later */
if (rf->config_filter && !rf->warned_filter) {
@@ -250,3 +253,46 @@ struct dev_filter *regex_filter_create(const struct dm_config_value *patterns, i
dm_pool_destroy(mem);
return NULL;
}
+
+static int _filter_contains_symlink(struct cmd_context *cmd, int filter_cfg)
+{
+ const struct dm_config_node *cn;
+ const struct dm_config_value *cv;
+ const char *fname;
+
+ if ((cn = find_config_tree_array(cmd, filter_cfg, NULL))) {
+ for (cv = cn->v; cv; cv = cv->next) {
+ if (cv->type != DM_CFG_STRING)
+ continue;
+ if (!cv->v.str)
+ continue;
+
+ fname = cv->v.str;
+
+ if (fname[0] != 'a')
+ continue;
+
+ if (strstr(fname, "/dev/disk/"))
+ return 1;
+ if (strstr(fname, "/dev/mapper/"))
+ return 1;
+
+ /* In case /dev/disk/by was omitted */
+ if (strstr(fname, "lvm-pv-uuid"))
+ return 1;
+ if (strstr(fname, "dm-uuid"))
+ return 1;
+ if (strstr(fname, "wwn-"))
+ return 1;
+ }
+ }
+
+ return 0;
+}
+
+int regex_filter_contains_symlink(struct cmd_context *cmd)
+{
+ return _filter_contains_symlink(cmd, devices_filter_CFG) ||
+ _filter_contains_symlink(cmd, devices_global_filter_CFG);
+}
+
diff --git a/lib/filters/filter.h b/lib/filters/filter.h
index 4cdfa2c9b..0678e5e11 100644
--- a/lib/filters/filter.h
+++ b/lib/filters/filter.h
@@ -64,4 +64,6 @@ struct dev_filter *usable_filter_create(struct cmd_context *cmd, struct dev_type
#define DEV_FILTERED_DEVICES_LIST 0x00001000
#define DEV_FILTERED_IS_LV 0x00002000
+int regex_filter_contains_symlink(struct cmd_context *cmd);
+
#endif /* _LVM_FILTER_H */
diff --git a/lib/label/label.c b/lib/label/label.c
index f845abb96..42d7b6709 100644
--- a/lib/label/label.c
+++ b/lib/label/label.c
@@ -27,6 +27,7 @@
#include "lib/format_text/layout.h"
#include "lib/device/device_id.h"
#include "lib/device/online.h"
+#include "lib/filters/filter.h"
#include <sys/stat.h>
#include <fcntl.h>
@@ -1099,6 +1100,20 @@ int label_scan_vg_online(struct cmd_context *cmd, const char *vgname,
log_debug("Skipping device_id filtering due to devname ids.");
}
+ /*
+ * See corresponding code in pvscan. This function is used during
+ * startup autoactivation when udev has not created all symlinks, so
+ * regex filter containing symlinks doesn't work. pvscan has code
+ * to properly check devs against the filter using DEVLINKS. The
+ * pvscan will only create pvs_online files for devs that pass the
+ * filter. We get devs from the pvs_online files, so we inherit the
+ * regex filtering from pvscan and don't have to do it ourself.
+ */
+ if (!cmd->enable_devices_file &&
+ !cmd->enable_devices_list &&
+ regex_filter_contains_symlink(cmd))
+ cmd->filter_regex_skip = 1;
+
cmd->filter_nodata_only = 1;
dm_list_iterate_items_safe(devl, devl2, &devs) {
@@ -1179,6 +1194,8 @@ int label_scan_vg_online(struct cmd_context *cmd, const char *vgname,
if (relax_deviceid_filter)
cmd->filter_deviceid_skip = 0;
+ cmd->filter_regex_skip = 0;
+
free_po_list(&pvs_online);
if (dm_list_empty(&devs)) {