diff --git a/.gitignore b/.gitignore
index 325731b..49c2c57 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1 +1 @@
-SOURCES/LVM2.2.03.12.tgz
+SOURCES/LVM2.2.03.14.tgz
diff --git a/.lvm2.metadata b/.lvm2.metadata
index dc25d8a..db0e692 100644
--- a/.lvm2.metadata
+++ b/.lvm2.metadata
@@ -1 +1 @@
-6d74d987b474dd0b45f239eb6dcc050622ad6962 SOURCES/LVM2.2.03.12.tgz
+e5d4364e823d72b9a08b3aecc13cd677972830f0 SOURCES/LVM2.2.03.14.tgz
diff --git a/SOURCES/0001-Revert-new-udev-autoactivation.patch b/SOURCES/0001-Revert-new-udev-autoactivation.patch
new file mode 100644
index 0000000..2b096a7
--- /dev/null
+++ b/SOURCES/0001-Revert-new-udev-autoactivation.patch
@@ -0,0 +1,545 @@
+From 63c4458aaf67d114c677baf657a7e9e43440f349 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Mon, 20 Dec 2021 14:22:02 -0600
+Subject: [PATCH 01/23] Revert "new udev autoactivation"
+
+This reverts commit 67722b312390cdab29c076c912e14bd739c5c0f6.
+---
+ scripts/Makefile.in                |   1 +
+ test/shell/udev-pvscan-vgchange.sh | 403 -----------------------------
+ udev/69-dm-lvm.rules.in            |  87 -------
+ udev/Makefile.in                   |   2 +-
+ 5 files changed, 4 insertions(+), 492 deletions(-)
+ delete mode 100644 test/shell/udev-pvscan-vgchange.sh
+ delete mode 100644 udev/69-dm-lvm.rules.in
+
+diff --git a/scripts/Makefile.in b/scripts/Makefile.in
+index 0d7f45680..ee0acb6f6 100644
+--- a/scripts/Makefile.in
++++ b/scripts/Makefile.in
+@@ -92,6 +92,7 @@ install_systemd_generators:
+ install_systemd_units:	install_dbus_service
+ 	@echo "    [INSTALL] systemd_units"
+ 	$(Q) $(INSTALL_DIR) $(systemd_unit_dir)
++	$(Q) $(INSTALL_DATA) lvm2-pvscan.service $(systemd_unit_dir)/lvm2-pvscan@.service
+ ifeq ("@BUILD_DMEVENTD@", "yes")
+ 	$(Q) $(INSTALL_DATA) dm_event_systemd_red_hat.socket $(systemd_unit_dir)/dm-event.socket
+ 	$(Q) $(INSTALL_DATA) dm_event_systemd_red_hat.service $(systemd_unit_dir)/dm-event.service
+diff --git a/test/shell/udev-pvscan-vgchange.sh b/test/shell/udev-pvscan-vgchange.sh
+deleted file mode 100644
+index c81acf0ce..000000000
+--- a/test/shell/udev-pvscan-vgchange.sh
++++ /dev/null
+@@ -1,403 +0,0 @@
+-#!/usr/bin/env bash
+-
+-# Copyright (C) 2021 Red Hat, Inc. All rights reserved.
+-#
+-# This copyrighted material is made available to anyone wishing to use,
+-# modify, copy, or redistribute it subject to the terms and conditions
+-# of the GNU General Public License v.2.
+-#
+-# You should have received a copy of the GNU General Public License
+-# along with this program; if not, write to the Free Software Foundation,
+-# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+-
+-test_description='udev rule and systemd unit run vgchange'
+-
+-SKIP_WITH_LVMPOLLD=1
+-SKIP_WITH_LVMLOCKD=1
+-
+-. lib/inittest
+-
+-#
+-# $ cat /tmp/devs
+-# /dev/sdb
+-# /dev/sdc
+-# /dev/sdd
+-#
+-# Specify this file as LVM_TEST_DEVICE_LIST=/tmp/devs
+-# when running the test.
+-#
+-# This test will wipe these devices.
+-#
+-
+-if [ -z ${LVM_TEST_DEVICE_LIST+x} ]; then echo "LVM_TEST_DEVICE_LIST is unset" && skip; else echo "LVM_TEST_DEVICE_LIST is set to '$LVM_TEST_DEVICE_LIST'"; fi
+-
+-test -e "$LVM_TEST_DEVICE_LIST" || skip
+-
+-num_devs=$(cat $LVM_TEST_DEVICE_LIST | wc -l)
+-
+-RUNDIR="/run"
+-test -d "$RUNDIR" || RUNDIR="/var/run"
+-PVS_ONLINE_DIR="$RUNDIR/lvm/pvs_online"
+-VGS_ONLINE_DIR="$RUNDIR/lvm/vgs_online"
+-PVS_LOOKUP_DIR="$RUNDIR/lvm/pvs_lookup"
+-
+-_clear_online_files() {
+-	# wait till udev is finished
+-	aux udev_wait
+-	rm -f "$PVS_ONLINE_DIR"/*
+-	rm -f "$VGS_ONLINE_DIR"/*
+-	rm -f "$PVS_LOOKUP_DIR"/*
+-}
+-
+-test -d "$PVS_ONLINE_DIR" || mkdir -p "$PVS_ONLINE_DIR"
+-test -d "$VGS_ONLINE_DIR" || mkdir -p "$VGS_ONLINE_DIR"
+-test -d "$PVS_LOOKUP_DIR" || mkdir -p "$PVS_LOOKUP_DIR"
+-_clear_online_files
+-
+-aux prepare_real_devs
+-
+-aux lvmconf 'devices/dir = "/dev"'
+-aux lvmconf 'devices/use_devicesfile = 1'
+-DFDIR="$LVM_SYSTEM_DIR/devices"
+-DF="$DFDIR/system.devices"
+-mkdir $DFDIR || true
+-not ls $DF
+-
+-get_real_devs
+-
+-wipe_all() {
+-	for dev in "${REAL_DEVICES[@]}"; do
+-		wipefs -a $dev
+-	done
+-}
+-
+-# udevadm trigger runs udev rule which runs systemd-run --no-wait vgchange -aay
+-# Because of --no-wait, we need to wait for the transient systemd
+-# service to be gone before checking the effects of the vgchange.
+-
+-wait_lvm_activate() {
+-	local vgw=$1
+-	local wait=0
+-
+-	while systemctl status lvm-activate-$vgw > /dev/null && test "$wait" -le 30; do
+-		sleep .2
+-		wait=$(( wait + 1 ))
+-	done
+-}
+-
+-# Test requires 3 devs
+-test $num_devs -gt 2 || skip
+-BDEV1=$(basename "$dev1")
+-BDEV2=$(basename "$dev2")
+-BDEV3=$(basename "$dev3")
+-
+-wipe_all
+-touch $DF
+-for dev in "${REAL_DEVICES[@]}"; do
+-	pvcreate $dev
+-done
+-
+-# 1 dev, 1 vg, 1 lv
+-
+-vgcreate $vg1 "$dev1"
+-lvcreate -l1 -an -n $lv1 $vg1 "$dev1"
+-
+-PVID1=$(pvs "$dev1" --noheading -o uuid | tr -d - | awk '{print $1}')
+-
+-_clear_online_files
+-udevadm trigger --settle -c add /sys/block/$BDEV1
+-
+-wait_lvm_activate $vg1
+-
+-ls "$RUNDIR/lvm/pvs_online/$PVID1"
+-ls "$RUNDIR/lvm/vgs_online/$vg1"
+-journalctl -u lvm-activate-$vg1 | tee out || true
+-grep "now active" out
+-check lv_field $vg1/$lv1 lv_active "active"
+-
+-vgchange -an $vg1
+-vgremove -y $vg1
+-
+-
+-# 2 devs, 1 vg, 2 lvs
+-
+-vgcreate $vg2 "$dev1" "$dev2"
+-lvcreate -l1 -an -n $lv1 $vg2 "$dev1"
+-lvcreate -l1 -an -n $lv2 $vg2 "$dev2"
+-
+-PVID1=$(pvs "$dev1" --noheading -o uuid | tr -d - | awk '{print $1}')
+-PVID2=$(pvs "$dev2" --noheading -o uuid | tr -d - | awk '{print $1}')
+-
+-_clear_online_files
+-
+-udevadm trigger --settle -c add /sys/block/$BDEV1
+-ls "$RUNDIR/lvm/pvs_online/$PVID1"
+-not ls "$RUNDIR/lvm/vgs_online/$vg2"
+-journalctl -u lvm-activate-$vg2 | tee out || true
+-not grep "now active" out
+-check lv_field $vg2/$lv1 lv_active ""
+-check lv_field $vg2/$lv2 lv_active ""
+-
+-udevadm trigger --settle -c add /sys/block/$BDEV2
+-ls "$RUNDIR/lvm/pvs_online/$PVID2"
+-ls "$RUNDIR/lvm/vgs_online/$vg2"
+-
+-wait_lvm_activate $vg2
+-
+-journalctl -u lvm-activate-$vg2 | tee out || true
+-grep "now active" out
+-check lv_field $vg2/$lv1 lv_active "active"
+-check lv_field $vg2/$lv2 lv_active "active"
+-
+-vgchange -an $vg2
+-vgremove -y $vg2
+-
+-
+-# 3 devs, 1 vg, 4 lvs, concurrent pvscans
+-# (attempting to have the pvscans run concurrently and race
+-# to activate the VG)
+-
+-vgcreate $vg3 "$dev1" "$dev2" "$dev3"
+-lvcreate -l1 -an -n $lv1 $vg3 "$dev1"
+-lvcreate -l1 -an -n $lv2 $vg3 "$dev2"
+-lvcreate -l1 -an -n $lv3 $vg3 "$dev3"
+-lvcreate -l8 -an -n $lv4 -i 2 $vg3 "$dev1" "$dev2"
+-
+-PVID1=$(pvs "$dev1" --noheading -o uuid | tr -d - | awk '{print $1}')
+-PVID2=$(pvs "$dev2" --noheading -o uuid | tr -d - | awk '{print $1}')
+-PVID3=$(pvs "$dev3" --noheading -o uuid | tr -d - | awk '{print $1}')
+-
+-_clear_online_files
+-
+-udevadm trigger -c add /sys/block/$BDEV1 &
+-udevadm trigger -c add /sys/block/$BDEV2 &
+-udevadm trigger -c add /sys/block/$BDEV3
+-
+-aux udev_wait
+-wait_lvm_activate $vg3
+-
+-ls "$RUNDIR/lvm/pvs_online/$PVID1"
+-ls "$RUNDIR/lvm/pvs_online/$PVID2"
+-ls "$RUNDIR/lvm/pvs_online/$PVID3"
+-ls "$RUNDIR/lvm/vgs_online/$vg3"
+-journalctl -u lvm-activate-$vg3 | tee out || true
+-grep "now active" out
+-check lv_field $vg3/$lv1 lv_active "active"
+-check lv_field $vg3/$lv2 lv_active "active"
+-check lv_field $vg3/$lv3 lv_active "active"
+-check lv_field $vg3/$lv4 lv_active "active"
+-
+-vgchange -an $vg3
+-vgremove -y $vg3
+-
+-
+-# 3 devs, 1 vg, 4 lvs, concurrent pvscans, metadata on only 1 PV
+-
+-wipe_all
+-rm $DF
+-touch $DF
+-pvcreate --metadatacopies 0 "$dev1"
+-pvcreate --metadatacopies 0 "$dev2"
+-pvcreate "$dev3"
+-
+-vgcreate $vg4 "$dev1" "$dev2" "$dev3"
+-lvcreate -l1 -an -n $lv1 $vg4 "$dev1"
+-lvcreate -l1 -an -n $lv2 $vg4 "$dev2"
+-lvcreate -l1 -an -n $lv3 $vg4 "$dev3"
+-lvcreate -l8 -an -n $lv4 -i 2 $vg4 "$dev1" "$dev2"
+-
+-PVID1=$(pvs "$dev1" --noheading -o uuid | tr -d - | awk '{print $1}')
+-PVID2=$(pvs "$dev2" --noheading -o uuid | tr -d - | awk '{print $1}')
+-PVID3=$(pvs "$dev3" --noheading -o uuid | tr -d - | awk '{print $1}')
+-
+-_clear_online_files
+-
+-udevadm trigger -c add /sys/block/$BDEV1 &
+-udevadm trigger -c add /sys/block/$BDEV2 &
+-udevadm trigger -c add /sys/block/$BDEV3
+-
+-aux udev_wait
+-wait_lvm_activate $vg4
+-
+-ls "$RUNDIR/lvm/pvs_online/$PVID1"
+-ls "$RUNDIR/lvm/pvs_online/$PVID2"
+-ls "$RUNDIR/lvm/pvs_online/$PVID3"
+-ls "$RUNDIR/lvm/vgs_online/$vg4"
+-journalctl -u lvm-activate-$vg4 | tee out || true
+-grep "now active" out
+-check lv_field $vg4/$lv1 lv_active "active"
+-check lv_field $vg4/$lv2 lv_active "active"
+-check lv_field $vg4/$lv3 lv_active "active"
+-check lv_field $vg4/$lv4 lv_active "active"
+-
+-vgchange -an $vg4
+-vgremove -y $vg4
+-
+-
+-# 3 devs, 3 vgs, 2 lvs in each vg, concurrent pvscans
+-
+-wipe_all
+-rm $DF
+-touch $DF
+-
+-vgcreate $vg5 "$dev1"
+-vgcreate $vg6 "$dev2"
+-vgcreate $vg7 "$dev3"
+-lvcreate -l1 -an -n $lv1 $vg5
+-lvcreate -l1 -an -n $lv2 $vg5
+-lvcreate -l1 -an -n $lv1 $vg6
+-lvcreate -l1 -an -n $lv2 $vg6
+-lvcreate -l1 -an -n $lv1 $vg7
+-lvcreate -l1 -an -n $lv2 $vg7
+-
+-_clear_online_files
+-
+-udevadm trigger -c add /sys/block/$BDEV1 &
+-udevadm trigger -c add /sys/block/$BDEV2 &
+-udevadm trigger -c add /sys/block/$BDEV3
+-
+-aux udev_wait
+-wait_lvm_activate $vg5
+-wait_lvm_activate $vg6
+-wait_lvm_activate $vg7
+-
+-ls "$RUNDIR/lvm/vgs_online/$vg5"
+-ls "$RUNDIR/lvm/vgs_online/$vg6"
+-ls "$RUNDIR/lvm/vgs_online/$vg7"
+-journalctl -u lvm-activate-$vg5 | tee out || true
+-grep "now active" out
+-journalctl -u lvm-activate-$vg6 | tee out || true
+-grep "now active" out
+-journalctl -u lvm-activate-$vg7 | tee out || true
+-grep "now active" out
+-check lv_field $vg5/$lv1 lv_active "active"
+-check lv_field $vg5/$lv2 lv_active "active"
+-check lv_field $vg6/$lv1 lv_active "active"
+-check lv_field $vg6/$lv2 lv_active "active"
+-check lv_field $vg7/$lv1 lv_active "active"
+-check lv_field $vg7/$lv2 lv_active "active"
+-
+-vgchange -an $vg5
+-vgremove -y $vg5
+-vgchange -an $vg6
+-vgremove -y $vg6
+-vgchange -an $vg7
+-vgremove -y $vg7
+-
+-# 3 devs, 1 vg, 1000 LVs
+-
+-wipe_all
+-rm $DF
+-touch $DF
+-pvcreate --metadatacopies 0 "$dev1"
+-pvcreate "$dev2"
+-pvcreate "$dev3"
+-vgcreate -s 128K $vg8 "$dev1" "$dev2" "$dev3"
+-
+-# Number of LVs to create
+-TEST_DEVS=1000
+-# On low-memory boxes let's not stress too much
+-test "$(aux total_mem)" -gt 524288 || TEST_DEVS=256
+-
+-vgcfgbackup -f data $vg8
+-
+-# Generate a lot of devices (size of 1 extent)
+-awk -v TEST_DEVS=$TEST_DEVS '/^\t\}/ {
+-    printf("\t}\n\tlogical_volumes {\n");
+-    cnt=0;
+-    for (i = 0; i < TEST_DEVS; i++) {
+-        printf("\t\tlvol%06d  {\n", i);
+-        printf("\t\t\tid = \"%06d-1111-2222-3333-2222-1111-%06d\"\n", i, i);
+-        print "\t\t\tstatus = [\"READ\", \"WRITE\", \"VISIBLE\"]";
+-        print "\t\t\tsegment_count = 1";
+-        print "\t\t\tsegment1 {";
+-        print "\t\t\t\tstart_extent = 0";
+-        print "\t\t\t\textent_count = 1";
+-        print "\t\t\t\ttype = \"striped\"";
+-        print "\t\t\t\tstripe_count = 1";
+-        print "\t\t\t\tstripes = [";
+-        print "\t\t\t\t\t\"pv0\", " cnt++;
+-        printf("\t\t\t\t]\n\t\t\t}\n\t\t}\n");
+-      }
+-  }
+-  {print}
+-' data >data_new
+-
+-vgcfgrestore -f data_new $vg8
+-
+-_clear_online_files
+-
+-udevadm trigger -c add /sys/block/$BDEV1 &
+-udevadm trigger -c add /sys/block/$BDEV2 &
+-udevadm trigger -c add /sys/block/$BDEV3
+-
+-aux udev_wait
+-wait_lvm_activate $vg8
+-
+-ls "$RUNDIR/lvm/vgs_online/$vg8"
+-journalctl -u lvm-activate-$vg8 | tee out || true
+-grep "now active" out
+-
+-num_active=$(lvs $vg8 --noheading -o active | grep active | wc -l)
+-
+-test $num_active -eq $TEST_DEVS
+-
+-vgchange -an $vg8
+-vgremove -y $vg8
+-
+-# 1 pv on an md dev, 1 vg
+-
+-wait_md_create() {
+-	local md=$1
+-
+-	while :; do
+-		if ! grep "$(basename $md)" /proc/mdstat; then
+-			echo "$md not ready"
+-			cat /proc/mdstat
+-			sleep 2
+-		else
+-			break
+-		fi
+-	done
+-	echo "$md" > WAIT_MD_DEV
+-}
+-
+-test -f /proc/mdstat && grep -q raid1 /proc/mdstat || \
+-       modprobe raid1 || skip
+-
+-mddev="/dev/md33"
+-not grep $mddev /proc/mdstat || skip
+-
+-wipe_all
+-rm $DF
+-touch $DF
+-
+-mdadm --create --metadata=1.0 "$mddev" --level 1 --chunk=64 --raid-devices=2 "$dev1" "$dev2"
+-wait_md_create "$mddev"
+-vgcreate $vg9 "$mddev"
+-
+-PVIDMD=`pvs $mddev --noheading -o uuid | tr -d - | awk '{print $1}'`
+-BDEVMD=$(basename "$mddev")
+-
+-lvcreate -l1 -an -n $lv1 $vg9
+-lvcreate -l1 -an -n $lv2 $vg9
+-
+-_clear_online_files
+-
+-udevadm trigger --settle -c add /sys/block/$BDEVMD
+-
+-wait_lvm_activate $vg9
+-
+-ls "$RUNDIR/lvm/vgs_online/$vg9"
+-journalctl -u lvm-activate-$vg9 | tee out || true
+-grep "now active" out
+-check lv_field $vg9/$lv1 lv_active "active"
+-check lv_field $vg9/$lv2 lv_active "active"
+-
+-vgchange -an $vg9
+-vgremove -y $vg9
+-
+-mdadm --stop "$mddev"
+-aux udev_wait
+-wipe_all
+-
+diff --git a/udev/69-dm-lvm.rules.in b/udev/69-dm-lvm.rules.in
+deleted file mode 100644
+index 39e5b9807..000000000
+--- a/udev/69-dm-lvm.rules.in
++++ /dev/null
+@@ -1,87 +0,0 @@
+-# Copyright (C) 2012,2021 Red Hat, Inc. All rights reserved.
+-#
+-# This file is part of LVM.
+-#
+-# This rule requires blkid to be called on block devices before so only devices
+-# used as LVM PVs are processed (ID_FS_TYPE="LVM2_member").
+-
+-SUBSYSTEM!="block", GOTO="lvm_end"
+-(LVM_EXEC_RULE)
+-
+-ENV{DM_UDEV_DISABLE_OTHER_RULES_FLAG}=="1", GOTO="lvm_end"
+-
+-# Only process devices already marked as a PV - this requires blkid to be called before.
+-ENV{ID_FS_TYPE}!="LVM2_member", GOTO="lvm_end"
+-ENV{DM_MULTIPATH_DEVICE_PATH}=="1", GOTO="lvm_end"
+-ACTION=="remove", GOTO="lvm_end"
+-
+-# Create /dev/disk/by-id/lvm-pv-uuid-<PV_UUID> symlink for each PV
+-ENV{ID_FS_UUID_ENC}=="?*", SYMLINK+="disk/by-id/lvm-pv-uuid-$env{ID_FS_UUID_ENC}"
+-
+-# If the PV is a special device listed below, scan only if the device is
+-# properly activated. These devices are not usable after an ADD event,
+-# but they require an extra setup and they are ready after a CHANGE event.
+-# Also support coldplugging with ADD event but only if the device is already
+-# properly activated.
+-# This logic should be eventually moved to rules where those particular
+-# devices are processed primarily (MD and loop).
+-
+-# DM device:
+-KERNEL!="dm-[0-9]*", GOTO="next"
+-ENV{DM_UDEV_PRIMARY_SOURCE_FLAG}=="1", ENV{DM_ACTIVATION}=="1", GOTO="lvm_scan"
+-GOTO="lvm_end"
+-
+-# MD device:
+-LABEL="next"
+-KERNEL!="md[0-9]*", GOTO="next"
+-IMPORT{db}="LVM_MD_PV_ACTIVATED"
+-ACTION=="add", ENV{LVM_MD_PV_ACTIVATED}=="1", GOTO="lvm_scan"
+-ACTION=="change", ENV{LVM_MD_PV_ACTIVATED}!="1", TEST=="md/array_state", ENV{LVM_MD_PV_ACTIVATED}="1", GOTO="lvm_scan"
+-ACTION=="add", KERNEL=="md[0-9]*p[0-9]*", GOTO="lvm_scan"
+-ENV{LVM_MD_PV_ACTIVATED}!="1", ENV{SYSTEMD_READY}="0"
+-GOTO="lvm_end"
+-
+-# Loop device:
+-LABEL="next"
+-KERNEL!="loop[0-9]*", GOTO="next"
+-ACTION=="add", ENV{LVM_LOOP_PV_ACTIVATED}=="1", GOTO="lvm_scan"
+-ACTION=="change", ENV{LVM_LOOP_PV_ACTIVATED}!="1", TEST=="loop/backing_file", ENV{LVM_LOOP_PV_ACTIVATED}="1", GOTO="lvm_scan"
+-ENV{LVM_LOOP_PV_ACTIVATED}!="1", ENV{SYSTEMD_READY}="0"
+-GOTO="lvm_end"
+-
+-LABEL="next"
+-ACTION!="add", GOTO="lvm_end"
+-
+-LABEL="lvm_scan"
+-
+-ENV{SYSTEMD_READY}="1"
+-
+-# pvscan will check if this device completes a VG,
+-# i.e. all PVs in the VG are now present with the
+-# arrival of this PV.  If so, it prints to stdout:
+-# LVM_VG_NAME_COMPLETE='foo'
+-#
+-# When the VG is complete it can be activated, so
+-# vgchange -aay <vgname> is run.  It is run via
+-# systemd since it can take longer to run than
+-# udev wants to block when processing rules.
+-# (if there are hundreds of LVs to activate,
+-# the vgchange can take many seconds.)
+-#
+-# pvscan only reads the single device specified,
+-# and uses temp files under /run/lvm to check if
+-# other PVs in the VG are present.
+-#
+-# If event_activation=0 in lvm.conf, this pvscan
+-# (using checkcomplete) will do nothing, so that
+-# no event-based autoactivation will be happen.
+-#
+-# TODO: adjust the output of vgchange -aay so that
+-# it's better suited to appearing in the journal.
+-
+-IMPORT{program}="(LVM_EXEC)/lvm pvscan --cache --listvg --checkcomplete --vgonline --udevoutput --journal=output $env{DEVNAME}"
+-ENV{LVM_VG_NAME_COMPLETE}=="?*", RUN+="/usr/bin/systemd-run -r --no-block --property DefaultDependencies=no --unit lvm-activate-$env{LVM_VG_NAME_COMPLETE} lvm vgchange -aay --nohints $env{LVM_VG_NAME_COMPLETE}"
+-GOTO="lvm_end"
+-
+-LABEL="lvm_end"
+-
+diff --git a/udev/Makefile.in b/udev/Makefile.in
+index e777dda16..e32cba921 100644
+--- a/udev/Makefile.in
++++ b/udev/Makefile.in
+@@ -18,7 +18,7 @@ top_builddir = @top_builddir@
+ include $(top_builddir)/make.tmpl
+ 
+ DM_RULES=10-dm.rules 13-dm-disk.rules 95-dm-notify.rules
+-LVM_RULES=11-dm-lvm.rules 69-dm-lvm.rules
++LVM_RULES=11-dm-lvm.rules 69-dm-lvm-metad.rules
+ 
+ DM_DIR=$(shell $(GREP) "\#define DM_DIR" $(top_srcdir)/libdm/misc/dm-ioctl.h | $(AWK) '{print $$3}')
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0002-Revert-pvscan-only-add-device-args-to-dev-cache.patch b/SOURCES/0002-Revert-pvscan-only-add-device-args-to-dev-cache.patch
new file mode 100644
index 0000000..8e73676
--- /dev/null
+++ b/SOURCES/0002-Revert-pvscan-only-add-device-args-to-dev-cache.patch
@@ -0,0 +1,450 @@
+From 2091305b796d5552fd991c527a0359a0b4d8fde0 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Mon, 20 Dec 2021 13:38:23 -0600
+Subject: [PATCH 02/23] Revert "pvscan: only add device args to dev cache"
+
+This reverts commit 33e47182f773c1a902b533580b63a803906de55d.
+---
+ lib/device/dev-cache.c          | 204 +++-----------------------------
+ lib/device/dev-cache.h          |   6 +-
+ lib/device/device_id.c          |  27 ++---
+ lib/device/device_id.h          |   1 -
+ test/shell/devicesfile-basic.sh |   2 +-
+ tools/pvscan.c                  |  58 ++++-----
+ 6 files changed, 52 insertions(+), 246 deletions(-)
+
+diff --git a/lib/device/dev-cache.c b/lib/device/dev-cache.c
+index 33b75a9a9..c6e5f68cf 100644
+--- a/lib/device/dev-cache.c
++++ b/lib/device/dev-cache.c
+@@ -1852,7 +1852,7 @@ int setup_devices_file(struct cmd_context *cmd)
+  * Add all system devices to dev-cache, and attempt to
+  * match all devices_file entries to dev-cache entries.
+  */
+-int setup_devices(struct cmd_context *cmd)
++static int _setup_devices(struct cmd_context *cmd, int no_file_match)
+ {
+ 	int file_exists;
+ 	int lock_mode = 0;
+@@ -1979,6 +1979,13 @@ int setup_devices(struct cmd_context *cmd)
+ 	 */
+ 	dev_cache_scan(cmd);
+ 
++	/*
++	 * The caller uses "no_file_match" if it wants to match specific devs
++	 * itself, instead of matching everything in device_ids_match.
++	 */
++	if (no_file_match && cmd->enable_devices_file)
++		return 1;
++
+ 	/*
+ 	 * Match entries from cmd->use_devices with device structs in dev-cache.
+ 	 */
+@@ -1987,6 +1994,16 @@ int setup_devices(struct cmd_context *cmd)
+ 	return 1;
+ }
+ 
++int setup_devices(struct cmd_context *cmd)
++{
++	return _setup_devices(cmd, 0);
++}
++
++int setup_devices_no_file_match(struct cmd_context *cmd)
++{
++	return _setup_devices(cmd, 1);
++}
++
+ /*
+  * The alternative to setup_devices() when the command is interested
+  * in using only one PV.
+@@ -2055,188 +2072,3 @@ int setup_device(struct cmd_context *cmd, const char *devname)
+ 	return 1;
+ }
+ 
+-/*
+- * pvscan --cache is specialized/optimized to look only at command args,
+- * so this just sets up the devices file, then individual devices are
+- * added to dev-cache and matched with device_ids later in pvscan.
+- */
+-
+-int setup_devices_for_pvscan_cache(struct cmd_context *cmd)
+-{
+-	if (cmd->enable_devices_list) {
+-		if (!_setup_devices_list(cmd))
+-			return_0;
+-		return 1;
+-	}
+-
+-	if (!setup_devices_file(cmd))
+-		return_0;
+-
+-	if (!cmd->enable_devices_file)
+-		return 1;
+-
+-	if (!devices_file_exists(cmd)) {
+-		log_debug("Devices file not found, ignoring.");
+-		cmd->enable_devices_file = 0;
+-		return 1;
+-	}
+-
+-	if (!lock_devices_file(cmd, LOCK_SH)) {
+-		log_error("Failed to lock the devices file to read.");
+-		return 0;
+-	}
+-
+-	if (!device_ids_read(cmd)) {
+-		log_error("Failed to read the devices file.");
+-		unlock_devices_file(cmd);
+-		return 0;
+-	}
+-
+-	unlock_devices_file(cmd);
+-	return 1;
+-}
+-
+-
+-/* Get a device name from a devno. */
+-
+-static char *_get_devname_from_devno(struct cmd_context *cmd, dev_t devno)
+-{
+-	char path[PATH_MAX];
+-	char devname[PATH_MAX];
+-	char namebuf[NAME_LEN];
+-	char line[1024];
+-	int major = MAJOR(devno);
+-	int minor = MINOR(devno);
+-	int line_major;
+-	int line_minor;
+-	uint64_t line_blocks;
+-	DIR *dir;
+-	struct dirent *dirent;
+-	FILE *fp;
+-
+-	/*
+-	 * $ ls /sys/dev/block/8:0/device/block/
+-	 * sda
+-	 */
+-	if (major_is_scsi_device(cmd->dev_types, major)) {
+-		if (dm_snprintf(path, sizeof(path), "%sdev/block/%d:%d/device/block",
+-				dm_sysfs_dir(), major, minor) < 0) {
+-			return NULL;
+-		}
+-
+-		if (!(dir = opendir(path)))
+-			return NULL;
+-
+-		while ((dirent = readdir(dir))) {
+-			if (dirent->d_name[0] == '.')
+-				continue;
+-			if (dm_snprintf(devname, sizeof(devname), "/dev/%s", dirent->d_name) < 0) {
+-				devname[0] = '\0';
+-				stack;
+-			}
+-			break;
+-		}
+-		closedir(dir);
+-
+-		if (devname[0]) {
+-			log_debug("Found %s for %d:%d from sys", devname, major, minor);
+-			return _strdup(devname);
+-		}
+-		return NULL;
+-	}
+-
+-	/*
+-	 * $ cat /sys/dev/block/253:3/dm/name
+-	 * mpatha
+-	 */
+-	if (major == cmd->dev_types->device_mapper_major) {
+-		if (dm_snprintf(path, sizeof(path), "%sdev/block/%d:%d/dm/name",
+-				dm_sysfs_dir(), major, minor) < 0) {
+-			return NULL;
+-		}
+-
+-		if (!get_sysfs_value(path, namebuf, sizeof(namebuf), 0))
+-			return NULL;
+-
+-		if (dm_snprintf(devname, sizeof(devname), "/dev/mapper/%s", namebuf) < 0) {
+-			devname[0] = '\0';
+-			stack;
+-		}
+-
+-		if (devname[0]) {
+-			log_debug("Found %s for %d:%d from sys", devname, major, minor);
+-			return _strdup(devname);
+-		}
+-		return NULL;
+-	}
+-
+-	/*
+-	 * /proc/partitions lists
+-	 * major minor #blocks name
+-	 */
+-
+-	if (!(fp = fopen("/proc/partitions", "r")))
+-		return NULL;
+-
+-	while (fgets(line, sizeof(line), fp)) {
+-		if (sscanf(line, "%u %u %llu %s", &line_major, &line_minor, (unsigned long long *)&line_blocks, namebuf) != 4)
+-			continue;
+-		if (line_major != major)
+-			continue;
+-		if (line_minor != minor)
+-			continue;
+-
+-		if (dm_snprintf(devname, sizeof(devname), "/dev/%s", namebuf) < 0) {
+-			devname[0] = '\0';
+-			stack;
+-		}
+-		break;
+-	}
+-	fclose(fp);
+-
+-	if (devname[0]) {
+-		log_debug("Found %s for %d:%d from proc", devname, major, minor);
+-		return _strdup(devname);
+-	}
+-
+-	/*
+-	 * If necessary, this could continue searching by stat'ing /dev entries.
+-	 */
+-
+-	return NULL;
+-}
+-
+-int setup_devname_in_dev_cache(struct cmd_context *cmd, const char *devname)
+-{
+-	struct stat buf;
+-	struct device *dev;
+-
+-	if (stat(devname, &buf) < 0) {
+-		log_error("Cannot access device %s.", devname);
+-		return 0;
+-	}
+-
+-	if (!S_ISBLK(buf.st_mode)) {
+-		log_error("Invaild device type %s.", devname);
+-		return 0;
+-	}
+-
+-	if (!_insert_dev(devname, buf.st_rdev))
+-		return_0;
+-
+-	if (!(dev = (struct device *) dm_hash_lookup(_cache.names, devname)))
+-		return_0;
+-
+-	return 1;
+-}
+-
+-int setup_devno_in_dev_cache(struct cmd_context *cmd, dev_t devno)
+-{
+-	const char *devname;
+-
+-	if (!(devname = _get_devname_from_devno(cmd, devno)))
+-		return_0;
+-
+-	return setup_devname_in_dev_cache(cmd, devname);
+-}
+-
+diff --git a/lib/device/dev-cache.h b/lib/device/dev-cache.h
+index 143848d6d..635dc4fc9 100644
+--- a/lib/device/dev-cache.h
++++ b/lib/device/dev-cache.h
+@@ -77,11 +77,7 @@ int get_dm_uuid_from_sysfs(char *buf, size_t buf_size, int major, int minor);
+ 
+ int setup_devices_file(struct cmd_context *cmd);
+ int setup_devices(struct cmd_context *cmd);
++int setup_devices_no_file_match(struct cmd_context *cmd);
+ int setup_device(struct cmd_context *cmd, const char *devname);
+ 
+-/* Normal device setup functions are split up for pvscan optimization. */
+-int setup_devices_for_pvscan_cache(struct cmd_context *cmd);
+-int setup_devname_in_dev_cache(struct cmd_context *cmd, const char *devname);
+-int setup_devno_in_dev_cache(struct cmd_context *cmd, dev_t devno);
+-
+ #endif
+diff --git a/lib/device/device_id.c b/lib/device/device_id.c
+index 167bf661b..eb06109ff 100644
+--- a/lib/device/device_id.c
++++ b/lib/device/device_id.c
+@@ -1534,22 +1534,6 @@ int device_ids_match_dev(struct cmd_context *cmd, struct device *dev)
+  * passes the filter.
+  */
+ 
+-void device_ids_match_device_list(struct cmd_context *cmd)
+-{
+-	struct dev_use *du;
+-
+-	dm_list_iterate_items(du, &cmd->use_devices) {
+-		if (du->dev)
+-			continue;
+-		if (!(du->dev = dev_cache_get(cmd, du->devname, NULL))) {
+-			log_warn("Device not found for %s.", du->devname);
+-		} else {
+-			/* Should we set dev->id?  Which idtype?  Use --deviceidtype? */
+-			du->dev->flags |= DEV_MATCHED_USE_ID;
+-		}
+-	}
+-}
+-
+ void device_ids_match(struct cmd_context *cmd)
+ {
+ 	struct dev_iter *iter;
+@@ -1557,7 +1541,16 @@ void device_ids_match(struct cmd_context *cmd)
+ 	struct device *dev;
+ 
+ 	if (cmd->enable_devices_list) {
+-		device_ids_match_device_list(cmd);
++		dm_list_iterate_items(du, &cmd->use_devices) {
++			if (du->dev)
++				continue;
++			if (!(du->dev = dev_cache_get(cmd, du->devname, NULL))) {
++				log_warn("Device not found for %s.", du->devname);
++			} else {
++				/* Should we set dev->id?  Which idtype?  Use --deviceidtype? */
++				du->dev->flags |= DEV_MATCHED_USE_ID;
++			}
++		}
+ 		return;
+ 	}
+ 
+diff --git a/lib/device/device_id.h b/lib/device/device_id.h
+index 0ada35c94..939b3a0f4 100644
+--- a/lib/device/device_id.h
++++ b/lib/device/device_id.h
+@@ -32,7 +32,6 @@ int device_id_add(struct cmd_context *cmd, struct device *dev, const char *pvid,
+ void device_id_pvremove(struct cmd_context *cmd, struct device *dev);
+ void device_ids_match(struct cmd_context *cmd);
+ int device_ids_match_dev(struct cmd_context *cmd, struct device *dev);
+-void device_ids_match_device_list(struct cmd_context *cmd);
+ void device_ids_validate(struct cmd_context *cmd, struct dm_list *scanned_devs, int *device_ids_invalid, int noupdate);
+ int device_ids_version_unchanged(struct cmd_context *cmd);
+ void device_ids_find_renamed_devs(struct cmd_context *cmd, struct dm_list *dev_list, int *search_count, int noupdate);
+diff --git a/test/shell/devicesfile-basic.sh b/test/shell/devicesfile-basic.sh
+index 9c3455c76..7ba9e2c7f 100644
+--- a/test/shell/devicesfile-basic.sh
++++ b/test/shell/devicesfile-basic.sh
+@@ -283,7 +283,7 @@ not ls "$RUNDIR/lvm/pvs_online/$PVID3"
+ # arg in devices list
+ _clear_online_files
+ pvscan --devices "$dev3" --cache -aay "$dev3"
+-pvscan --devices "$dev4","$dev3" --cache -aay "$dev4"
++pvscan --devices "$dev4" --cache -aay "$dev4"
+ check lv_field $vg2/$lv2 lv_active "active"
+ vgchange -an $vg2
+ 
+diff --git a/tools/pvscan.c b/tools/pvscan.c
+index 95d593d57..8e2611361 100644
+--- a/tools/pvscan.c
++++ b/tools/pvscan.c
+@@ -857,21 +857,11 @@ static int _get_devs_from_saved_vg(struct cmd_context *cmd, const char *vgname,
+ 
+ 		devno = MKDEV(file_major, file_minor);
+ 
+-		if (!setup_devno_in_dev_cache(cmd, devno)) {
+-			log_error_pvscan(cmd, "No device set up for %d:%d PVID %s", file_major, file_minor, pvid);
+-			goto bad;
+-		}
+-
+ 		if (!(dev = dev_cache_get_by_devt(cmd, devno, NULL, NULL))) {
+ 			log_error_pvscan(cmd, "No device found for %d:%d PVID %s", file_major, file_minor, pvid);
+ 			goto bad;
+ 		}
+ 
+-		/*
+-		 * Do not need to match device_id here, see comment after
+-		 * get_devs_from_saved_vg about relying on pvid online file.
+-		 */
+-
+ 		name1 = dev_name(dev);
+ 		name2 = pvl->pv->device_hint;
+ 
+@@ -1109,11 +1099,17 @@ static int _pvscan_aa(struct cmd_context *cmd, struct pvscan_aa_params *pp,
+ 		 * PROCESS_SKIP_SCAN: we have already done lvmcache_label_scan
+ 		 * so tell process_each to skip it.
+ 		 */
++		if (do_all)
++			read_flags |= PROCESS_SKIP_SCAN;
+ 
++		/*
++		 * When the command is processing specific devs (not all), it
++		 * has done setup_devices_no_file_match() to avoid matching ids
++		 * fo all devs unnecessarily, but now that we're falling back
++		 * to process_each_vg() we need to complete the id matching.
++		 */
+ 		if (!do_all)
+-			lvmcache_label_scan(cmd);
+-
+-		read_flags |= PROCESS_SKIP_SCAN;
++			device_ids_match(cmd);
+ 
+ 		ret = process_each_vg(cmd, 0, NULL, NULL, vgnames, read_flags, 0, handle, _pvscan_aa_single);
+ 	}
+@@ -1196,15 +1192,11 @@ static int _get_args_devs(struct cmd_context *cmd, struct dm_list *pvscan_args,
+ 	/* in common usage, no dev will be found for a devno */
+ 
+ 	dm_list_iterate_items(arg, pvscan_args) {
+-		if (arg->devname) {
+-			if (!setup_devname_in_dev_cache(cmd, arg->devname))
+-				log_error_pvscan(cmd, "No device set up for name arg %s", arg->devname);
++		if (arg->devname)
+ 			arg->dev = dev_cache_get(cmd, arg->devname, NULL);
+-		} else if (arg->devno) {
+-			if (!setup_devno_in_dev_cache(cmd, arg->devno))
+-				log_error_pvscan(cmd, "No device set up for devno arg %d", (int)arg->devno);
++		else if (arg->devno)
+ 			arg->dev = dev_cache_get_by_devt(cmd, arg->devno, NULL, NULL);
+-		} else
++		else
+ 			return_0;
+ 	}
+ 
+@@ -1680,13 +1672,11 @@ static int _pvscan_cache_args(struct cmd_context *cmd, int argc, char **argv,
+ 	cmd->pvscan_cache_single = 1;
+ 
+ 	/*
+-	 * Special pvscan-specific setup steps to avoid looking
+-	 * at any devices except for device args.
+-	 * Read devices file and determine if devices file will be used.
+-	 * Does not do dev_cache_scan (adds nothing to dev-cache), and
+-	 * does not do any device id matching.
++	 * "no_file_match" means that when the devices file is used,
++	 * setup_devices will skip matching devs to devices file entries.
++	 * Specific devs must be matched later with device_ids_match_dev().
+ 	 */
+-	if (!setup_devices_for_pvscan_cache(cmd)) {
++	if (!setup_devices_no_file_match(cmd)) {
+ 		log_error_pvscan(cmd, "Failed to set up devices.");
+ 		return 0;
+ 	}
+@@ -1745,21 +1735,17 @@ static int _pvscan_cache_args(struct cmd_context *cmd, int argc, char **argv,
+ 	log_debug("pvscan_cache_args: filter devs nodata");
+ 
+ 	/*
+-	 * Match dev args with the devices file because special/optimized
+-	 * device setup was used above which does not check the devices file.
+-	 * If a match fails here do not exclude it, that will be done below by
+-	 * passes_filter() which runs filter-deviceid. The
+-	 * relax_deviceid_filter case needs to be able to work around
++	 * Match dev args with the devices file because
++	 * setup_devices_no_file_match() was used above which skipped checking
++	 * the devices file.  If a match fails here do not exclude it, that
++	 * will be done below by passes_filter() which runs filter-deviceid.
++	 * The relax_deviceid_filter case needs to be able to work around
+ 	 * unmatching devs.
+ 	 */
+-
+ 	if (cmd->enable_devices_file) {
+-		dm_list_iterate_items(devl, &pvscan_devs)
++		dm_list_iterate_items_safe(devl, devl2, &pvscan_devs)
+ 			device_ids_match_dev(cmd, devl->dev);
+-
+ 	}
+-	if (cmd->enable_devices_list)
+-		device_ids_match_device_list(cmd);
+ 
+ 	if (cmd->enable_devices_file && device_ids_use_devname(cmd)) {
+ 		relax_deviceid_filter = 1;
+-- 
+2.31.1
+
diff --git a/SOURCES/0003-pvscan-fix-messages-from-coverity-changes.patch b/SOURCES/0003-pvscan-fix-messages-from-coverity-changes.patch
new file mode 100644
index 0000000..5ff1c9d
--- /dev/null
+++ b/SOURCES/0003-pvscan-fix-messages-from-coverity-changes.patch
@@ -0,0 +1,34 @@
+From a5a2d5fa1ec47a5a548db4cf435dc84de7ce7c31 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Wed, 20 Oct 2021 16:12:41 -0500
+Subject: [PATCH 03/23] pvscan: fix messages from coverity changes
+
+---
+ tools/pvscan.c | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+diff --git a/tools/pvscan.c b/tools/pvscan.c
+index 8e2611361..f60c4a2ca 100644
+--- a/tools/pvscan.c
++++ b/tools/pvscan.c
+@@ -1354,7 +1354,7 @@ static int _online_devs(struct cmd_context *cmd, int do_all, struct dm_list *pvs
+ 		devsize = dev->size;
+ 		if (!devsize &&
+ 		    !dev_get_size(dev, &devsize)) {
+-			log_print("pvscan[%d] PV %s can get device size.", getpid(), dev_name(dev));
++			log_print_pvscan(cmd, "PV %s missing device size.", dev_name(dev));
+ 			release_vg(vg);
+ 			continue;
+ 		}
+@@ -1786,7 +1786,7 @@ static int _pvscan_cache_args(struct cmd_context *cmd, int argc, char **argv,
+ 		int has_pvid;
+ 
+ 		if (!label_read_pvid(devl->dev, &has_pvid)) {
+-			log_print("pvscan[%d] %s cannot read.", getpid(), dev_name(devl->dev));
++			log_print_pvscan(cmd, "%s cannot read label.", dev_name(devl->dev));
+ 			dm_list_del(&devl->list);
+ 			continue;
+ 		}
+-- 
+2.31.1
+
diff --git a/SOURCES/0004-vgimportdevices-skip-lvmlockd-locking.patch b/SOURCES/0004-vgimportdevices-skip-lvmlockd-locking.patch
new file mode 100644
index 0000000..d84d9d9
--- /dev/null
+++ b/SOURCES/0004-vgimportdevices-skip-lvmlockd-locking.patch
@@ -0,0 +1,39 @@
+From 074fce5c73c55e7a1547d5efff65a9f96e6db3b1 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Mon, 25 Oct 2021 12:11:17 -0500
+Subject: [PATCH 04/23] vgimportdevices: skip lvmlockd locking
+
+Help bootstrapping existing shared vgs into the devices file.
+Reading the vg in vgimportdevices would require locking to be
+started, but vgchange lockstart won't see the vg if it's not
+in the devices file.  The lvmlockd locks are not protecting
+vg modifications so skipping them here won't be a problem.
+---
+ tools/vgimportdevices.c | 11 +++++++++++
+ 1 file changed, 11 insertions(+)
+
+diff --git a/tools/vgimportdevices.c b/tools/vgimportdevices.c
+index 3f315f98f..2580613c4 100644
+--- a/tools/vgimportdevices.c
++++ b/tools/vgimportdevices.c
+@@ -172,6 +172,17 @@ int vgimportdevices(struct cmd_context *cmd, int argc, char **argv)
+ 	cmd->filter_regex_with_devices_file = 1;
+ 	cmd->create_edit_devices_file = 1;
+ 
++	/*
++	 * This helps a user bootstrap existing shared VGs into the devices
++	 * file. Reading the vg to import devices requires locking, but
++	 * lockstart won't find the vg before it's in the devices file.
++	 * So, allow importing devices without an lvmlockd lock (in a
++	 * a shared vg the vg metadata won't be updated with device ids,
++	 * so the lvmlockd lock isn't protecting vg modification.)
++	 */
++	cmd->lockd_gl_disable = 1;
++	cmd->lockd_vg_disable = 1;
++
+ 	/*
+ 	 * For each VG:
+ 	 * device_id_add() each PV in the VG
+-- 
+2.31.1
+
diff --git a/SOURCES/0005-hints-remove-the-cmd-hints-list.patch b/SOURCES/0005-hints-remove-the-cmd-hints-list.patch
new file mode 100644
index 0000000..09ef5d4
--- /dev/null
+++ b/SOURCES/0005-hints-remove-the-cmd-hints-list.patch
@@ -0,0 +1,95 @@
+From 00ebabfe6e1ebfceffcef335d44a6156a1c15418 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Mon, 1 Nov 2021 16:01:09 -0500
+Subject: [PATCH 05/23] hints: remove the cmd hints list
+
+which is no longer used after commit
+"toollib: remove all devices list from process_each_pv"
+---
+ lib/commands/toolcontext.c | 2 --
+ lib/commands/toolcontext.h | 1 -
+ lib/label/hints.c          | 1 -
+ lib/label/label.c          | 8 ++------
+ 4 files changed, 2 insertions(+), 10 deletions(-)
+
+diff --git a/lib/commands/toolcontext.c b/lib/commands/toolcontext.c
+index 105aecd5d..1b7170de1 100644
+--- a/lib/commands/toolcontext.c
++++ b/lib/commands/toolcontext.c
+@@ -1605,7 +1605,6 @@ struct cmd_context *create_config_context(void)
+ 
+ 	dm_list_init(&cmd->config_files);
+ 	dm_list_init(&cmd->tags);
+-	dm_list_init(&cmd->hints);
+ 
+ 	if (!_init_lvm_conf(cmd))
+ 		goto_out;
+@@ -1670,7 +1669,6 @@ struct cmd_context *create_toolcontext(unsigned is_clvmd,
+ 	dm_list_init(&cmd->formats);
+ 	dm_list_init(&cmd->segtypes);
+ 	dm_list_init(&cmd->tags);
+-	dm_list_init(&cmd->hints);
+ 	dm_list_init(&cmd->config_files);
+ 	label_init();
+ 
+diff --git a/lib/commands/toolcontext.h b/lib/commands/toolcontext.h
+index 701b7a739..356c79f8a 100644
+--- a/lib/commands/toolcontext.h
++++ b/lib/commands/toolcontext.h
+@@ -206,7 +206,6 @@ struct cmd_context {
+ 	 * Devices and filtering.
+ 	 */
+ 	struct dev_filter *filter;
+-	struct dm_list hints;
+ 	struct dm_list use_devices;		/* struct dev_use for each entry in devices file */
+ 	const char *md_component_checks;
+ 	const char *search_for_devnames;	/* config file setting */
+diff --git a/lib/label/hints.c b/lib/label/hints.c
+index 3dba9f8ec..e444a0c82 100644
+--- a/lib/label/hints.c
++++ b/lib/label/hints.c
+@@ -365,7 +365,6 @@ static void _unlock_hints(struct cmd_context *cmd)
+ 
+ void hints_exit(struct cmd_context *cmd)
+ {
+-	free_hints(&cmd->hints);
+ 	if (_hints_fd == -1)
+ 		return;
+ 	_unlock_hints(cmd);
+diff --git a/lib/label/label.c b/lib/label/label.c
+index 3cd912270..479a5037a 100644
+--- a/lib/label/label.c
++++ b/lib/label/label.c
+@@ -1207,8 +1207,6 @@ int label_scan(struct cmd_context *cmd)
+ 			 (unsigned long long)want_size_kb);
+ 	}
+ 
+-	dm_list_init(&cmd->hints);
+-
+ 	/*
+ 	 * If we're using hints to limit which devs we scanned, verify
+ 	 * that those hints were valid, and if not we need to scan the
+@@ -1220,18 +1218,16 @@ int label_scan(struct cmd_context *cmd)
+ 			_scan_list(cmd, cmd->filter, &all_devs, 0, NULL);
+ 			/* scan_devs are the devs that have been scanned */
+ 			dm_list_splice(&scan_devs, &all_devs);
+-			free_hints(&hints_list);
+ 			using_hints = 0;
+ 			create_hints = 0;
+ 			/* invalid hints means a new dev probably appeared and
+ 			   we should search for any missing pvids again. */
+ 			unlink_searched_devnames(cmd);
+-		} else {
+-			/* The hints may be used by another device iteration. */
+-			dm_list_splice(&cmd->hints, &hints_list);
+ 		}
+ 	}
+ 
++	free_hints(&hints_list);
++
+ 	/*
+ 	 * Check if the devices_file content is up to date and
+ 	 * if not update it.
+-- 
+2.31.1
+
diff --git a/SOURCES/0006-filter-sysfs-skip-when-device-id-is-set.patch b/SOURCES/0006-filter-sysfs-skip-when-device-id-is-set.patch
new file mode 100644
index 0000000..61d8fe7
--- /dev/null
+++ b/SOURCES/0006-filter-sysfs-skip-when-device-id-is-set.patch
@@ -0,0 +1,422 @@
+From f73be4480a5dd104a77e3ef84d7dcc80b834e593 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Tue, 2 Nov 2021 15:42:26 -0500
+Subject: [PATCH 06/23] filter-sysfs: skip when device id is set
+
+When a device id is set for a device, using an idtype other
+than devname, it means that sysfs has been used with the device
+to match the device id.  So, checking for a sysfs entry for the
+device in filter-sysfs is redundant.  For any other cases not
+covered by this (e.g. devname ids), have filter-sysfs simply
+stat /sys/dev/block/major:minor to test if the device exists
+in sysfs.
+
+The extensive processing done by filter-sysfs init is removed.
+It was taking an immense amount of time with many devices, e.g.
+. 1024 PVs in 520 VGs
+. 520 concurrent vgchange -ay <vgname> commands
+. vgchange scans only PVs in the named VG (based on pvs_online
+  files from a pending patch)
+
+A large number of the vgchange commands were taking over 1 min,
+and nearly half of that time was used by filter-sysfs init.
+With this patch, the vgchange commands take about half the time.
+---
+ lib/commands/toolcontext.c |  24 ++-
+ lib/filters/filter-sysfs.c | 296 +++----------------------------------
+ 2 files changed, 32 insertions(+), 288 deletions(-)
+
+diff --git a/lib/commands/toolcontext.c b/lib/commands/toolcontext.c
+index 1b7170de1..a0c78ddd6 100644
+--- a/lib/commands/toolcontext.c
++++ b/lib/commands/toolcontext.c
+@@ -1143,19 +1143,6 @@ static struct dev_filter *_init_filter_chain(struct cmd_context *cmd)
+ 	 * Update MAX_FILTERS definition above when adding new filters.
+ 	 */
+ 
+-	/*
+-	 * sysfs filter. Only available on 2.6 kernels.  Non-critical.
+-	 * Listed first because it's very efficient at eliminating
+-	 * unavailable devices.
+-	 *
+-	 * TODO: I suspect that using the lvm_type and device_id
+-	 * filters before this one may be more efficient.
+-	 */
+-	if (find_config_tree_bool(cmd, devices_sysfs_scan_CFG, NULL)) {
+-		if ((filters[nr_filt] = sysfs_filter_create()))
+-			nr_filt++;
+-	}
+-
+ 	/* internal filter used by command processing. */
+ 	if (!(filters[nr_filt] = internal_filter_create())) {
+ 		log_error("Failed to create internal device filter");
+@@ -1195,6 +1182,17 @@ static struct dev_filter *_init_filter_chain(struct cmd_context *cmd)
+ 	}
+ 	nr_filt++;
+ 
++	/*
++	 * sysfs filter. Only available on 2.6 kernels.  Non-critical.
++	 * Eliminates unavailable devices.
++	 * TODO: this may be unnecessary now with device ids
++	 * (currently not used for devs match to device id using syfs)
++	 */
++	if (find_config_tree_bool(cmd, devices_sysfs_scan_CFG, NULL)) {
++		if ((filters[nr_filt] = sysfs_filter_create()))
++			nr_filt++;
++	}
++
+ 	/* usable device filter. Required. */
+ 	if (!(filters[nr_filt] = usable_filter_create(cmd, cmd->dev_types, FILTER_MODE_NO_LVMETAD))) {
+ 		log_error("Failed to create usabled device filter");
+diff --git a/lib/filters/filter-sysfs.c b/lib/filters/filter-sysfs.c
+index 32ac324dd..672211057 100644
+--- a/lib/filters/filter-sysfs.c
++++ b/lib/filters/filter-sysfs.c
+@@ -17,288 +17,49 @@
+ 
+ #ifdef __linux__
+ 
+-#include <sys/sysmacros.h>
+-#include <dirent.h>
+-
+-static int _locate_sysfs_blocks(const char *sysfs_dir, char *path, size_t len,
+-				unsigned *sysfs_depth)
++static int _accept_p(struct cmd_context *cmd, struct dev_filter *f, struct device *dev, const char *use_filter_name)
+ {
++	char path[PATH_MAX];
++	const char *sysfs_dir;
+ 	struct stat info;
+-	unsigned i;
+-	static const struct dir_class {
+-		const char path[32];
+-		int depth;
+-	} classes[] = {
+-		/*
+-		 * unified classification directory for all kernel subsystems
+-		 *
+-		 * /sys/subsystem/block/devices
+-		 * |-- sda -> ../../../devices/pci0000:00/0000:00:1f.2/host0/target0:0:0/0:0:0:0/block/sda
+-		 * |-- sda1 -> ../../../devices/pci0000:00/0000:00:1f.2/host0/target0:0:0/0:0:0:0/block/sda/sda1
+-		 *  `-- sr0 -> ../../../devices/pci0000:00/0000:00:1f.2/host1/target1:0:0/1:0:0:0/block/sr0
+-		 *
+-		 */
+-		{ "subsystem/block/devices", 0 },
+-
+-		/*
+-		 * block subsystem as a class
+-		 *
+-		 * /sys/class/block
+-		 * |-- sda -> ../../devices/pci0000:00/0000:00:1f.2/host0/target0:0:0/0:0:0:0/block/sda
+-		 * |-- sda1 -> ../../devices/pci0000:00/0000:00:1f.2/host0/target0:0:0/0:0:0:0/block/sda/sda1
+-		 *  `-- sr0 -> ../../devices/pci0000:00/0000:00:1f.2/host1/target1:0:0/1:0:0:0/block/sr0
+-		 *
+-		 */
+-		{ "class/block", 0 },
+-
+-		/*
+-		 * old block subsystem layout with nested directories
+-		 *
+-		 * /sys/block/
+-		 * |-- sda
+-		 * |   |-- capability
+-		 * |   |-- dev
+-		 * ...
+-		 * |   |-- sda1
+-		 * |   |   |-- dev
+-		 * ...
+-		 * |
+-		 * `-- sr0
+-		 *     |-- capability
+-		 *     |-- dev
+-		 * ...
+-		 *
+-		 */
+-
+-		{ "block", 1 }
+-	};
+-
+-	for (i = 0; i < DM_ARRAY_SIZE(classes); ++i)
+-		if ((dm_snprintf(path, len, "%s%s", sysfs_dir, classes[i].path) >= 0) &&
+-		    (stat(path, &info) == 0)) {
+-			*sysfs_depth = classes[i].depth;
+-			return 1;
+-		}
+-
+-	return 0;
+-}
+-
+-/*----------------------------------------------------------------
+- * We need to store a set of dev_t.
+- *--------------------------------------------------------------*/
+-struct entry {
+-	struct entry *next;
+-	dev_t dev;
+-};
+-
+-#define SET_BUCKETS 64
+-struct dev_set {
+-	struct dm_pool *mem;
+-	const char *sys_block;
+-	unsigned sysfs_depth;
+-	int initialised;
+-	struct entry *slots[SET_BUCKETS];
+-};
+-
+-static struct dev_set *_dev_set_create(struct dm_pool *mem,
+-				       const char *sys_block,
+-				       unsigned sysfs_depth)
+-{
+-	struct dev_set *ds;
+-
+-	if (!(ds = dm_pool_zalloc(mem, sizeof(*ds))))
+-		return NULL;
+-
+-	ds->mem = mem;
+-	if (!(ds->sys_block = dm_pool_strdup(mem, sys_block)))
+-		return NULL;
+-
+-	ds->sysfs_depth = sysfs_depth;
+-	ds->initialised = 0;
+-
+-	return ds;
+-}
+-
+-static unsigned _hash_dev(dev_t dev)
+-{
+-	return (major(dev) ^ minor(dev)) & (SET_BUCKETS - 1);
+-}
+ 
+-/*
+- * Doesn't check that the set already contains dev.
+- */
+-static int _set_insert(struct dev_set *ds, dev_t dev)
+-{
+-	struct entry *e;
+-	unsigned h = _hash_dev(dev);
+-
+-	if (!(e = dm_pool_alloc(ds->mem, sizeof(*e))))
+-		return 0;
+-
+-	e->next = ds->slots[h];
+-	e->dev = dev;
+-	ds->slots[h] = e;
+-
+-	return 1;
+-}
++	dev->filtered_flags &= ~DEV_FILTERED_SYSFS;
+ 
+-static int _set_lookup(struct dev_set *ds, dev_t dev)
+-{
+-	unsigned h = _hash_dev(dev);
+-	struct entry *e;
++	/*
++	 * Any kind of device id other than devname has been set
++	 * using sysfs so we know that sysfs info exists for dev.
++	 */
++	if (dev->id && dev->id->idtype && (dev->id->idtype != DEV_ID_TYPE_DEVNAME))
++		return 1;
+ 
+-	for (e = ds->slots[h]; e; e = e->next)
+-		if (e->dev == dev)
++	sysfs_dir = dm_sysfs_dir();
++	if (sysfs_dir && *sysfs_dir) {
++		if (dm_snprintf(path, sizeof(path), "%sdev/block/%d:%d",
++				sysfs_dir, (int)MAJOR(dev->dev), (int)MINOR(dev->dev)) < 0) {
++			log_debug("failed to create sysfs path");
+ 			return 1;
+-
+-	return 0;
+-}
+-
+-/*----------------------------------------------------------------
+- * filter methods
+- *--------------------------------------------------------------*/
+-static int _parse_dev(const char *file, FILE *fp, dev_t *result)
+-{
+-	unsigned major, minor;
+-	char buffer[64];
+-
+-	if (!fgets(buffer, sizeof(buffer), fp)) {
+-		log_error("Empty sysfs device file: %s", file);
+-		return 0;
+-	}
+-
+-	if (sscanf(buffer, "%u:%u", &major, &minor) != 2) {
+-		log_error("Incorrect format for sysfs device file: %s.", file);
+-		return 0;
+-	}
+-
+-	*result = makedev(major, minor);
+-	return 1;
+-}
+-
+-static int _read_dev(const char *file, dev_t *result)
+-{
+-	int r;
+-	FILE *fp;
+-
+-	if (!(fp = fopen(file, "r"))) {
+-		log_sys_error("fopen", file);
+-		return 0;
+-	}
+-
+-	r = _parse_dev(file, fp, result);
+-
+-	if (fclose(fp))
+-		log_sys_error("fclose", file);
+-
+-	return r;
+-}
+-
+-/*
+- * Recurse through sysfs directories, inserting any devs found.
+- */
+-static int _read_devs(struct dev_set *ds, const char *dir, unsigned sysfs_depth)
+-{
+-	struct dirent *d;
+-	DIR *dr;
+-	struct stat info;
+-	char path[PATH_MAX];
+-	char file[PATH_MAX];
+-	dev_t dev = { 0 };
+-	int r = 1;
+-
+-	if (!(dr = opendir(dir))) {
+-		log_sys_error("opendir", dir);
+-		return 0;
+-	}
+-
+-	while ((d = readdir(dr))) {
+-		if (!strcmp(d->d_name, ".") || !strcmp(d->d_name, ".."))
+-			continue;
+-
+-		if (dm_snprintf(path, sizeof(path), "%s/%s", dir,
+-				 d->d_name) < 0) {
+-			log_warn("WARNING: sysfs path name too long: %s in %s.",
+-				 d->d_name, dir);
+-			continue;
+ 		}
+ 
+-		/* devices have a "dev" file */
+-		if (dm_snprintf(file, sizeof(file), "%s/dev", path) < 0) {
+-			log_warn("WARNING: sysfs path name too long: %s in %s.",
+-				 d->d_name, dir);
+-			continue;
+-		}
+-
+-		if (!stat(file, &info)) {
+-			/* recurse if we found a device and expect subdirs */
+-			if (sysfs_depth)
+-				_read_devs(ds, path, sysfs_depth - 1);
+-
+-			/* add the device we have found */
+-			if (_read_dev(file, &dev))
+-				_set_insert(ds, dev);
++		if (lstat(path, &info)) {
++			log_debug_devs("%s: Skipping (sysfs)", dev_name(dev));
++			dev->filtered_flags |= DEV_FILTERED_SYSFS;
++			return 0;
+ 		}
+ 	}
+ 
+-	if (closedir(dr))
+-		log_sys_debug("closedir", dir);
+-
+-	return r;
+-}
+-
+-static int _init_devs(struct dev_set *ds)
+-{
+-	if (!_read_devs(ds, ds->sys_block, ds->sysfs_depth)) {
+-		ds->initialised = -1;
+-		return 0;
+-	}
+-
+-	ds->initialised = 1;
+-
+-	return 1;
+-}
+-
+-
+-static int _accept_p(struct cmd_context *cmd, struct dev_filter *f, struct device *dev, const char *use_filter_name)
+-{
+-	struct dev_set *ds = (struct dev_set *) f->private;
+-
+-	dev->filtered_flags &= ~DEV_FILTERED_SYSFS;
+-
+-	if (!ds->initialised)
+-		_init_devs(ds);
+-
+-	/* Pass through if initialisation failed */
+-	if (ds->initialised != 1)
+-		return 1;
+-
+-	if (!_set_lookup(ds, dev->dev)) {
+-		log_debug_devs("%s: Skipping (sysfs)", dev_name(dev));
+-		dev->filtered_flags |= DEV_FILTERED_SYSFS;
+-		return 0;
+-	}
+-
+ 	return 1;
+ }
+ 
+ static void _destroy(struct dev_filter *f)
+ {
+-	struct dev_set *ds = (struct dev_set *) f->private;
+-
+ 	if (f->use_count)
+ 		log_error(INTERNAL_ERROR "Destroying sysfs filter while in use %u times.", f->use_count);
+-
+-	dm_pool_destroy(ds->mem);
++	free(f);
+ }
+ 
+ struct dev_filter *sysfs_filter_create(void)
+ {
+ 	const char *sysfs_dir = dm_sysfs_dir();
+-	char sys_block[PATH_MAX];
+-	unsigned sysfs_depth;
+-	struct dm_pool *mem;
+-	struct dev_set *ds;
+ 	struct dev_filter *f;
+ 
+ 	if (!*sysfs_dir) {
+@@ -306,26 +67,12 @@ struct dev_filter *sysfs_filter_create(void)
+ 		return NULL;
+ 	}
+ 
+-	if (!_locate_sysfs_blocks(sysfs_dir, sys_block, sizeof(sys_block), &sysfs_depth))
+-		return NULL;
+-
+-	if (!(mem = dm_pool_create("sysfs", 256))) {
+-		log_error("sysfs pool creation failed");
+-		return NULL;
+-	}
+-
+-	if (!(ds = _dev_set_create(mem, sys_block, sysfs_depth))) {
+-		log_error("sysfs dev_set creation failed");
+-		goto bad;
+-	}
+-
+-	if (!(f = dm_pool_zalloc(mem, sizeof(*f))))
++	if (!(f = zalloc(sizeof(*f))))
+ 		goto_bad;
+ 
+ 	f->passes_filter = _accept_p;
+ 	f->destroy = _destroy;
+ 	f->use_count = 0;
+-	f->private = ds;
+ 	f->name = "sysfs";
+ 
+ 	log_debug_devs("Sysfs filter initialised.");
+@@ -333,7 +80,6 @@ struct dev_filter *sysfs_filter_create(void)
+ 	return f;
+ 
+  bad:
+-	dm_pool_destroy(mem);
+ 	return NULL;
+ }
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0007-lvmdevices-increase-open-file-limit.patch b/SOURCES/0007-lvmdevices-increase-open-file-limit.patch
new file mode 100644
index 0000000..6a586d7
--- /dev/null
+++ b/SOURCES/0007-lvmdevices-increase-open-file-limit.patch
@@ -0,0 +1,61 @@
+From f732f3d53faee3732d0f4a666c378709e6c2f5e9 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Fri, 29 Oct 2021 14:49:36 -0500
+Subject: [PATCH 07/23] lvmdevices: increase open file limit
+
+---
+ lib/label/label.c  | 4 ++--
+ lib/label/label.h  | 2 ++
+ tools/lvmdevices.c | 3 +++
+ 3 files changed, 7 insertions(+), 2 deletions(-)
+
+diff --git a/lib/label/label.c b/lib/label/label.c
+index 479a5037a..9fac3e464 100644
+--- a/lib/label/label.c
++++ b/lib/label/label.c
+@@ -891,7 +891,7 @@ static int _setup_bcache(void)
+ 
+ #define BASE_FD_COUNT 32 /* Number of open files we want apart from devs */
+ 
+-static void _prepare_open_file_limit(struct cmd_context *cmd, unsigned int num_devs)
++void prepare_open_file_limit(struct cmd_context *cmd, unsigned int num_devs)
+ {
+ #ifdef HAVE_PRLIMIT
+ 	struct rlimit old = { 0 }, new;
+@@ -1165,7 +1165,7 @@ int label_scan(struct cmd_context *cmd)
+ 	 * which we want to keep open) is higher than the current
+ 	 * soft limit.
+ 	 */
+-	_prepare_open_file_limit(cmd, dm_list_size(&scan_devs));
++	prepare_open_file_limit(cmd, dm_list_size(&scan_devs));
+ 
+ 	/*
+ 	 * Do the main scan.
+diff --git a/lib/label/label.h b/lib/label/label.h
+index 8b510eb79..34563efd0 100644
+--- a/lib/label/label.h
++++ b/lib/label/label.h
+@@ -134,4 +134,6 @@ void dev_invalidate(struct device *dev);
+ void dev_set_last_byte(struct device *dev, uint64_t offset);
+ void dev_unset_last_byte(struct device *dev);
+ 
++void prepare_open_file_limit(struct cmd_context *cmd, unsigned int num_devs);
++
+ #endif
+diff --git a/tools/lvmdevices.c b/tools/lvmdevices.c
+index 8d9634848..3f104f7de 100644
+--- a/tools/lvmdevices.c
++++ b/tools/lvmdevices.c
+@@ -176,6 +176,9 @@ int lvmdevices(struct cmd_context *cmd, int argc, char **argv)
+ 		log_error("Failed to read the devices file.");
+ 		return ECMD_FAILED;
+ 	}
++
++	prepare_open_file_limit(cmd, dm_list_size(&cmd->use_devices));
++
+ 	dev_cache_scan(cmd);
+ 	device_ids_match(cmd);
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0008-filter-sysfs-support-old-kernels-without-sys-dev-blo.patch b/SOURCES/0008-filter-sysfs-support-old-kernels-without-sys-dev-blo.patch
new file mode 100644
index 0000000..cd4a4e3
--- /dev/null
+++ b/SOURCES/0008-filter-sysfs-support-old-kernels-without-sys-dev-blo.patch
@@ -0,0 +1,73 @@
+From fad2b3dc8c44ba1222508ee78b5f161994efe638 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Tue, 9 Nov 2021 11:54:48 -0600
+Subject: [PATCH 08/23] filter-sysfs: support old kernels without sys/dev/block
+
+rhel5 for example doesn't have /sys/dev/block
+---
+ lib/filters/filter-sysfs.c | 28 ++++++++++++++++++++++++++++
+ 1 file changed, 28 insertions(+)
+
+diff --git a/lib/filters/filter-sysfs.c b/lib/filters/filter-sysfs.c
+index 672211057..d8de7940b 100644
+--- a/lib/filters/filter-sysfs.c
++++ b/lib/filters/filter-sysfs.c
+@@ -15,6 +15,8 @@
+ #include "lib/misc/lib.h"
+ #include "lib/filters/filter.h"
+ 
++static int _sys_dev_block_found;
++
+ #ifdef __linux__
+ 
+ static int _accept_p(struct cmd_context *cmd, struct dev_filter *f, struct device *dev, const char *use_filter_name)
+@@ -23,6 +25,9 @@ static int _accept_p(struct cmd_context *cmd, struct dev_filter *f, struct devic
+ 	const char *sysfs_dir;
+ 	struct stat info;
+ 
++	if (!_sys_dev_block_found)
++		return 1;
++
+ 	dev->filtered_flags &= ~DEV_FILTERED_SYSFS;
+ 
+ 	/*
+@@ -57,6 +62,26 @@ static void _destroy(struct dev_filter *f)
+ 	free(f);
+ }
+ 
++static void _check_sys_dev_block(void)
++{
++	char path[PATH_MAX];
++	const char *sysfs_dir;
++	struct stat info;
++
++	sysfs_dir = dm_sysfs_dir();
++	if (sysfs_dir && *sysfs_dir) {
++		if (dm_snprintf(path, sizeof(path), "%sdev/block", sysfs_dir) < 0)
++			return;
++
++		if (lstat(path, &info)) {
++			log_debug("filter-sysfs disabled: /sys/dev/block not found");
++			_sys_dev_block_found = 0;
++		} else {
++			_sys_dev_block_found = 1;
++		}
++	}
++}
++
+ struct dev_filter *sysfs_filter_create(void)
+ {
+ 	const char *sysfs_dir = dm_sysfs_dir();
+@@ -67,6 +92,9 @@ struct dev_filter *sysfs_filter_create(void)
+ 		return NULL;
+ 	}
+ 
++	/* support old kernels that don't have this */
++	_check_sys_dev_block();
++
+ 	if (!(f = zalloc(sizeof(*f))))
+ 		goto_bad;
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0009-device_id-match-different-dm-device-names.patch b/SOURCES/0009-device_id-match-different-dm-device-names.patch
new file mode 100644
index 0000000..94ec305
--- /dev/null
+++ b/SOURCES/0009-device_id-match-different-dm-device-names.patch
@@ -0,0 +1,155 @@
+From 459d931a9bfe4c9adcbbf2e76fdf35fda5b13c61 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Fri, 12 Nov 2021 16:42:51 -0600
+Subject: [PATCH 09/23] device_id: match different dm device names
+
+If a devices file entry for a dm device is using the devname
+for the device id, then recognize different dm names as matching.
+---
+ lib/device/device_id.c | 81 +++++++++++++++++++++++++++++++++++-------
+ 1 file changed, 69 insertions(+), 12 deletions(-)
+
+diff --git a/lib/device/device_id.c b/lib/device/device_id.c
+index eb06109ff..dea739fc4 100644
+--- a/lib/device/device_id.c
++++ b/lib/device/device_id.c
+@@ -1360,6 +1360,10 @@ void device_id_update_vg_uuid(struct cmd_context *cmd, struct volume_group *vg,
+ 
+ static int _idtype_compatible_with_major_number(struct cmd_context *cmd, int idtype, int major)
+ {
++	/* devname can be used with any kind of device */
++	if (idtype == DEV_ID_TYPE_DEVNAME)
++		return 1;
++
+ 	if (idtype == DEV_ID_TYPE_MPATH_UUID ||
+ 	    idtype == DEV_ID_TYPE_CRYPT_UUID ||
+ 	    idtype == DEV_ID_TYPE_LVMLV_UUID)
+@@ -1388,6 +1392,43 @@ static int _idtype_compatible_with_major_number(struct cmd_context *cmd, int idt
+ 	return 1;
+ }
+ 
++static int _match_dm_devnames(struct cmd_context *cmd, struct device *dev,
++			      struct dev_id *id, struct dev_use *du)
++{
++	struct stat buf;
++
++	if (MAJOR(dev->dev) != cmd->dev_types->device_mapper_major)
++		return 0;
++
++	if (id->idname && du->idname && !strcmp(id->idname, du->idname))
++		return 1;
++
++	if (du->idname && !strcmp(du->idname, dev_name(dev))) {
++		log_debug("Match device_id %s %s to %s: ignoring idname %s",
++			  idtype_to_str(du->idtype), du->idname, dev_name(dev), id->idname ?: ".");
++		return 1;
++	}
++
++	if (!du->idname)
++		return 0;
++
++	/* detect that a du entry is for a dm device */
++
++	if (!strncmp(du->idname, "/dev/dm-", 8) || !strncmp(du->idname, "/dev/mapper/", 12)) {
++		if (stat(du->idname, &buf))
++			return 0;
++
++		if ((MAJOR(buf.st_rdev) == cmd->dev_types->device_mapper_major) &&
++		    (MINOR(buf.st_rdev) == MINOR(dev->dev))) {
++			log_debug("Match device_id %s %s to %s: using other dm name, ignoring %s",
++				  idtype_to_str(du->idtype), du->idname, dev_name(dev), id->idname ?: ".");
++			return 1;
++		}
++	}
++
++	return 0;
++}
++
+ /*
+  * check for dev->ids entry with du->idtype, if found compare it,
+  * if not, system_read of this type and add entry to dev->ids, compare it.
+@@ -1408,35 +1449,52 @@ static int _match_du_to_dev(struct cmd_context *cmd, struct dev_use *du, struct
+ 	 * so we can skip trying to match certain du entries based simply on
+ 	 * the major number of dev.
+ 	 */
+-	if (!_idtype_compatible_with_major_number(cmd, du->idtype, (int)MAJOR(dev->dev)))
++	if (!_idtype_compatible_with_major_number(cmd, du->idtype, (int)MAJOR(dev->dev))) {
++		/*
++		log_debug("Mismatch device_id %s %s to %s: wrong major",
++			  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev));
++		*/
+ 		return 0;
++	}
+ 
+ 	if (!dev_get_partition_number(dev, &part)) {
+-		log_debug("compare %s failed to get dev partition", dev_name(dev));
++		/*
++		log_debug("Mismatch device_id %s %s to %s: no partition",
++			  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev));
++		*/
+ 		return 0;
+ 	}
+ 	if (part != du->part) {
+ 		/*
+-		log_debug("compare mis %s %s part %d to %s part %d",
+-			  idtype_to_str(du->idtype), du->idname ?: ".", du->part, dev_name(dev), part);
++		log_debug("Mismatch device_id %s %s to %s: wrong partition %d vs %d",
++			  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev), du->part, part);
+ 		*/
+ 		return 0;
+ 	}
+ 
+ 	dm_list_iterate_items(id, &dev->ids) {
+ 		if (id->idtype == du->idtype) {
+-			if (id->idname && !strcmp(id->idname, du->idname)) {
++			if ((id->idtype == DEV_ID_TYPE_DEVNAME) && _match_dm_devnames(cmd, dev, id, du)) {
++				/* dm devs can have differing names that we know still match */
++				du->dev = dev;
++				dev->id = id;
++				dev->flags |= DEV_MATCHED_USE_ID;
++				log_debug("Match device_id %s %s to %s: dm names",
++					  idtype_to_str(du->idtype), du->idname, dev_name(dev));
++				return 1;
++
++			} else if (id->idname && !strcmp(id->idname, du->idname)) {
+ 				du->dev = dev;
+ 				dev->id = id;
+ 				dev->flags |= DEV_MATCHED_USE_ID;
+ 				log_debug("Match device_id %s %s to %s",
+ 					  idtype_to_str(du->idtype), du->idname, dev_name(dev));
+ 				return 1;
++
+ 			} else {
+ 				/*
+-				log_debug("compare mis %s %s to %s %s",
+-			  		  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev),
+-					  ((id->idtype != DEV_ID_TYPE_DEVNAME) && id->idname) ? id->idname : "");
++				log_debug("Mismatch device_id %s %s to %s: idname %s",
++			  		  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev), id->idname ?: ":");
+ 				*/
+ 				return 0;
+ 			}
+@@ -1456,7 +1514,7 @@ static int _match_du_to_dev(struct cmd_context *cmd, struct dev_use *du, struct
+ 		id->dev = dev;
+ 		dm_list_add(&dev->ids, &id->list);
+ 		/*
+-		log_debug("compare mis %s %s to %s no idtype",
++		log_debug("Mismatch device_id %s %s to %s: no idtype",
+ 			  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev));
+ 		*/
+ 		return 0;
+@@ -1481,9 +1539,8 @@ static int _match_du_to_dev(struct cmd_context *cmd, struct dev_use *du, struct
+ 	}
+ 
+ 	/*
+-	log_debug("compare mis %s %s to %s %s",
+-		  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev),
+-		  ((id->idtype != DEV_ID_TYPE_DEVNAME) && id->idname) ? id->idname : "");
++	log_debug("Mismatch device_id %s %s to %s: idname %s",
++		  idtype_to_str(du->idtype), du->idname ?: ".", dev_name(dev), idname);
+ 	*/
+ 	return 0;
+ }
+-- 
+2.31.1
+
diff --git a/SOURCES/0010-device_id-fix-search-on-filtered-device.patch b/SOURCES/0010-device_id-fix-search-on-filtered-device.patch
new file mode 100644
index 0000000..edc2d3e
--- /dev/null
+++ b/SOURCES/0010-device_id-fix-search-on-filtered-device.patch
@@ -0,0 +1,134 @@
+From 5533cd7bf4c1edc5d8fb0e95d2f83b2b2d446339 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Tue, 16 Nov 2021 09:29:24 -0600
+Subject: [PATCH 10/23] device_id: fix search on filtered device
+
+When devnames are used as device ids and devnames change,
+then new devices need to be located for the PVs.  If the old
+devname is now used by a filtered device, this was preventing
+the code from searching for the new device, so the PV was
+reported as missing.
+---
+ lib/device/device_id.c            | 16 ++++++-
+ test/shell/devicesfile-devname.sh | 69 +++++++++++++++++++++++++++++++
+ 2 files changed, 83 insertions(+), 2 deletions(-)
+
+diff --git a/lib/device/device_id.c b/lib/device/device_id.c
+index dea739fc4..48f1682a3 100644
+--- a/lib/device/device_id.c
++++ b/lib/device/device_id.c
+@@ -2025,12 +2025,19 @@ void device_ids_find_renamed_devs(struct cmd_context *cmd, struct dm_list *dev_l
+ 	search_auto = !strcmp(cmd->search_for_devnames, "auto");
+ 
+ 	dm_list_iterate_items(du, &cmd->use_devices) {
+-		if (du->dev)
+-			continue;
+ 		if (!du->pvid)
+ 			continue;
+ 		if (du->idtype != DEV_ID_TYPE_DEVNAME)
+ 			continue;
++
++		/*
++		 * if the old incorrect devname is now a device that's
++		 * filtered and not scanned, e.g. an mpath component,
++		 * then we want to look for the pvid on a new device.
++		 */
++		if (du->dev && !du->dev->filtered_flags)
++			continue;
++
+ 		if (!(dil = dm_pool_zalloc(cmd->mem, sizeof(*dil))))
+ 			continue;
+ 
+@@ -2055,6 +2062,11 @@ void device_ids_find_renamed_devs(struct cmd_context *cmd, struct dm_list *dev_l
+ 	 * the searched file, so a subsequent lvm command will do the search
+ 	 * again.  In future perhaps we could add a policy to automatically
+ 	 * remove a devices file entry that's not been found for some time.
++	 *
++	 * TODO: like the hint file, add a hash of all devnames to the searched
++	 * file so it can be ignored and removed if the devs/hash change.
++	 * If hints are enabled, the hints invalidation could also remove the
++	 * searched file.
+ 	 */
+ 	if (_searched_devnames_exists(cmd)) {
+ 		log_debug("Search for PVIDs skipped for %s", _searched_file);
+diff --git a/test/shell/devicesfile-devname.sh b/test/shell/devicesfile-devname.sh
+index f95be52b1..a99fe3e9a 100644
+--- a/test/shell/devicesfile-devname.sh
++++ b/test/shell/devicesfile-devname.sh
+@@ -545,4 +545,73 @@ grep "$PVID2" "$DF" |tee out
+ grep "$dev2" out
+ not grep "$dev1" out
+ 
++vgchange -an $vg1
++vgchange -an $vg2
++vgremove -ff $vg1
++vgremove -ff $vg2
++
++# devnames change so the new devname now refers to a filtered device,
++# e.g. an mpath or md component, which is not scanned
++
++wait_md_create() {
++        local md=$1
++
++        while :; do
++                if ! grep "$(basename $md)" /proc/mdstat; then
++                        echo "$md not ready"
++                        cat /proc/mdstat
++                        sleep 2
++                else
++                        break
++                fi
++        done
++        echo "$md" > WAIT_MD_DEV
++}
++
++aux wipefs_a "$dev1"
++aux wipefs_a "$dev2"
++aux wipefs_a "$dev3"
++aux wipefs_a "$dev4"
++
++mddev="/dev/md33"
++not grep $mddev /proc/mdstat || skip
++
++rm "$DF"
++touch "$DF"
++vgcreate $vg1 "$dev1" "$dev2"
++cat "$DF"
++cp "$DF" "$ORIG"
++
++# PVID with dashes for matching pvs -o+uuid output
++OPVID1=`pvs "$dev1" --noheading -o uuid | awk '{print $1}'`
++OPVID2=`pvs "$dev2" --noheading -o uuid | awk '{print $1}'`
++
++# PVID without dashes for matching devices file fields
++PVID1=`pvs "$dev1" --noheading -o uuid | tr -d - | awk '{print $1}'`
++PVID2=`pvs "$dev2" --noheading -o uuid | tr -d - | awk '{print $1}'`
++
++mdadm --create --metadata=1.0 "$mddev" --level 1 --chunk=64 --raid-devices=2 "$dev3" "$dev4"
++wait_md_create "$mddev"
++
++sed -e "s|DEVNAME=$dev1|DEVNAME=$dev3|" "$ORIG" > tmp1.devices
++sed -e "s|IDNAME=$dev1|IDNAME=$dev3|" tmp1.devices > "$DF"
++cat "$DF"
++pvs -o+uuid |tee out
++grep "$dev1" out
++grep "$dev2" out
++grep "$OPVID1" out
++grep "$OPVID2" out
++not grep "$dev3" out
++not grep "$dev4" out
++
++grep "$dev1" "$DF"
++grep "$dev2" "$DF"
++grep "$PVID1" "$DF"
++grep "$PVID2" "$DF"
++not grep "$dev3" "$DF"
++not grep "$dev4" "$DF"
++
++mdadm --stop "$mddev"
++aux udev_wait
++
+ vgremove -ff $vg1
+-- 
+2.31.1
+
diff --git a/SOURCES/0011-device_id-searched_devnames-improvements.patch b/SOURCES/0011-device_id-searched_devnames-improvements.patch
new file mode 100644
index 0000000..d8a658e
--- /dev/null
+++ b/SOURCES/0011-device_id-searched_devnames-improvements.patch
@@ -0,0 +1,102 @@
+From 39adf3e513ac7b1cbbbf0189f973573ade3c8939 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Tue, 16 Nov 2021 11:26:41 -0600
+Subject: [PATCH 11/23] device_id: searched_devnames improvements
+
+Remove the searched_devnames file in a couple more places:
+. When hints need refreshing it's possible that a missing
+  devices file entry could be found by searching devices
+  again.
+. When a devices file entry devname is first found to be
+  incorrect, a new search for missing entries may be
+  useful.
+---
+ lib/device/device_id.c | 28 ++++++++++++++++++++++++++--
+ lib/label/hints.c      | 10 ++++++++++
+ 2 files changed, 36 insertions(+), 2 deletions(-)
+
+diff --git a/lib/device/device_id.c b/lib/device/device_id.c
+index 48f1682a3..ce7ded154 100644
+--- a/lib/device/device_id.c
++++ b/lib/device/device_id.c
+@@ -74,6 +74,8 @@ void unlink_searched_devnames(struct cmd_context *cmd)
+ 
+ 	if (unlink(_searched_file))
+ 		log_debug("unlink %s errno %d", _searched_file, errno);
++	else
++		log_debug("unlink %s", _searched_file);
+ }
+ 
+ static int _searched_devnames_exists(struct cmd_context *cmd)
+@@ -780,7 +782,7 @@ static void _device_ids_update_try(struct cmd_context *cmd)
+ 
+ 	/* Defer updates to non-pvscan-cache commands. */
+ 	if (cmd->pvscan_cache_single) {
+-		log_print("pvscan[%d] skip updating devices file.", getpid());
++		log_print("Devices file update skipped."); 
+ 		return;
+ 	}
+ 
+@@ -1441,8 +1443,22 @@ static int _match_du_to_dev(struct cmd_context *cmd, struct dev_use *du, struct
+ 	const char *idname;
+ 	int part;
+ 
+-	if (!du->idname || !du->idtype)
++	/*
++	 * The idname will be removed from an entry with devname type when the
++	 * devname is read and found to hold a different PVID than the PVID in
++	 * the entry.  At that point we only have the PVID and no known
++	 * location for it.
++	 */
++	if (!du->idname || !du->idtype) {
++		/*
++		log_debug("Mismatch device_id %s %s %s to %s",
++			  du->idtype ? idtype_to_str(du->idtype) : "idtype_missing",
++			  du->idname ? du->idname : "idname_missing",
++			  du->devname ? du->devname : "devname_missing",
++			  dev_name(dev));
++		*/
+ 		return 0;
++	}
+ 
+ 	/*
+ 	 * Some idtypes can only match devices with a specific major number,
+@@ -1957,6 +1973,14 @@ void device_ids_validate(struct cmd_context *cmd, struct dm_list *scanned_devs,
+ 			*device_ids_invalid = 1;
+ 	}
+ 
++	/*
++	 * When a new devname/pvid mismatch is discovered, a new search for the
++	 * pvid should be permitted (searched_devnames may exist to suppress
++	 * searching for other pvids.)
++	 */
++	if (update_file)
++		unlink_searched_devnames(cmd);
++
+ 	/* FIXME: for wrong devname cases, wait to write new until device_ids_find_renamed_devs? */
+ 
+ 	/*
+diff --git a/lib/label/hints.c b/lib/label/hints.c
+index e444a0c82..3ce9634f2 100644
+--- a/lib/label/hints.c
++++ b/lib/label/hints.c
+@@ -1390,6 +1390,16 @@ int get_hints(struct cmd_context *cmd, struct dm_list *hints_out, int *newhints,
+ 		log_debug("get_hints: needs refresh");
+ 		free_hints(&hints_list);
+ 
++		/*
++		 * This is not related to hints, and is probably unnecessary,
++		 * but it could possibly help.  When hints become invalid it's
++		 * usually becaues devs on the system have changed, and that
++		 * also means that a missing devices file entry might be found
++		 * by searching devices again.  (the searched_devnames
++		 * mechanism should eventually be replaced)
++		 */
++		unlink_searched_devnames(cmd);
++
+ 		if (!_lock_hints(cmd, LOCK_EX, NONBLOCK))
+ 			return 0;
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0012-tests-pv-ext-flags-work-with-devices-file.patch b/SOURCES/0012-tests-pv-ext-flags-work-with-devices-file.patch
new file mode 100644
index 0000000..1e421c0
--- /dev/null
+++ b/SOURCES/0012-tests-pv-ext-flags-work-with-devices-file.patch
@@ -0,0 +1,40 @@
+From 9c9bf13186d387d807f279c112745768c8b32513 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Tue, 16 Nov 2021 14:21:07 -0600
+Subject: [PATCH 12/23] tests pv-ext-flags: work with devices file
+
+---
+ test/shell/pv-ext-flags.sh | 4 ++++
+ 1 file changed, 4 insertions(+)
+
+diff --git a/test/shell/pv-ext-flags.sh b/test/shell/pv-ext-flags.sh
+index 3e6bcff76..ae4d6b7ff 100644
+--- a/test/shell/pv-ext-flags.sh
++++ b/test/shell/pv-ext-flags.sh
+@@ -57,9 +57,11 @@ dd if="$dev1" of=dev1_backup bs=1M
+ 
+ # pvcreate and pvremove can be forced even if the PV is marked as used
+ pvremove -ff -y "$dev1"
++lvmdevices --deldev "$dev1" || true
+ dd if=dev1_backup of="$dev1" bs=1M
+ pvcreate -ff -y "$dev1"
+ dd if=dev1_backup of="$dev1" bs=1M
++lvmdevices --adddev "$dev1" || true
+ 
+ # prepare a VG with $dev1 and $dev both having 1 MDA
+ aux enable_dev "$dev2"
+@@ -116,9 +118,11 @@ dd if="$dev1" of=dev1_backup bs=1M
+ 
+ # pvcreate and pvremove can be forced even if the PV is marked as used
+ pvremove -ff -y "$dev1"
++lvmdevices --deldev "$dev1" || true
+ dd if=dev1_backup of="$dev1" bs=1M
+ pvcreate -ff -y "$dev1"
+ dd if=dev1_backup of="$dev1" bs=1M
++lvmdevices --adddev "$dev1" || true
+ 
+ # prepare a VG with $dev1 and $dev both having 1 MDA
+ aux enable_dev "$dev2"
+-- 
+2.31.1
+
diff --git a/SOURCES/0013-display-ignore-reportformat.patch b/SOURCES/0013-display-ignore-reportformat.patch
new file mode 100644
index 0000000..f7dc091
--- /dev/null
+++ b/SOURCES/0013-display-ignore-reportformat.patch
@@ -0,0 +1,91 @@
+From 594c1fec1644fdf291aa0ff23de20db65c4cfadf Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Wed, 17 Nov 2021 10:40:27 -0600
+Subject: [PATCH 13/23] display: ignore --reportformat
+
+Using the option would do nothing useful but would
+print extraneous braces.
+---
+ tools/command-lines.in | 12 ++++++------
+ tools/lvmcmdline.c     | 15 +++++++++++++++
+ 2 files changed, 21 insertions(+), 6 deletions(-)
+
+diff --git a/tools/command-lines.in b/tools/command-lines.in
+index 10b23e75d..00ac08934 100644
+--- a/tools/command-lines.in
++++ b/tools/command-lines.in
+@@ -1359,10 +1359,10 @@ OO: --aligned, --all, --binary, --colon, --columns,
+ --configreport ConfigReport, --foreign, --history, --ignorelockingfailure,
+ --logonly, --maps, --noheadings,
+ --nosuffix, --options String, --sort String, --readonly,
+---reportformat ReportFmt, --segments, --select String, --separator String,
++--segments, --select String, --separator String,
+ --shared, --unbuffered, --units Units
+ OP: VG|LV|Tag ...
+-IO: --partial, --ignoreskippedcluster
++IO: --partial, --ignoreskippedcluster, --reportformat ReportFmt
+ ID: lvdisplay_general
+ 
+ ---
+@@ -1590,10 +1590,10 @@ pvdisplay
+ OO: --aligned, --all, --binary, --colon, --columns, --configreport ConfigReport,
+ --foreign, --ignorelockingfailure,
+ --logonly, --maps, --noheadings, --nosuffix, --options String,
+---readonly, --reportformat ReportFmt, --select String, --separator String, --shared,
++--readonly, --select String, --separator String, --shared,
+ --short, --sort String, --unbuffered, --units Units
+ OP: PV|Tag ...
+-IO: --ignoreskippedcluster
++IO: --ignoreskippedcluster, --reportformat ReportFmt
+ ID: pvdisplay_general
+ 
+ ---
+@@ -1809,10 +1809,10 @@ vgdisplay
+ OO: --activevolumegroups, --aligned, --binary, --colon, --columns,
+ --configreport ConfigReport, --foreign, --ignorelockingfailure,
+ --logonly, --noheadings, --nosuffix,
+---options String, --readonly, --reportformat ReportFmt, --select String,
++--options String, --readonly, --select String,
+ --shared, --short, --separator String, --sort String, --unbuffered, --units Units
+ OP: VG|Tag ...
+-IO: --partial, --ignoreskippedcluster
++IO: --partial, --ignoreskippedcluster, --reportformat ReportFmt
+ ID: vgdisplay_general
+ 
+ ---
+diff --git a/tools/lvmcmdline.c b/tools/lvmcmdline.c
+index 1e12bedca..1727ba089 100644
+--- a/tools/lvmcmdline.c
++++ b/tools/lvmcmdline.c
+@@ -3058,6 +3058,7 @@ int lvm_run_command(struct cmd_context *cmd, int argc, char **argv)
+ 	int i;
+ 	int skip_hyphens;
+ 	int refresh_done = 0;
++	int io;
+ 
+ 	/* Avoid excessive access to /etc/localtime and set TZ variable for glibc
+ 	 * so it does not need to check /etc/localtime everytime that needs that info */
+@@ -3140,6 +3141,20 @@ int lvm_run_command(struct cmd_context *cmd, int argc, char **argv)
+ 	if (!(cmd->command = _find_command(cmd, cmd->name, &argc, argv)))
+ 		return EINVALID_CMD_LINE;
+ 
++	/*
++	 * If option --foo is set which is listed in IO (ignore option) in
++	 * command-lines.in, then unset foo.  Commands won't usually use an
++	 * ignored option, but there can be shared code that checks for --foo,
++	 * and should not find it to be set.
++	 */
++	for (io = 0; io < cmd->command->io_count; io++) {
++		int opt = cmd->command->ignore_opt_args[io].opt;
++		if (arg_is_set(cmd, opt)) {
++			log_debug("Ignore opt %d", opt);
++			cmd->opt_arg_values[opt].count = 0;
++		}
++	}
++
+ 	/*
+ 	 * Remaining position args after command name and --options are removed.
+ 	 */
+-- 
+2.31.1
+
diff --git a/SOURCES/0014-fix-spelling-of-pruning.patch b/SOURCES/0014-fix-spelling-of-pruning.patch
new file mode 100644
index 0000000..e24450a
--- /dev/null
+++ b/SOURCES/0014-fix-spelling-of-pruning.patch
@@ -0,0 +1,25 @@
+From 7ac0b3c119b1cbb8e0b4969ece0b279637ace8c3 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Fri, 19 Nov 2021 12:02:35 -0600
+Subject: [PATCH 14/23] fix spelling of pruning
+
+---
+ lib/format_text/archive.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/lib/format_text/archive.c b/lib/format_text/archive.c
+index 09a472b4c..2e8792a93 100644
+--- a/lib/format_text/archive.c
++++ b/lib/format_text/archive.c
+@@ -219,7 +219,7 @@ static void _remove_expired(const char *dir, const char *vgname,
+ 
+ 	sum /= 1024 * 1024;
+ 	if (sum > 128 || archives_size > 8192)
+-		log_print_unless_silent("Consider prunning %s VG archive with more then %u MiB in %u files (check archiving is needed in lvm.conf).",
++		log_print_unless_silent("Consider pruning %s VG archive with more then %u MiB in %u files (check archiving is needed in lvm.conf).",
+ 					vgname, (unsigned)sum, archives_size);
+ }
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0015-man-lvmautoactivation.patch b/SOURCES/0015-man-lvmautoactivation.patch
new file mode 100644
index 0000000..0128098
--- /dev/null
+++ b/SOURCES/0015-man-lvmautoactivation.patch
@@ -0,0 +1,416 @@
+From 25dbe3dd825a629ff7f67cb43342cc345071d3f7 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Wed, 24 Nov 2021 16:03:39 -0600
+Subject: [PATCH 15/23] man: lvmautoactivation
+
+new topical man page describing autoactivation
+---
+ man/Makefile.in              |   2 +-
+ man/lvm.8_main               |   1 +
+ man/lvmautoactivation.7_main | 280 +++++++++++++++++++++++++++++++++++
+ man/pvscan.8_des             |  63 ++++----
+ 4 files changed, 309 insertions(+), 37 deletions(-)
+ create mode 100644 man/lvmautoactivation.7_main
+
+diff --git a/man/Makefile.in b/man/Makefile.in
+index 40248d640..ba6f2046f 100644
+--- a/man/Makefile.in
++++ b/man/Makefile.in
+@@ -33,7 +33,7 @@ CMIRRORDMAN = cmirrord.8
+ LVMDBUSDMAN = lvmdbusd.8
+ 
+ MAN5=lvm.conf.5
+-MAN7=lvmsystemid.7 lvmreport.7 lvmraid.7
++MAN7=lvmsystemid.7 lvmreport.7 lvmraid.7 lvmautoactivation.7
+ 
+ MAN8=lvm.8 lvmdump.8 lvm-fullreport.8 lvm-lvpoll.8 \
+      lvcreate.8 lvchange.8 lvmconfig.8 lvconvert.8 lvdisplay.8 \
+diff --git a/man/lvm.8_main b/man/lvm.8_main
+index 6f86d0353..a008a3bc0 100644
+--- a/man/lvm.8_main
++++ b/man/lvm.8_main
+@@ -579,6 +579,7 @@ Prepends source file name and code line number with libdm debugging.
+ .BR lvmraid (7),
+ .BR lvmthin (7),
+ .BR lvmcache (7),
++.BR lvmautoactivation (7),
+ .P
+ .BR dmsetup (8),
+ .BR dmstats (8),
+diff --git a/man/lvmautoactivation.7_main b/man/lvmautoactivation.7_main
+new file mode 100644
+index 000000000..87c15a3d1
+--- /dev/null
++++ b/man/lvmautoactivation.7_main
+@@ -0,0 +1,280 @@
++.TH "LVMAUTOACTIVATION" "7" "LVM TOOLS #VERSION#" "Red Hat, Inc" "\""
++.
++.SH NAME
++.
++lvmautoactivation \(em LVM autoactivation
++.
++.SH DESCRIPTION
++.
++Autoactivation is the activation of LVs performed automatically by the
++system in response to LVM devices being attached to the machine.  When all
++PVs in a VG have been attached, the VG is complete, and LVs in the VG are
++activated.
++.P
++Autoactivation of VGs, or specific LVs, can be prevented using vgchange or
++lvchange --setautoactivation n.  The lvm.conf auto_activation_volume_list
++is another way to limit autoactivation.
++.P
++The most common form of autoactivation is "event based", in which complete
++VGs are activated in response to uevents which occur during system startup
++or at any time after the system has started.  Another form of
++autoactivation is "service based" in which complete VGs are activated at a
++fixed point during system startup by a systemd service, and are not
++activated in response to uevents.  This can be controlled with the
++lvm.conf setting event_activation.
++.P
++Event based autoactivation is driven by udev, udev rules, and systemd.
++When a device is attached to a machine, a uevent is generated by the
++kernel to notify userspace of the new device.  systemd-udev runs udev
++rules to process the new device.  Udev rules use blkid to identify the
++device as an LVM PV and then execute the lvm-specific udev rule for the
++device, which triggers autoactivation.
++.P
++There are two variations of event based autoactivation that may be used a
++system, depending on the LVM udev rule that is installed (found in
++/lib/udev/rules.d/.)  The following summarizes the steps in each rule
++which lead to autoactivation:
++.P
++.B 69-dm-lvm-metad.rules
++.
++.IP \[bu] 2
++device /dev/name with major:minor X:Y is attached to the machine
++.
++.IP \[bu] 2
++systemd/udev runs blkid to identify /dev/name as an LVM PV
++.
++.IP \[bu] 2
++udev rule 69-dm-lvm-metad.rules is run for /dev/name
++.
++.IP \[bu] 2
++the lvm udev rule runs the systemd service lvm2-pvscan@X:Yservice
++.
++.IP \[bu] 2
++the lvm2-pvscan service runs:
++.br
++pvscan --cache -aay --major X --minor Y
++.
++.IP \[bu] 2
++pvscan reads the device, records that the PV is online
++(see pvs_online), and checks if the VG is complete.
++.
++.IP \[bu] 2
++if the VG is complete, pvscan creates the vgs_online temp file,
++and activates the VG.
++.
++.IP \[bu] 2
++the activation command output can be seen from
++systemctl status lvm2-pvscan*
++.P
++.B 69-dm-lvm.rules
++.
++.IP \[bu] 2
++device /dev/name with major:minor X:Y is attached to the machine
++.
++.IP \[bu] 2
++systemd/udev runs blkid to identify /dev/name as an LVM PV
++.
++.IP \[bu] 2
++udev rule 69-dm-lvm.rules is run for /dev/name
++.
++.IP \[bu] 2
++the lvm udev rule runs:
++.br
++pvscan --cache --listvg --checkcomplete --vgonline
++.br
++--autoactivation event --udevoutput --journal=output /dev/name
++.
++.IP \[bu] 2
++pvscan reads the device, records that the PV is online
++(see pvs_online), and checks if the VG is complete.
++.
++.IP \[bu] 2
++if the VG is complete, pvscan creates the vgs_online temp file,
++and prints the name of the VG for the udev rule to import:
++LVM_VG_NAME_COMPLETE='vgname'
++.
++.IP \[bu] 2
++if the lvm udev rule sees LVM_VG_NAME_COMPLETE from pvscan,
++it activates the VG using a transient systemd service named
++lvm-activate-<vgname>.
++.
++.IP \[bu] 2
++the lvm-activate-<vgname> service runs
++.br
++vgchange -aay --autoactivation event <vgname>
++.
++.IP \[bu] 2
++the activation command output can be seen from
++systemctl status lvm-activate-<vgname>
++.P
++.
++.SS pvscan options
++.P
++.B --cache
++.br
++Read the <device> arg (and only that device), and record that
++the PV is online by creating the /run/lvm/pvs_online/<pvid>
++file containing the name of the VG and the device for the PV.
++.P
++.B -aay
++.br
++Activate the VG from the pvscan command
++(includes implicit --checkcomplete and --vgonline.)
++.P
++.B --checkcomplete
++.br
++Check if the VG is complete, i.e. all PVs are present on
++the system, by checking /run/lvm/pvs_online/<pvid> files.
++.P
++.B --vgonline
++.br
++Create /run/lvm/vgs_online/<vgname> if the VG is complete
++(used to ensure only one command performs activation.)
++.P
++.B --autoactivation event
++.br
++Inform the command it is used for event based autoactivation.
++.P
++.B --listvg
++.br
++Print the name of the VG using the device.
++.P
++.B --udevoutput
++.br
++Only print output that can be imported to the udev rule,
++using the udev environment key format, i.e. NAME='value'.
++.P
++.B --journal=output
++.br
++Send standard command output to the journal (when stdout
++is reserved for udev output.)
++.P
++.SS Temp files
++.P
++Autoactivation commands use a number of temp files in /run/lvm (with the
++expectation that /run is cleared between boots.)
++.P
++.B pvs_online
++.br
++pvscan --cache creates a file here for each PV that is attached.  The file
++is named with the PVID and contains the VG name and device information.
++The existence of the file is used to determine when all PVs for a given VG
++are present.  The device information in these files is also used to
++optimize locating devices for a VG when the VG is activated.
++.P
++.B pvs_lookup
++.br
++pvscan --cache creates a file here named for a VG (if one doesn't already
++exist.)  The file contains a list of PVIDs in the VG.  This is needed when
++a PV is processed which has no VG metadata, in which case the list of
++PVIDs from the lookup file is used to check if the VG is complete.
++.P
++.B vgs_online
++.br
++The first activation command (pvscan or vgchange) to create a file here,
++named for the VG, will activate the VG.  This resolves a race when
++concurrent commands attempt to activate a VG at once.
++.
++.SH EXAMPLES
++.P
++VG "vg" contains two PVs:
++.nf
++$ pvs -o name,vgname,uuid /dev/sdb /dev/sdc
++  PV         VG PV UUID                               
++  /dev/sdb   vg 1uKpaT-lFOZ-NLHX-j4jI-OBi1-QpdE-HZ5hZY
++  /dev/sdc   vg 5J3tM8-aIPe-2vbd-DBe7-bvRq-TGj0-DaKV2G
++.fi
++.P
++use of --cache:
++.nf
++$ pvscan --cache /dev/sdb
++  pvscan[12922] PV /dev/sdb online.
++$ pvscan --cache /dev/sdc
++  pvscan[12923] PV /dev/sdc online.
++
++$ cat /run/lvm/pvs_online/1uKpaTlFOZNLHXj4jIOBi1QpdEHZ5hZY 
++8:16
++vg:vg
++dev:/dev/sdb
++$ cat /run/lvm/pvs_online/5J3tM8aIPe2vbdDBe7bvRqTGj0DaKV2G 
++8:32
++vg:vg
++dev:/dev/sdc
++.fi
++.P
++use of -aay:
++.nf
++$ pvscan --cache -aay /dev/sdb
++  pvscan[12935] PV /dev/sdb online, VG vg incomplete (need 1).
++$ pvscan --cache -aay /dev/sdc
++  pvscan[12936] PV /dev/sdc online, VG vg is complete.
++  pvscan[12936] VG vg run autoactivation.
++  1 logical volume(s) in volume group "vg" now active
++
++$ cat /run/lvm/pvs_online/1uKpaTlFOZNLHXj4jIOBi1QpdEHZ5hZY 
++8:16
++vg:vg
++dev:/dev/sdb
++$ cat /run/lvm/pvs_online/5J3tM8aIPe2vbdDBe7bvRqTGj0DaKV2G 
++8:32
++vg:vg
++dev:/dev/sdc
++$ ls /run/lvm/vgs_online/vg 
++/run/lvm/vgs_online/vg
++.fi
++.P
++use of --listvg:
++.nf
++$ pvscan --cache --listvg /dev/sdb
++  VG vg
++$ pvscan --cache --listvg /dev/sdc
++  VG vg
++
++$ cat /run/lvm/pvs_online/1uKpaTlFOZNLHXj4jIOBi1QpdEHZ5hZY 
++8:16
++vg:vg
++dev:/dev/sdb
++$ cat /run/lvm/pvs_online/5J3tM8aIPe2vbdDBe7bvRqTGj0DaKV2G 
++8:32
++vg:vg
++dev:/dev/sdc
++.fi
++.P
++use of --checkcomplete:
++.nf
++$ pvscan --cache --listvg --checkcomplete --vgonline /dev/sdb
++  pvscan[12996] PV /dev/sdb online, VG vg incomplete (need 1).
++  VG vg incomplete
++$ pvscan --cache --listvg --checkcomplete --vgonline /dev/sdc
++  pvscan[12997] PV /dev/sdc online, VG vg is complete.
++  VG vg complete
++.fi
++.P
++use of --udevoutput:
++.nf
++$ pvscan --cache --listvg --checkcomplete --vgonline --udevoutput /dev/sdb
++LVM_VG_NAME_INCOMPLETE='vg'
++$ pvscan --cache --listvg --checkcomplete --vgonline --udevoutput /dev/sdc
++LVM_VG_NAME_COMPLETE='vg'
++.fi
++.P
++use of --listlvs:
++.nf
++$ lvs -o name,devices vg
++  LV    Devices                
++  lvol0 /dev/sdb(0)            
++  lvol1 /dev/sdc(0)            
++  lvol2 /dev/sdb(1),/dev/sdc(1)
++
++$ pvscan --cache --listlvs --checkcomplete /dev/sdb
++  pvscan[13288] PV /dev/sdb online, VG vg incomplete (need 1).
++  VG vg incomplete
++  LV vg/lvol0 complete
++  LV vg/lvol2 incomplete
++$ pvscan --cache --listlvs --checkcomplete /dev/sdc
++  pvscan[13289] PV /dev/sdc online, VG vg is complete.
++  VG vg complete
++  LV vg/lvol1 complete
++  LV vg/lvol2 complete
++.fi
++
+diff --git a/man/pvscan.8_des b/man/pvscan.8_des
+index b20b987da..4c5929955 100644
+--- a/man/pvscan.8_des
++++ b/man/pvscan.8_des
+@@ -4,56 +4,47 @@ like
+ or
+ .BR pvdisplay (8).
+ .P
+-When the --cache and -aay options are used, pvscan records which PVs are
+-available on the system, and activates LVs in completed VGs.  A VG is
+-complete when pvscan sees that the final PV in the VG has appeared.  This
+-is used by event-based system startup (systemd, udev) to activate LVs.
+-.P
+-The four main variations of this are:
++When --cache is used, pvscan updates runtime lvm state on the system, or
++with -aay performs autoactivation.
+ .P
+ .B pvscan --cache
+ .I device
+ .P
+-If device is present, lvm adds a record that the PV on device is online.
++If device is present, lvm records that the PV on device is online.
+ If device is not present, lvm removes the online record for the PV.
+-In most cases, the pvscan will only read the named devices.
++pvscan only reads the named device.
+ .P
+-.B pvscan --cache -aay
+-.IR device ...
++.B pvscan --cache
+ .P
+-This begins by performing the same steps as above.  Afterward, if the VG
+-for the specified PV is complete, then pvscan will activate LVs in the VG
+-(the same as vgchange -aay vgname would do.)
++Updates the runtime state for all lvm devices.
+ .P
+-.B pvscan --cache
++.B pvscan --cache -aay
++.I device
+ .P
+-This first clears all existing PV online records, then scans all devices
+-on the system, adding PV online records for any PVs that are found.
++Performs the --cache steps for the device, then checks if the VG using the
++device is complete.  If so, LVs in the VG are autoactivated, the same as
++vgchange -aay vgname would do.  (A device name may be replaced with major
++and minor numbers.)
+ .P
+ .B pvscan --cache -aay
+ .P
+-This begins by performing the same steps as pvscan --cache.  Afterward, it
+-activates LVs in any complete VGs.
++Performs the --cache steps for all devices, then autoactivates any complete VGs.
+ .P
+-To prevent devices from being scanned by pvscan --cache, add them
+-to
+-.BR lvm.conf (5)
+-.B devices/global_filter.
+-For more information, see:
+-.br
+-.B lvmconfig --withcomments devices/global_filter
++.B pvscan --cache --listvg|--listlvs
++.I device
++.P
++Performs the --cache steps for the device, then prints the name of the VG
++using the device, or the names of LVs using the device.  --checkcomplete
++is usually included to check if all PVs for the VG or LVs are online.
++When this command is called by a udev rule, the output must conform to
++udev rule specifications (see --udevoutput.)  The udev rule will use the
++results to perform autoactivation.
+ .P
+-Auto-activation of VGs or LVs can be enabled/disabled using:
+-.br
++Autoactivation of VGs or LVs can be enabled/disabled using vgchange or
++lvchange with --setautoactivation y|n, or by adding names to
+ .BR lvm.conf (5)
+ .B activation/auto_activation_volume_list
+ .P
+-For more information, see:
+-.br
+-.B lvmconfig --withcomments activation/auto_activation_volume_list
+-.P
+-To disable auto-activation, explicitly set this list to an empty list,
+-i.e. auto_activation_volume_list = [ ].
+-.P
+-When this setting is undefined (e.g. commented), then all LVs are
+-auto-activated.
++See
++.BR lvmautoactivation (7)
++for more information about how pvscan is used for autoactivation.
+-- 
+2.31.1
+
diff --git a/SOURCES/0017-tests-devicesfile-devname.sh-drop-mdadm-chunk.patch b/SOURCES/0017-tests-devicesfile-devname.sh-drop-mdadm-chunk.patch
new file mode 100644
index 0000000..ef22830
--- /dev/null
+++ b/SOURCES/0017-tests-devicesfile-devname.sh-drop-mdadm-chunk.patch
@@ -0,0 +1,25 @@
+From 10a4478e9b778dd8d4ff9737a503474b00ce9510 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Wed, 1 Dec 2021 08:56:05 -0600
+Subject: [PATCH 17/23] tests devicesfile-devname.sh drop mdadm chunk
+
+---
+ test/shell/devicesfile-devname.sh | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/test/shell/devicesfile-devname.sh b/test/shell/devicesfile-devname.sh
+index a99fe3e9a..338637275 100644
+--- a/test/shell/devicesfile-devname.sh
++++ b/test/shell/devicesfile-devname.sh
+@@ -590,7 +590,7 @@ OPVID2=`pvs "$dev2" --noheading -o uuid | awk '{print $1}'`
+ PVID1=`pvs "$dev1" --noheading -o uuid | tr -d - | awk '{print $1}'`
+ PVID2=`pvs "$dev2" --noheading -o uuid | tr -d - | awk '{print $1}'`
+ 
+-mdadm --create --metadata=1.0 "$mddev" --level 1 --chunk=64 --raid-devices=2 "$dev3" "$dev4"
++mdadm --create --metadata=1.0 "$mddev" --level 1 --raid-devices=2 "$dev3" "$dev4"
+ wait_md_create "$mddev"
+ 
+ sed -e "s|DEVNAME=$dev1|DEVNAME=$dev3|" "$ORIG" > tmp1.devices
+-- 
+2.31.1
+
diff --git a/SOURCES/0018-devices-file-don-t-write-in-test-mode.patch b/SOURCES/0018-devices-file-don-t-write-in-test-mode.patch
new file mode 100644
index 0000000..feb3bf7
--- /dev/null
+++ b/SOURCES/0018-devices-file-don-t-write-in-test-mode.patch
@@ -0,0 +1,26 @@
+From 04770589b49effdb064c9b3790e8dd2fee2c3547 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Wed, 1 Dec 2021 10:08:08 -0600
+Subject: [PATCH 18/23] devices file: don't write in test mode
+
+---
+ lib/device/device_id.c | 3 +++
+ 1 file changed, 3 insertions(+)
+
+diff --git a/lib/device/device_id.c b/lib/device/device_id.c
+index ce7ded154..4c2b5a3dd 100644
+--- a/lib/device/device_id.c
++++ b/lib/device/device_id.c
+@@ -673,6 +673,9 @@ int device_ids_write(struct cmd_context *cmd)
+ 		cmd->enable_devices_file = 1;
+ 	}
+ 
++	if (test_mode())
++		return 1;
++
+ 	if (_devices_file_version[0]) {
+ 		if (sscanf(_devices_file_version, "%u.%u.%u", &df_major, &df_minor, &df_counter) != 3) {
+ 			/* don't update a file we can't parse */
+-- 
+2.31.1
+
diff --git a/SOURCES/0019-print-warning-about-unrecognized-journal-option-valu.patch b/SOURCES/0019-print-warning-about-unrecognized-journal-option-valu.patch
new file mode 100644
index 0000000..5fc92af
--- /dev/null
+++ b/SOURCES/0019-print-warning-about-unrecognized-journal-option-valu.patch
@@ -0,0 +1,24 @@
+From 604fd528fb4f00a9f77e084a1b22eff2aeef0259 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Thu, 2 Dec 2021 12:40:52 -0600
+Subject: [PATCH 19/23] print warning about unrecognized journal option value
+
+---
+ lib/log/log.c | 1 +
+ 1 file changed, 1 insertion(+)
+
+diff --git a/lib/log/log.c b/lib/log/log.c
+index 7b4d537b3..5771a1d01 100644
+--- a/lib/log/log.c
++++ b/lib/log/log.c
+@@ -892,6 +892,7 @@ uint32_t log_journal_str_to_val(const char *str)
+ 		return LOG_JOURNAL_OUTPUT;
+ 	if (!strcasecmp(str, "debug"))
+ 		return LOG_JOURNAL_DEBUG;
++	log_warn("Ignoring unrecognized journal value.");
+ 	return 0;
+ }
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0020-device_id-handle-wwid-with-spaces-or-control-charact.patch b/SOURCES/0020-device_id-handle-wwid-with-spaces-or-control-charact.patch
new file mode 100644
index 0000000..e254e36
--- /dev/null
+++ b/SOURCES/0020-device_id-handle-wwid-with-spaces-or-control-charact.patch
@@ -0,0 +1,50 @@
+From 357a807e81bbd1430b045eb2601a64b17d588400 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Thu, 2 Dec 2021 13:30:36 -0600
+Subject: [PATCH 20/23] device_id: handle wwid with spaces or control
+ characters
+
+non-standard wwid can be reported from sysfs with spaces/etc.
+replace with "_"
+---
+ lib/device/device_id.c | 10 ++++++----
+ 1 file changed, 6 insertions(+), 4 deletions(-)
+
+diff --git a/lib/device/device_id.c b/lib/device/device_id.c
+index 4c2b5a3dd..0621bc858 100644
+--- a/lib/device/device_id.c
++++ b/lib/device/device_id.c
+@@ -304,6 +304,7 @@ const char *device_id_system_read(struct cmd_context *cmd, struct device *dev, u
+ {
+ 	char sysbuf[PATH_MAX] = { 0 };
+ 	const char *idname = NULL;
++	int i;
+ 
+ 	if (idtype == DEV_ID_TYPE_SYS_WWID) {
+ 		read_sys_block(cmd, dev, "device/wwid", sysbuf, sizeof(sysbuf));
+@@ -311,10 +312,6 @@ const char *device_id_system_read(struct cmd_context *cmd, struct device *dev, u
+ 		if (!sysbuf[0])
+ 			read_sys_block(cmd, dev, "wwid", sysbuf, sizeof(sysbuf));
+ 
+-		/* scsi_debug wwid begins "t10.Linux   scsi_debug ..." */
+-		if (strstr(sysbuf, "scsi_debug"))
+-			sysbuf[0] = '\0';
+-
+ 		/* qemu wwid begins "t10.ATA     QEMU HARDDISK ..." */
+ 		if (strstr(sysbuf, "QEMU HARDDISK"))
+ 			sysbuf[0] = '\0';
+@@ -355,6 +352,11 @@ const char *device_id_system_read(struct cmd_context *cmd, struct device *dev, u
+ 		return idname;
+ 	}
+ 
++	for (i = 0; i < strlen(sysbuf); i++) {
++		if (isblank(sysbuf[i]) || isspace(sysbuf[i]) || iscntrl(sysbuf[i]))
++			sysbuf[i] = '_';
++	}
++
+ 	if (!sysbuf[0])
+ 		goto_bad;
+ 
+-- 
+2.31.1
+
diff --git a/SOURCES/0021-man-add-section-about-static-autoactivation.patch b/SOURCES/0021-man-add-section-about-static-autoactivation.patch
new file mode 100644
index 0000000..a6d10cf
--- /dev/null
+++ b/SOURCES/0021-man-add-section-about-static-autoactivation.patch
@@ -0,0 +1,96 @@
+From 7631c5b826b5a3eddfcd22db9b80574b249794c1 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Mon, 6 Dec 2021 13:20:32 -0600
+Subject: [PATCH 21/23] man: add section about static autoactivation
+
+---
+ man/lvmautoactivation.7_main | 48 ++++++++++++++++++++++++++++++------
+ 1 file changed, 41 insertions(+), 7 deletions(-)
+
+diff --git a/man/lvmautoactivation.7_main b/man/lvmautoactivation.7_main
+index 87c15a3d1..bf885991d 100644
+--- a/man/lvmautoactivation.7_main
++++ b/man/lvmautoactivation.7_main
+@@ -14,14 +14,16 @@ activated.
+ Autoactivation of VGs, or specific LVs, can be prevented using vgchange or
+ lvchange --setautoactivation n.  The lvm.conf auto_activation_volume_list
+ is another way to limit autoactivation.
++.
++.SS event autoactivation
+ .P
+ The most common form of autoactivation is "event based", in which complete
+ VGs are activated in response to uevents which occur during system startup
+ or at any time after the system has started.  Another form of
+-autoactivation is "service based" in which complete VGs are activated at a
+-fixed point during system startup by a systemd service, and are not
+-activated in response to uevents.  This can be controlled with the
+-lvm.conf setting event_activation.
++autoactivation is "static" in which complete VGs are activated at a fixed
++point during system startup by a systemd service, and not in response to
++events.  This can be controlled with the lvm.conf setting
++event_activation.
+ .P
+ Event based autoactivation is driven by udev, udev rules, and systemd.
+ When a device is attached to a machine, a uevent is generated by the
+@@ -30,8 +32,8 @@ rules to process the new device.  Udev rules use blkid to identify the
+ device as an LVM PV and then execute the lvm-specific udev rule for the
+ device, which triggers autoactivation.
+ .P
+-There are two variations of event based autoactivation that may be used a
+-system, depending on the LVM udev rule that is installed (found in
++There are two variations of event baed autoactivation that may be used on
++a system, depending on the LVM udev rule that is installed (found in
+ /lib/udev/rules.d/.)  The following summarizes the steps in each rule
+ which lead to autoactivation:
+ .P
+@@ -149,7 +151,7 @@ using the udev environment key format, i.e. NAME='value'.
+ Send standard command output to the journal (when stdout
+ is reserved for udev output.)
+ .P
+-.SS Temp files
++.SS run files
+ .P
+ Autoactivation commands use a number of temp files in /run/lvm (with the
+ expectation that /run is cleared between boots.)
+@@ -175,6 +177,38 @@ The first activation command (pvscan or vgchange) to create a file here,
+ named for the VG, will activate the VG.  This resolves a race when
+ concurrent commands attempt to activate a VG at once.
+ .
++.SS static autoactivation
++.P
++When event autoactivation is disabled by setting lvm.conf
++event_activation=0, autoactivation is performed at one or more static
++points during system startup. At these points, a vgchange -aay command is
++run to activate complete VGs from devices that are present on the system
++at that time. pvscan commands (and lvm2-pvscan services) do not perform
++autoactivation in this mode.  pvscan commands may still be run from
++uevents but will do nothing when they read the event_activation=0 setting.
++.P
++The static vgchange -aay commands are run by three systemd services at
++three points during startup: lvm2-activation-early, lvm2-activation, and
++lvm2-activation-net. These static activation services are "generated
++services", so the service files are created at run time by the
++lvm2-activation-generator command (run by systemd).
++lvm2-activation-generator creates the services if lvm.conf
++event_activation=0.
++.P
++The limitation of this method is that devices may not be attached to the
++system (or set up) at a reliable point in time during startup, and they
++may not be present when the services run vgchange.  In this case, the VGs
++will not be autoactivated.  So, the timing of device attachment/setup
++determines whether static autoactivation will produce the same results as
++event autoactivation.  For this reason, static autoactivation is not
++recommended.
++.P
++Sometimes, static autoactivation is mistakenly expected to disable all
++autoactivation of particular VGs. This may appear to be effective if those
++VGs are slow to be attached or set up. But, the only correct and reliable
++way to disable autoactivation is using vgchange/lvchange
++--setautoactivation n, or lvm.conf auto_activation_volume_list.
++.
+ .SH EXAMPLES
+ .P
+ VG "vg" contains two PVs:
+-- 
+2.31.1
+
diff --git a/SOURCES/0022-lvcreate-include-recent-options.patch b/SOURCES/0022-lvcreate-include-recent-options.patch
new file mode 100644
index 0000000..38a729d
--- /dev/null
+++ b/SOURCES/0022-lvcreate-include-recent-options.patch
@@ -0,0 +1,35 @@
+From af4bfa1f1f84194000bc50f43ddc906c0cd4b104 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Mon, 13 Dec 2021 08:59:31 -0600
+Subject: [PATCH 22/23] lvcreate: include recent options
+
+The permitted option list in lvcreate has not kept
+up with command-lines.in.
+---
+ tools/lvcreate.c | 4 ++++
+ 1 file changed, 4 insertions(+)
+
+diff --git a/tools/lvcreate.c b/tools/lvcreate.c
+index 0121c09a8..79af42685 100644
+--- a/tools/lvcreate.c
++++ b/tools/lvcreate.c
+@@ -824,12 +824,16 @@ static int _lvcreate_params(struct cmd_context *cmd,
+ 	autobackup_ARG,\
+ 	available_ARG,\
+ 	contiguous_ARG,\
++	devices_ARG,\
++	devicesfile_ARG,\
+ 	ignoreactivationskip_ARG,\
+ 	ignoremonitoring_ARG,\
++	journal_ARG,\
+ 	metadataprofile_ARG,\
+ 	monitor_ARG,\
+ 	mirrors_ARG,\
+ 	name_ARG,\
++	nohints_ARG,\
+ 	noudevsync_ARG,\
+ 	permission_ARG,\
+ 	persistent_ARG,\
+-- 
+2.31.1
+
diff --git a/SOURCES/0023-man-lvmautoactivation-replace-systemctl-with-journal.patch b/SOURCES/0023-man-lvmautoactivation-replace-systemctl-with-journal.patch
new file mode 100644
index 0000000..16b08c4
--- /dev/null
+++ b/SOURCES/0023-man-lvmautoactivation-replace-systemctl-with-journal.patch
@@ -0,0 +1,26 @@
+From 61833dd5b6117e8ace84289cff656d1dfb0ed123 Mon Sep 17 00:00:00 2001
+From: David Teigland <teigland@redhat.com>
+Date: Tue, 14 Dec 2021 12:02:08 -0600
+Subject: [PATCH 23/23] man lvmautoactivation: replace systemctl with
+ journalctl
+
+---
+ man/lvmautoactivation.7_main | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/man/lvmautoactivation.7_main b/man/lvmautoactivation.7_main
+index bf885991d..54dab718b 100644
+--- a/man/lvmautoactivation.7_main
++++ b/man/lvmautoactivation.7_main
+@@ -107,7 +107,7 @@ vgchange -aay --autoactivation event <vgname>
+ .
+ .IP \[bu] 2
+ the activation command output can be seen from
+-systemctl status lvm-activate-<vgname>
++journalctl -u lvm-activate-<vgname>
+ .P
+ .
+ .SS pvscan options
+-- 
+2.31.1
+
diff --git a/SOURCES/0024-make-generate.patch b/SOURCES/0024-make-generate.patch
new file mode 100644
index 0000000..f5a15ad
--- /dev/null
+++ b/SOURCES/0024-make-generate.patch
@@ -0,0 +1,196 @@
+From 4b26fb3543049f3d179b620ff937c44e922ada58 Mon Sep 17 00:00:00 2001
+From: Marian Csontos <mcsontos@redhat.com>
+Date: Tue, 4 Jan 2022 17:15:56 +0100
+Subject: [PATCH] make: generate
+
+---
+ man/lvdisplay.8_pregen | 12 --------
+ man/pvdisplay.8_pregen | 12 --------
+ man/pvscan.8_pregen    | 63 ++++++++++++++++++------------------------
+ man/vgdisplay.8_pregen | 12 --------
+ 4 files changed, 27 insertions(+), 72 deletions(-)
+
+diff --git a/man/lvdisplay.8_pregen b/man/lvdisplay.8_pregen
+index a1740ebed..04aab4c09 100644
+--- a/man/lvdisplay.8_pregen
++++ b/man/lvdisplay.8_pregen
+@@ -61,8 +61,6 @@ and more, using a more compact and configurable output format.
+ .br
+ [    \fB--readonly\fP ]
+ .br
+-[    \fB--reportformat\fP \fBbasic\fP|\fBjson\fP ]
+-.br
+ [    \fB--segments\fP ]
+ .br
+ [    \fB--separator\fP \fIString\fP ]
+@@ -332,16 +330,6 @@ device-mapper kernel driver, so this option is unable to report whether
+ or not LVs are actually in use.
+ .
+ .HP
+-\fB--reportformat\fP \fBbasic\fP|\fBjson\fP
+-.br
+-Overrides current output format for reports which is defined globally by
+-the report/output_format setting in \fBlvm.conf\fP(5).
+-\fBbasic\fP is the original format with columns and rows.
+-If there is more than one report per command, each report is prefixed
+-with the report name for identification. \fBjson\fP produces report
+-output in JSON format. See \fBlvmreport\fP(7) for more information.
+-.
+-.HP
+ \fB--segments\fP
+ .br
+ .
+diff --git a/man/pvdisplay.8_pregen b/man/pvdisplay.8_pregen
+index 22a0992b5..2f26a8727 100644
+--- a/man/pvdisplay.8_pregen
++++ b/man/pvdisplay.8_pregen
+@@ -61,8 +61,6 @@ and more, using a more compact and configurable output format.
+ .br
+ [    \fB--readonly\fP ]
+ .br
+-[    \fB--reportformat\fP \fBbasic\fP|\fBjson\fP ]
+-.br
+ [    \fB--separator\fP \fIString\fP ]
+ .br
+ [    \fB--shared\fP ]
+@@ -320,16 +318,6 @@ device-mapper kernel driver, so this option is unable to report whether
+ or not LVs are actually in use.
+ .
+ .HP
+-\fB--reportformat\fP \fBbasic\fP|\fBjson\fP
+-.br
+-Overrides current output format for reports which is defined globally by
+-the report/output_format setting in \fBlvm.conf\fP(5).
+-\fBbasic\fP is the original format with columns and rows.
+-If there is more than one report per command, each report is prefixed
+-with the report name for identification. \fBjson\fP produces report
+-output in JSON format. See \fBlvmreport\fP(7) for more information.
+-.
+-.HP
+ \fB-S\fP|\fB--select\fP \fIString\fP
+ .br
+ Select objects for processing and reporting based on specified criteria.
+diff --git a/man/pvscan.8_pregen b/man/pvscan.8_pregen
+index 9eb6b5bf9..1c96d5aab 100644
+--- a/man/pvscan.8_pregen
++++ b/man/pvscan.8_pregen
+@@ -91,59 +91,50 @@ like
+ or
+ .BR pvdisplay (8).
+ .P
+-When the --cache and -aay options are used, pvscan records which PVs are
+-available on the system, and activates LVs in completed VGs.  A VG is
+-complete when pvscan sees that the final PV in the VG has appeared.  This
+-is used by event-based system startup (systemd, udev) to activate LVs.
+-.P
+-The four main variations of this are:
++When --cache is used, pvscan updates runtime lvm state on the system, or
++with -aay performs autoactivation.
+ .P
+ .B pvscan --cache
+ .I device
+ .P
+-If device is present, lvm adds a record that the PV on device is online.
++If device is present, lvm records that the PV on device is online.
+ If device is not present, lvm removes the online record for the PV.
+-In most cases, the pvscan will only read the named devices.
++pvscan only reads the named device.
+ .P
+-.B pvscan --cache -aay
+-.IR device ...
++.B pvscan --cache
+ .P
+-This begins by performing the same steps as above.  Afterward, if the VG
+-for the specified PV is complete, then pvscan will activate LVs in the VG
+-(the same as vgchange -aay vgname would do.)
++Updates the runtime state for all lvm devices.
+ .P
+-.B pvscan --cache
++.B pvscan --cache -aay
++.I device
+ .P
+-This first clears all existing PV online records, then scans all devices
+-on the system, adding PV online records for any PVs that are found.
++Performs the --cache steps for the device, then checks if the VG using the
++device is complete.  If so, LVs in the VG are autoactivated, the same as
++vgchange -aay vgname would do.  (A device name may be replaced with major
++and minor numbers.)
+ .P
+ .B pvscan --cache -aay
+ .P
+-This begins by performing the same steps as pvscan --cache.  Afterward, it
+-activates LVs in any complete VGs.
++Performs the --cache steps for all devices, then autoactivates any complete VGs.
+ .P
+-To prevent devices from being scanned by pvscan --cache, add them
+-to
+-.BR lvm.conf (5)
+-.B devices/global_filter.
+-For more information, see:
+-.br
+-.B lvmconfig --withcomments devices/global_filter
++.B pvscan --cache --listvg|--listlvs
++.I device
+ .P
+-Auto-activation of VGs or LVs can be enabled/disabled using:
+-.br
++Performs the --cache steps for the device, then prints the name of the VG
++using the device, or the names of LVs using the device.  --checkcomplete
++is usually included to check if all PVs for the VG or LVs are online.
++When this command is called by a udev rule, the output must conform to
++udev rule specifications (see --udevoutput.)  The udev rule will use the
++results to perform autoactivation.
++.P
++Autoactivation of VGs or LVs can be enabled/disabled using vgchange or
++lvchange with --setautoactivation y|n, or by adding names to
+ .BR lvm.conf (5)
+ .B activation/auto_activation_volume_list
+ .P
+-For more information, see:
+-.br
+-.B lvmconfig --withcomments activation/auto_activation_volume_list
+-.P
+-To disable auto-activation, explicitly set this list to an empty list,
+-i.e. auto_activation_volume_list = [ ].
+-.P
+-When this setting is undefined (e.g. commented), then all LVs are
+-auto-activated.
++See
++.BR lvmautoactivation (7)
++for more information about how pvscan is used for autoactivation.
+ .
+ .SH USAGE
+ .
+diff --git a/man/vgdisplay.8_pregen b/man/vgdisplay.8_pregen
+index 9c694921d..0a12b3c39 100644
+--- a/man/vgdisplay.8_pregen
++++ b/man/vgdisplay.8_pregen
+@@ -58,8 +58,6 @@ and more, using a more compact and configurable output format.
+ .br
+ [    \fB--readonly\fP ]
+ .br
+-[    \fB--reportformat\fP \fBbasic\fP|\fBjson\fP ]
+-.br
+ [    \fB--shared\fP ]
+ .br
+ [    \fB--separator\fP \fIString\fP ]
+@@ -312,16 +310,6 @@ device-mapper kernel driver, so this option is unable to report whether
+ or not LVs are actually in use.
+ .
+ .HP
+-\fB--reportformat\fP \fBbasic\fP|\fBjson\fP
+-.br
+-Overrides current output format for reports which is defined globally by
+-the report/output_format setting in \fBlvm.conf\fP(5).
+-\fBbasic\fP is the original format with columns and rows.
+-If there is more than one report per command, each report is prefixed
+-with the report name for identification. \fBjson\fP produces report
+-output in JSON format. See \fBlvmreport\fP(7) for more information.
+-.
+-.HP
+ \fB-S\fP|\fB--select\fP \fIString\fP
+ .br
+ Select objects for processing and reporting based on specified criteria.
+-- 
+2.31.1
+
diff --git a/SOURCES/lvm2-2_03_13-device_id-handle-scsi_debug-wwid.patch b/SOURCES/lvm2-2_03_13-device_id-handle-scsi_debug-wwid.patch
deleted file mode 100644
index 84cc940..0000000
--- a/SOURCES/lvm2-2_03_13-device_id-handle-scsi_debug-wwid.patch
+++ /dev/null
@@ -1,18 +0,0 @@
- lib/device/device_id.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
-diff --git a/lib/device/device_id.c b/lib/device/device_id.c
-index f158e4f..9cc82f1 100644
---- a/lib/device/device_id.c
-+++ b/lib/device/device_id.c
-@@ -308,6 +308,10 @@ const char *device_id_system_read(struct cmd_context *cmd, struct device *dev, u
- 
- 		if (!sysbuf[0])
- 			_read_sys_block(cmd, dev, "wwid", sysbuf, sizeof(sysbuf));
-+
-+		/* scsi_debug wwid begins "t10.Linux   scsi_debug ..." */
-+		if (strstr(sysbuf, "scsi_debug"))
-+			sysbuf[0] = '\0';
- 	}
- 
- 	else if (idtype == DEV_ID_TYPE_SYS_SERIAL)
diff --git a/SOURCES/lvm2-2_03_13-devices-don-t-use-deleted-loop-backing-file-for-devi.patch b/SOURCES/lvm2-2_03_13-devices-don-t-use-deleted-loop-backing-file-for-devi.patch
deleted file mode 100644
index 6de11be..0000000
--- a/SOURCES/lvm2-2_03_13-devices-don-t-use-deleted-loop-backing-file-for-devi.patch
+++ /dev/null
@@ -1,21 +0,0 @@
- lib/device/device_id.c | 6 +++++-
- 1 file changed, 5 insertions(+), 1 deletion(-)
-
-diff --git a/lib/device/device_id.c b/lib/device/device_id.c
-index 67f72e5..1b98487 100644
---- a/lib/device/device_id.c
-+++ b/lib/device/device_id.c
-@@ -325,8 +325,12 @@ const char *device_id_system_read(struct cmd_context *cmd, struct device *dev, u
- 	else if (idtype == DEV_ID_TYPE_MD_UUID)
- 		_read_sys_block(cmd, dev, "md/uuid", sysbuf, sizeof(sysbuf));
- 
--	else if (idtype == DEV_ID_TYPE_LOOP_FILE)
-+	else if (idtype == DEV_ID_TYPE_LOOP_FILE) {
- 		_read_sys_block(cmd, dev, "loop/backing_file", sysbuf, sizeof(sysbuf));
-+		/* if backing file is deleted, fall back to devname */
-+		if (strstr(sysbuf, "(deleted)"))
-+			sysbuf[0] = '\0';
-+	}
- 
- 	else if (idtype == DEV_ID_TYPE_DEVNAME) {
- 		if (!(idname = strdup(dev_name(dev))))
diff --git a/SOURCES/lvm2-2_03_13-enable-command-syntax-for-thin-and-writecache.patch b/SOURCES/lvm2-2_03_13-enable-command-syntax-for-thin-and-writecache.patch
deleted file mode 100644
index 652b0b7..0000000
--- a/SOURCES/lvm2-2_03_13-enable-command-syntax-for-thin-and-writecache.patch
+++ /dev/null
@@ -1,25 +0,0 @@
- tools/command-lines.in | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
-diff --git a/tools/command-lines.in b/tools/command-lines.in
-index 1107c1e..67c37ff 100644
---- a/tools/command-lines.in
-+++ b/tools/command-lines.in
-@@ -534,7 +534,7 @@ RULE: all and lv_is_visible
- 
- ---
- 
--lvconvert --type thin-pool LV_linear_striped_raid_cache_error_zero
-+lvconvert --type thin-pool LV_linear_striped_raid_cache_writecache_error_zero
- OO: --stripes_long Number, --stripesize SizeKB,
- OO_LVCONVERT_THINPOOL, OO_LVCONVERT_POOL, OO_LVCONVERT
- OP: PV ...
-@@ -566,7 +566,7 @@ RULE: --poolmetadata not --readahead --stripesize --stripes_long
- # This command syntax is deprecated, and the primary forms
- # of creating a pool or swapping metadata should be used.
- 
--lvconvert --thinpool LV_linear_striped_raid_cache_thinpool
-+lvconvert --thinpool LV_linear_striped_raid_cache_writecache_thinpool
- OO: --stripes_long Number, --stripesize SizeKB,
- OO_LVCONVERT_THINPOOL, OO_LVCONVERT_POOL, OO_LVCONVERT
- OP: PV ...
diff --git a/SOURCES/lvm2-2_03_13-lvconvert-allow-writecache-with-other-thinpool-comma.patch b/SOURCES/lvm2-2_03_13-lvconvert-allow-writecache-with-other-thinpool-comma.patch
deleted file mode 100644
index 2875b22..0000000
--- a/SOURCES/lvm2-2_03_13-lvconvert-allow-writecache-with-other-thinpool-comma.patch
+++ /dev/null
@@ -1,16 +0,0 @@
- tools/lvconvert.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/tools/lvconvert.c b/tools/lvconvert.c
-index 8dd8a15..6066d1f 100644
---- a/tools/lvconvert.c
-+++ b/tools/lvconvert.c
-@@ -4803,7 +4803,7 @@ static int _lvconvert_to_pool_or_swap_metadata_single(struct cmd_context *cmd,
- 
- 	switch (cmd->command->command_enum) {
- 	case lvconvert_to_thinpool_or_swap_metadata_CMD:
--		if (lv_is_cache(lv))
-+		if (lv_is_cache(lv) || lv_is_writecache(lv))
- 			/* For cached LV check the cache origin LV type */
- 			lvt_enum = get_lvt_enum(seg_lv(first_seg(lv), 0));
- 		to_thinpool = 1;
diff --git a/SOURCES/lvm2-2_03_13-lvconvert-fix-vdo-virtual-size-when-specified.patch b/SOURCES/lvm2-2_03_13-lvconvert-fix-vdo-virtual-size-when-specified.patch
deleted file mode 100644
index 7758cca..0000000
--- a/SOURCES/lvm2-2_03_13-lvconvert-fix-vdo-virtual-size-when-specified.patch
+++ /dev/null
@@ -1,17 +0,0 @@
- lib/metadata/vdo_manip.c | 3 ++-
- 1 file changed, 2 insertions(+), 1 deletion(-)
-
-diff --git a/lib/metadata/vdo_manip.c b/lib/metadata/vdo_manip.c
-index 7d5a2cb..afc513a 100644
---- a/lib/metadata/vdo_manip.c
-+++ b/lib/metadata/vdo_manip.c
-@@ -393,7 +393,8 @@ struct logical_volume *convert_vdo_pool_lv(struct logical_volume *data_lv,
- 	} else {
- 		log_verbose("Skiping VDO formating %s.", display_lvname(data_lv));
- 		/* TODO: parse existing VDO data and retrieve vdo_logical_size */
--		vdo_logical_size = data_lv->size;
-+		if (!*virtual_extents)
-+			vdo_logical_size = data_lv->size;
- 	}
- 
- 	if (!deactivate_lv(data_lv->vg->cmd, data_lv)) {
diff --git a/SOURCES/lvm2-2_03_13-lvmdevices-add-deviceidtype-option.patch b/SOURCES/lvm2-2_03_13-lvmdevices-add-deviceidtype-option.patch
deleted file mode 100644
index 6d4e6bf..0000000
--- a/SOURCES/lvm2-2_03_13-lvmdevices-add-deviceidtype-option.patch
+++ /dev/null
@@ -1,211 +0,0 @@
- lib/device/device_id.c | 32 ++++++++++++++----------
- man/lvmdevices.8_des   | 68 +++++++++++++++++++++++++++++++++++++++-----------
- tools/args.h           |  5 ++++
- tools/command-lines.in |  1 +
- tools/lvmdevices.c     |  7 ++++--
- 5 files changed, 84 insertions(+), 29 deletions(-)
-
-diff --git a/lib/device/device_id.c b/lib/device/device_id.c
-index 1b98487..f158e4f 100644
---- a/lib/device/device_id.c
-+++ b/lib/device/device_id.c
-@@ -931,6 +931,7 @@ int device_id_add(struct cmd_context *cmd, struct device *dev, const char *pvid_
- 	/*
- 	 * Choose the device_id type for the device being added.
- 	 *
-+	 * 0. use an idtype specified by the user
- 	 * 1. use an idtype specific to a special/virtual device type
- 	 *    e.g. loop, mpath, crypt, lvmlv, md, etc.
- 	 * 2. use an idtype specified by user option.
-@@ -939,6 +940,24 @@ int device_id_add(struct cmd_context *cmd, struct device *dev, const char *pvid_
- 	 * 5. use devname as the last resort.
- 	 */
- 
-+	if (idtype_arg) {
-+		if (!(idtype = idtype_from_str(idtype_arg)))
-+			log_warn("WARNING: ignoring unknown device_id type %s.", idtype_arg);
-+		else {
-+			if (id_arg) {
-+				if ((idname = strdup(id_arg)))
-+					goto id_done;
-+				log_warn("WARNING: ignoring device_id name %s.", id_arg);
-+			}
-+
-+			if ((idname = device_id_system_read(cmd, dev, idtype)))
-+				goto id_done;
-+
-+			log_warn("WARNING: ignoring deviceidtype %s which is not available for device.", idtype_arg);
-+			idtype = 0;
-+		}
-+	}
-+
- 	if (MAJOR(dev->dev) == cmd->dev_types->device_mapper_major) {
- 		if (_dev_has_mpath_uuid(cmd, dev, &idname)) {
- 			idtype = DEV_ID_TYPE_MPATH_UUID;
-@@ -972,19 +991,6 @@ int device_id_add(struct cmd_context *cmd, struct device *dev, const char *pvid_
- 		log_warn("Missing support for DRBD idtype");
- 	}
- 
--	if (idtype_arg) {
--		if (!(idtype = idtype_from_str(idtype_arg)))
--			log_warn("WARNING: ignoring unknown device_id type %s.", idtype_arg);
--		else {
--			if (id_arg) {
--				if (!(idname = strdup(id_arg)))
--					stack;
--				goto id_done;
--			}
--			goto id_name;
--		}
--	}
--
- 	/*
- 	 * No device-specific, existing, or user-specified idtypes,
- 	 * so use first available of sys_wwid / sys_serial / devname.
-diff --git a/man/lvmdevices.8_des b/man/lvmdevices.8_des
-index 015aa11..2335456 100644
---- a/man/lvmdevices.8_des
-+++ b/man/lvmdevices.8_des
-@@ -9,18 +9,18 @@ remove it from the devices file with lvmdevices --deldev.  The
- vgimportdevices(8) command adds all PVs from a VG to the devices file,
- and updates the VG metadata to include device IDs of the PVs.
- .P
--Commands adding new devices to the devices file necessarily look outside
--the existing devices file to find the devices to add.  pvcreate, vgcreate,
--and vgextend also look outside the devices file to create new PVs and add
--them to the devices file.
-+Commands that add new devices to the devices file necessarily look outside
-+the existing devices file to find the devices being added.  pvcreate,
-+vgcreate, and vgextend also look outside the devices file to create new
-+PVs and add those PVs to the devices file.
- .P
- LVM records devices in the devices file using hardware-specific IDs, such
- as the WWID, and attempts to use subsystem-specific IDs for virtual device
--types (which also aim to be as unique and stable as possible.)
--These device IDs are also written in the VG metadata.  When no hardware or
-+types (which also aim to be as unique and stable as possible.) These
-+device IDs are also written in the VG metadata.  When no hardware or
- virtual ID is available, lvm falls back using the unstable device name as
--the device ID.  When devnames are used, lvm performs extra scanning to
--find devices if their devname changes, e.g. after reboot.
-+the device ID.  When devnames are used as IDs, lvm performs extra scanning
-+to find devices if their devname changes, e.g. after reboot.
- .P
- When proper device IDs are used, an lvm command will not look at devices
- outside the devices file, but when devnames are used as a fallback, lvm
-@@ -34,12 +34,13 @@ overriding the devices file.  The listed devices act as a sort of devices
- file in terms of limiting which devices lvm will see and use.  Devices
- that are not listed will appear to be missing to the lvm command.
- .P
--Multiple devices files can be kept in \fI#DEFAULT_SYS_DIR#/devices\fP, which allows lvm
--to be used with different sets of devices, e.g. system devices do not need
--to be exposed to a specific application, and the application can use lvm on
--its own devices that are not exposed to the system.  The option
----devicesfile <filename> is used to select the devices file to use with the
--command.  Without the option set, the default system devices file is used.
-+Multiple devices files can be kept \fI#DEFAULT_SYS_DIR#/devices\fP, which
-+allows lvm to be used with different sets of devices.  For example, system
-+devices do not need to be exposed to a specific application, and the
-+application can use lvm on its own devices that are not exposed to the
-+system.  The option --devicesfile <filename> is used to select the devices
-+file to use with the command.  Without the option set, the default system
-+devices file is used.
- .P
- Setting --devicesfile "" causes lvm to not use a devices file.
- .P
-@@ -59,3 +60,42 @@ if it does not yet exist.
- .P
- It is recommended to use lvm commands to make changes to the devices file to
- ensure proper updates.
-+.P
-+The device ID and device ID type are included in the VG metadata and can
-+be reported with pvs -o deviceid,deviceidtype.  (Note that the lvmdevices
-+command does not update VG metadata, but subsequent lvm commands modifying
-+the metadata will include the device ID.)
-+.P
-+Possible device ID types are:
-+.br
-+.IP \[bu] 2
-+.B sys_wwid
-+uses the wwid reported by sysfs.  This is the first choice for non-virtual
-+devices.
-+.IP \[bu] 2
-+.B sys_serial
-+uses the serial number reported by sysfs.  This is the second choice for
-+non-virtual devices.
-+.IP \[bu] 2
-+.B mpath_uuid
-+is used for dm multipath devices, reported by sysfs.
-+.IP \[bu] 2
-+.B crypt_uuid
-+is used for dm crypt devices, reported by sysfs.
-+.IP \[bu] 2
-+.B md_uuid
-+is used for md devices, reported by sysfs.
-+.B lvmlv_uuid
-+is used if a PV is placed on top of an lvm LV, reported by sysfs.
-+.IP \[bu] 2
-+.B loop_file
-+is used for loop devices, the backing file name repored by sysfs.
-+.IP \[bu] 2
-+.B devname
-+the device name is used if no other type applies.
-+.P
-+
-+The default choice for device ID type can be overriden using lvmdevices
-+--addev --deviceidtype <type>.  If the specified type is available for the
-+device it will be used, otherwise the device will be added using the type
-+that would otherwise be chosen.
-diff --git a/tools/args.h b/tools/args.h
-index 741c82b..d4f23f8 100644
---- a/tools/args.h
-+++ b/tools/args.h
-@@ -228,6 +228,11 @@ arg(detachprofile_ARG, '\0', "detachprofile", 0, 0, 0,
-     "Detaches a metadata profile from a VG or LV.\n"
-     "See \\fBlvm.conf\\fP(5) for more information about profiles.\n")
- 
-+arg(deviceidtype_ARG, '\0', "deviceidtype", string_VAL, 0, 0,
-+    "The type of device ID to use for the device.\n"
-+    "If the specified type is available for the device,\n"
-+    "then it will override the default type that lvm would use.\n")
-+
- arg(devices_ARG, '\0', "devices", pv_VAL, ARG_GROUPABLE, 0,
-     "Devices that the command can use. This option can be repeated\n"
-     "or accepts a comma separated list of devices. This overrides\n"
-diff --git a/tools/command-lines.in b/tools/command-lines.in
-index 67c37ff..8607305 100644
---- a/tools/command-lines.in
-+++ b/tools/command-lines.in
-@@ -1430,6 +1430,7 @@ ID: lvmdevices_update
- DESC: Update the devices file to fix incorrect values.
- 
- lvmdevices --adddev PV
-+OO: --deviceidtype String
- ID: lvmdevices_edit
- DESC: Add a device to the devices file.
- 
-diff --git a/tools/lvmdevices.c b/tools/lvmdevices.c
-index 6b3e056..3448bdd 100644
---- a/tools/lvmdevices.c
-+++ b/tools/lvmdevices.c
-@@ -265,6 +265,7 @@ int lvmdevices(struct cmd_context *cmd, int argc, char **argv)
- 
- 	if (arg_is_set(cmd, adddev_ARG)) {
- 		const char *devname;
-+		const char *deviceidtype;
- 
- 		if (!(devname = arg_str_value(cmd, adddev_ARG, NULL)))
- 			goto_bad;
-@@ -311,8 +312,10 @@ int lvmdevices(struct cmd_context *cmd, int argc, char **argv)
- 				 dev_name(dev), dev_filtered_reason(dev));
- 		}
- 
--		/* allow deviceidtype_ARG/deviceid_ARG ? */
--		if (!device_id_add(cmd, dev, dev->pvid, NULL, NULL))
-+		/* also allow deviceid_ARG ? */
-+		deviceidtype = arg_str_value(cmd, deviceidtype_ARG, NULL);
-+
-+		if (!device_id_add(cmd, dev, dev->pvid, deviceidtype, NULL))
- 			goto_bad;
- 		if (!device_ids_write(cmd))
- 			goto_bad;
diff --git a/SOURCES/lvm2-2_03_13-lvremove-fix-removing-thin-pool-with-writecache-on-d.patch b/SOURCES/lvm2-2_03_13-lvremove-fix-removing-thin-pool-with-writecache-on-d.patch
deleted file mode 100644
index 45a878d..0000000
--- a/SOURCES/lvm2-2_03_13-lvremove-fix-removing-thin-pool-with-writecache-on-d.patch
+++ /dev/null
@@ -1,150 +0,0 @@
- lib/metadata/lv_manip.c                | 19 +++++++++
- lib/metadata/metadata-exported.h       |  2 +
- lib/metadata/thin_manip.c              | 12 ++++++
- test/shell/lvremove-thindata-caches.sh | 71 ++++++++++++++++++++++++++++++++++
- 4 files changed, 104 insertions(+)
- create mode 100644 test/shell/lvremove-thindata-caches.sh
-
-diff --git a/lib/metadata/lv_manip.c b/lib/metadata/lv_manip.c
-index 508f78c..37dd361 100644
---- a/lib/metadata/lv_manip.c
-+++ b/lib/metadata/lv_manip.c
-@@ -6692,6 +6692,25 @@ int lv_remove_single(struct cmd_context *cmd, struct logical_volume *lv,
- 			return_0;
- 	}
- 
-+	/* if thin pool data lv is writecache, then detach and remove the writecache */
-+	if (lv_is_thin_pool(lv)) {
-+		struct logical_volume *data_lv = data_lv_from_thin_pool(lv);
-+
-+		if (data_lv && lv_is_writecache(data_lv)) {
-+			struct logical_volume *cachevol_lv = first_seg(data_lv)->writecache;
-+
-+			if (!lv_detach_writecache_cachevol(data_lv, 1)) {
-+				log_error("Failed to detach writecache from %s", display_lvname(data_lv));
-+				return 0;
-+			}
-+
-+			if (!lv_remove_single(cmd, cachevol_lv, force, 1)) {
-+				log_error("Failed to remove cachevol %s.", display_lvname(cachevol_lv));
-+				return 0;
-+			}
-+		}
-+	}
-+
- 	if (lv_is_writecache(lv)) {
- 		struct logical_volume *cachevol_lv = first_seg(lv)->writecache;
- 
-diff --git a/lib/metadata/metadata-exported.h b/lib/metadata/metadata-exported.h
-index c611635..54bc0d0 100644
---- a/lib/metadata/metadata-exported.h
-+++ b/lib/metadata/metadata-exported.h
-@@ -927,6 +927,8 @@ int handle_pool_metadata_spare(struct volume_group *vg, uint32_t extents,
- int vg_set_pool_metadata_spare(struct logical_volume *lv);
- int vg_remove_pool_metadata_spare(struct volume_group *vg);
- 
-+struct logical_volume *data_lv_from_thin_pool(struct logical_volume *pool_lv);
-+
- int attach_thin_external_origin(struct lv_segment *seg,
- 				struct logical_volume *external_lv);
- int detach_thin_external_origin(struct lv_segment *seg);
-diff --git a/lib/metadata/thin_manip.c b/lib/metadata/thin_manip.c
-index 451c382..6ce88bd 100644
---- a/lib/metadata/thin_manip.c
-+++ b/lib/metadata/thin_manip.c
-@@ -21,6 +21,18 @@
- #include "lib/config/defaults.h"
- #include "lib/display/display.h"
- 
-+struct logical_volume *data_lv_from_thin_pool(struct logical_volume *pool_lv)
-+{
-+	struct lv_segment *seg_thinpool = first_seg(pool_lv);
-+
-+	if (!seg_thinpool || !seg_is_thin_pool(seg_thinpool)) {
-+		log_error(INTERNAL_ERROR "data_lv_from_thin_pool arg not thin pool %s", pool_lv->name);
-+		return NULL;
-+	}
-+
-+	return seg_thinpool->areas[0].u.lv.lv;
-+}
-+
- /* TODO: drop unused no_update */
- int attach_pool_message(struct lv_segment *pool_seg, dm_thin_message_t type,
- 			struct logical_volume *lv, uint32_t delete_id,
-diff --git a/test/shell/lvremove-thindata-caches.sh b/test/shell/lvremove-thindata-caches.sh
-new file mode 100644
-index 0000000..ba099c3
---- /dev/null
-+++ b/test/shell/lvremove-thindata-caches.sh
-@@ -0,0 +1,71 @@
-+#!/usr/bin/env bash
-+
-+# Copyright (C) 2017-2020 Red Hat, Inc. All rights reserved.
-+#
-+# This copyrighted material is made available to anyone wishing to use,
-+# modify, copy, or redistribute it subject to the terms and conditions
-+# of the GNU General Public License v.2.
-+#
-+# You should have received a copy of the GNU General Public License
-+# along with this program; if not, write to the Free Software Foundation,
-+# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
-+
-+SKIP_WITH_LVMPOLLD=1
-+
-+. lib/inittest
-+
-+aux have_cache 1 10 0 || skip
-+aux have_writecache 1 0 0 || skip
-+which mkfs.xfs || skip
-+
-+aux prepare_devs 6 70 # want 64M of usable space from each dev
-+
-+vgcreate $SHARED $vg "$dev1" "$dev2" "$dev3" "$dev4" "$dev5" "$dev6"
-+
-+# lv1 is thinpool LV: 128M
-+# lv2 is fast LV:      64M
-+# lv3 is thin LV:       1G
-+
-+#
-+# Test lvremove of a thinpool that uses cache|writecache on data
-+#
-+
-+# attach writecache to thinpool data
-+lvcreate --type thin-pool -n $lv1 -L128M --poolmetadataspare n $vg "$dev1" "$dev2"
-+lvcreate --type thin -n $lv3 -V1G --thinpool $lv1 $vg
-+lvcreate -n $lv2 -L64M -an $vg "$dev3"
-+lvconvert -y --type writecache --cachevol $lv2 $vg/$lv1
-+lvchange -ay $vg/$lv1
-+lvs -a $vg
-+mkfs.xfs -f -s size=4096 "$DM_DEV_DIR/$vg/$lv3"
-+lvremove -y $vg/$lv1
-+
-+# attach cache/writeback (cachevol) to thinpool data
-+lvcreate --type thin-pool -n $lv1 -L128M --poolmetadataspare n $vg "$dev1" "$dev2"
-+lvcreate --type thin -n $lv3 -V1G --thinpool $lv1 $vg
-+lvcreate -n $lv2 -L64M -an $vg "$dev3"
-+lvconvert -y --type cache --cachevol $lv2 --cachemode writeback $vg/$lv1
-+lvchange -ay $vg/$lv1
-+mkfs.xfs -f -s size=4096 "$DM_DEV_DIR/$vg/$lv3"
-+lvremove -y $vg/$lv1
-+
-+# attach cache/writethrough (cachevol) to thinpool data
-+lvcreate --type thin-pool -n $lv1 -L128M --poolmetadataspare n $vg "$dev1" "$dev2"
-+lvcreate --type thin -n $lv3 -V1G --thinpool $lv1 $vg
-+lvcreate -n $lv2 -L64M -an $vg "$dev3"
-+lvconvert -y --type cache --cachevol $lv2 --cachemode writethrough $vg/$lv1
-+lvchange -ay $vg/$lv1
-+mkfs.xfs -f -s size=4096 "$DM_DEV_DIR/$vg/$lv3"
-+lvremove -y $vg/$lv1
-+
-+# attach cache (cachepool) to thinpool data
-+lvcreate --type thin-pool -n $lv1 -L128M --poolmetadataspare n $vg "$dev1" "$dev2"
-+lvcreate --type thin -n $lv3 -V1G --thinpool $lv1 $vg
-+lvcreate -y --type cache-pool -n $lv2 -L64M --poolmetadataspare n $vg "$dev3" "$dev6"
-+lvconvert -y --type cache --cachepool $lv2 --poolmetadataspare n $vg/$lv1
-+lvchange -ay $vg/$lv1
-+mkfs.xfs -f -s size=4096 "$DM_DEV_DIR/$vg/$lv3"
-+lvremove -y $vg/$lv1
-+
-+vgremove -f $vg
-+
diff --git a/SOURCES/lvm2-2_03_13-man-vdoimport-page.patch b/SOURCES/lvm2-2_03_13-man-vdoimport-page.patch
deleted file mode 100644
index fe6032c..0000000
--- a/SOURCES/lvm2-2_03_13-man-vdoimport-page.patch
+++ /dev/null
@@ -1,102 +0,0 @@
- man/vdoimport.8_main | 92 ++++++++++++++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 92 insertions(+)
- create mode 100644 man/vdoimport.8_main
-
-diff --git a/man/vdoimport.8_main b/man/vdoimport.8_main
-new file mode 100644
-index 0000000..1f32909
---- /dev/null
-+++ b/man/vdoimport.8_main
-@@ -0,0 +1,92 @@
-+.TH "FSADM" "8" "LVM TOOLS #VERSION#" "Red Hat, Inc" "\""
-+.
-+.SH "NAME"
-+.
-+vdoimport \(em utility to import VDO volumes into a new volume group.
-+.
-+.SH SYNOPSIS
-+.
-+.PD 0
-+.ad l
-+.TP 10
-+.B vdoimport
-+.RI [ options ]
-+.IR device
-+.
-+.PD
-+.
-+.SH DESCRIPTION
-+.
-+vdoimport utility imports VDO volumes created and managed by
-+.BR vdo (8)
-+manager into
-+.BR lvm2 (8)
-+managed VDO LV. This is realized by moving VDO superblock by 2MiB
-+and creating lvm2 metadata at the front of this device. The operation is not reversible,
-+thus after conversion to lvm2 the access to VDO data is only possible with
-+.BR lvm2 (8)
-+commands,
-+.BR vdo (8)
-+manager no longer control such volume.
-+.
-+.SH OPTIONS
-+.
-+.TP
-+.BR -f | --force
-+Bypass some sanity checks.
-+.
-+.TP
-+.BR -h | --help
-+Display the help text.
-+.
-+.TP
-+.BR -n | --name
-+Specifies the name of converted VDO LV. When the name is not specified,
-+some automatic name is selected. In case the converted VDO volume is
-+already using LV a backend device, the name of this LV is used for VDO LV.
-+In this case also the of volume group must stay same.
-+.
-+.TP
-+.BR -v | --verbose
-+Be more verbose.
-+.
-+.TP
-+.BR -y | --yes
-+Answer "yes" at any prompts.
-+.
-+.TP
-+.BR --dry-run
-+Print commands without running them.
-+.
-+.
-+.SH DIAGNOSTICS
-+.
-+On successful completion, the status code is 0.
-+A status code of 1 is used for failure.
-+.
-+.SH EXAMPLES
-+.
-+Convert VDO volume created by vdo manager into logical volume LV1 with within volume group VG1.
-+.P
-+#
-+.B vdoimport --name VG1/LV1 /dev/mapper/vdo-volume
-+.
-+.SH ENVIRONMENT VARIABLES
-+.
-+.TP
-+.B TMPDIR
-+The temporary directory name for mount points. Defaults to "\fI/tmp\fP".
-+.TP
-+.B DM_DEV_DIR
-+The device directory name.
-+Defaults to "\fI/dev\fP" and must be an absolute path.
-+.
-+.SH SEE ALSO
-+.
-+.nh
-+.ad l
-+.BR lvm (8),
-+.BR lvm.conf (5),
-+.P
-+.BR vdo (8),
-+.BR vdo2lvm (8),
diff --git a/SOURCES/lvm2-2_03_13-test.patch b/SOURCES/lvm2-2_03_13-test.patch
deleted file mode 100644
index f6672b7..0000000
--- a/SOURCES/lvm2-2_03_13-test.patch
+++ /dev/null
@@ -1,61 +0,0 @@
- test/shell/vgsplit-cache.sh | 47 +++++++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 47 insertions(+)
-
-diff --git a/test/shell/vgsplit-cache.sh b/test/shell/vgsplit-cache.sh
-index eba85be..202e4b5 100644
---- a/test/shell/vgsplit-cache.sh
-+++ b/test/shell/vgsplit-cache.sh
-@@ -75,6 +75,53 @@ lvremove -y $vg
- vgremove -ff $vg
- vgremove -ff $vg1
- 
-+#
-+# Check we handle pmspare for splitted VGs
-+#
-+aux prepare_vg 7
-+
-+# Create cache-pool and pmspare on single PV1
-+lvcreate -L10 --type cache-pool $vg/cpool "$dev1"
-+# Move spare to separate PV3
-+pvmove -n $vg/lvol0_pmspare "$dev1" "$dev3"
-+# Create origin on PV2
-+lvcreate -L10 -n orig $vg  "$dev2"
-+lvconvert -H -y --cachepool $vg/cpool $vg/orig
-+
-+vgchange -an $vg
-+
-+# Check we do not create new _pmspare
-+vgsplit --poolmetadataspare n  $vg $vg1 "$dev2" "$dev1"
-+
-+check lv_exists $vg/lvol0_pmspare
-+check lv_not_exists $vg1/lvol0_pmspare
-+
-+vgremove $vg
-+vgremove -f $vg1
-+
-+
-+aux prepare_vg 7
-+
-+# Again - now with handling _pmspare by vgsplit
-+lvcreate -L10 --type cache-pool $vg/cpool "$dev1"
-+# Move spare to separate PV3
-+pvmove -n $vg/lvol0_pmspare "$dev1" "$dev3"
-+# Create origin on PV2
-+lvcreate -L10 -n orig $vg  "$dev2"
-+lvconvert -H -y --cachepool $vg/cpool $vg/orig
-+
-+vgchange -an $vg
-+
-+# Handle _pmspare  (default)
-+vgsplit --poolmetadataspare y  $vg $vg1 "$dev2" "$dev1"
-+
-+check lv_not_exists $vg/lvol0_pmspare
-+check lv_exists $vg1/lvol0_pmspare
-+
-+vgremove $vg
-+vgremove -f $vg1
-+
-+
- vgcreate $vg "$dev1" "$dev2" "$dev3" "$dev4"
- 
- lvcreate -L6 -n $lv1 -an $vg "$dev2"
diff --git a/SOURCES/lvm2-2_03_13-tests-extend-vgmerge-testing.patch b/SOURCES/lvm2-2_03_13-tests-extend-vgmerge-testing.patch
deleted file mode 100644
index 22dca89..0000000
--- a/SOURCES/lvm2-2_03_13-tests-extend-vgmerge-testing.patch
+++ /dev/null
@@ -1,53 +0,0 @@
- test/shell/vgmerge-operation.sh | 42 +++++++++++++++++++++++++++++++++++++++++
- 1 file changed, 42 insertions(+)
-
-diff --git a/test/shell/vgmerge-operation.sh b/test/shell/vgmerge-operation.sh
-index 21889e9..0bf517d 100644
---- a/test/shell/vgmerge-operation.sh
-+++ b/test/shell/vgmerge-operation.sh
-@@ -80,3 +80,45 @@ grep "Duplicate logical volume name \"$lv1\" in \"$vg2\" and \"$vg1" err
- check pvlv_counts $vg1 2 1 0
- check pvlv_counts $vg2 2 1 0
- vgremove -f $vg1 $vg2
-+
-+
-+# 'vgmerge' handle pmspare for merged VG
-+if aux have_thin 1 5 0; then
-+
-+# With disabled pmspare nothing is created
-+vgcreate $vg1 "$dev1" "$dev2"
-+vgcreate $vg2 "$dev3" "$dev4"
-+lvcreate -T -L8M $vg1/pool1 --poolmetadatasize 8M --poolmetadataspare n
-+lvcreate -T -L8M $vg2/pool2 --poolmetadatasize 4M --poolmetadataspare n
-+vgchange -an $vg1 $vg2
-+
-+vgmerge --poolmetadataspare n $vg1 $vg2
-+check lv_not_exists $vg/lvol0_pmspare
-+vgremove -ff $vg1
-+
-+
-+# With pmspare handling there are one created
-+vgcreate $vg1 "$dev1" "$dev2"
-+vgcreate $vg2 "$dev3" "$dev4"
-+lvcreate -T -L8M $vg1/pool1 --poolmetadatasize 8M --poolmetadataspare n
-+lvcreate -T -L8M $vg2/pool2 --poolmetadatasize 4M --poolmetadataspare n
-+vgchange -an $vg1 $vg2
-+
-+vgmerge $vg1 $vg2
-+check lv_field $vg1/lvol0_pmspare size "8.00m"
-+vgremove -ff $vg1
-+
-+
-+# When merged, bigger pmspare is preserved
-+vgcreate $vg1 "$dev1" "$dev2"
-+vgcreate $vg2 "$dev3" "$dev4"
-+lvcreate -T -L8M $vg1/pool1 --poolmetadatasize 8M
-+lvcreate -T -L8M $vg2/pool2 --poolmetadatasize 4M
-+vgchange -an $vg1 $vg2
-+
-+vgmerge $vg1 $vg2
-+
-+check lv_field $vg1/lvol0_pmspare size "8.00m"
-+vgremove -ff $vg1
-+
-+fi
diff --git a/SOURCES/lvm2-2_03_13-thin-fix-component-detection-of-external-origin.patch b/SOURCES/lvm2-2_03_13-thin-fix-component-detection-of-external-origin.patch
deleted file mode 100644
index 5b97d90..0000000
--- a/SOURCES/lvm2-2_03_13-thin-fix-component-detection-of-external-origin.patch
+++ /dev/null
@@ -1,63 +0,0 @@
- WHATS_NEW                          |  1 +
- lib/activate/activate.c            |  5 ++++-
- test/shell/lvconvert-cache-thin.sh | 22 ++++++++++++++++++++++
- 3 files changed, 27 insertions(+), 1 deletion(-)
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index 5806ecb..097160e 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,5 +1,6 @@
- Version 2.03.13 - 
- ===============================
-+  Fix detection of active components of external origin volume.
-   Add vdoimport tool to support conversion of VDO volumes.
-   Support configurable allocation/vdo_pool_header_size.
-   Fix handling of lvconvert --type vdo-pool --virtualsize.
-diff --git a/lib/activate/activate.c b/lib/activate/activate.c
-index 6bda738..94fc944 100644
---- a/lib/activate/activate.c
-+++ b/lib/activate/activate.c
-@@ -2740,7 +2740,10 @@ static int _component_cb(struct logical_volume *lv, void *data)
- 	    (lv_is_thin_pool(lv) && pool_is_active(lv)))
- 		return -1;
- 
--	if (lv_is_active(lv)) {
-+	/* External origin is activated through thinLV and uses -real suffix.
-+	 * Note: for old clustered logic we would need to check for all thins */
-+	if ((lv_is_external_origin(lv) && lv_info(lv->vg->cmd, lv, 1, NULL, 0, 0)) ||
-+	    lv_is_active(lv)) {
- 		if (!lv_is_component(lv) || lv_is_visible(lv))
- 			return -1;	/* skip whole subtree */
- 
-diff --git a/test/shell/lvconvert-cache-thin.sh b/test/shell/lvconvert-cache-thin.sh
-index 7dda6e6..9254239 100644
---- a/test/shell/lvconvert-cache-thin.sh
-+++ b/test/shell/lvconvert-cache-thin.sh
-@@ -67,4 +67,26 @@ fail lvconvert --yes --thinpool $vg/$lv1 --poolmetadata $vg/$lv
- # Thin-pool CAN use cached data LV
- lvconvert --yes --thinpool $vg/$lv
- 
-+lvremove -f $vg
-+
-+# Check we can active snapshot of cached external origin (BZ: 1967744)
-+lvcreate -T -L10M $vg/pool "$dev1"
-+
-+lvcreate -L10M -n origin $vg "$dev1"
-+lvcreate -H -L4M -n CPOOL $vg/origin "$dev2"
-+
-+# Use cached origin as external origin
-+lvconvert -y -T --thinpool $vg/pool --originname extorig origin
-+
-+# Check we can easily create snapshot of such LV
-+lvcreate -y -kn -n snap -s $vg/origin
-+
-+# Deactivate everything and do a component activation of _cmeta volume
-+lvchange -an $vg
-+lvchange -ay -y $vg/CPOOL_cpool_cmeta
-+
-+# Now this must fail since component volume is active
-+not lvcreate -y -kn -n snap2 -s $vg/origin |& tee err
-+grep "cmeta is active" err
-+
- vgremove -f $vg
diff --git a/SOURCES/lvm2-2_03_13-vdo-add-vdoimport-support.patch b/SOURCES/lvm2-2_03_13-vdo-add-vdoimport-support.patch
deleted file mode 100644
index aed2254..0000000
--- a/SOURCES/lvm2-2_03_13-vdo-add-vdoimport-support.patch
+++ /dev/null
@@ -1,729 +0,0 @@
- WHATS_NEW                 |   3 +
- configure                 |  25 +++
- configure.ac              |  15 ++
- include/configure.h.in    |   3 +
- man/Makefile.in           |   7 +-
- scripts/Makefile.in       |   4 +
- scripts/vdoimport.sh      | 376 ++++++++++++++++++++++++++++++++++++++++++++++
- test/Makefile.in          |   1 +
- test/shell/vdo-convert.sh | 110 ++++++++++++++
- 9 files changed, 543 insertions(+), 1 deletion(-)
- create mode 100755 scripts/vdoimport.sh
- create mode 100644 test/shell/vdo-convert.sh
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index 04c6dcd..5806ecb 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,5 +1,8 @@
- Version 2.03.13 - 
- ===============================
-+  Add vdoimport tool to support conversion of VDO volumes.
-+  Support configurable allocation/vdo_pool_header_size.
-+  Fix handling of lvconvert --type vdo-pool --virtualsize.
-   Fix load of kvdo target when it is not present in memory (2.03.12).
- 
- Version 2.03.12 - 07th May 2021
-diff --git a/configure b/configure
-index 7c6bd48..661702d 100755
---- a/configure
-+++ b/configure
-@@ -643,6 +643,8 @@ WRITE_INSTALL
- WRITECACHE
- VDO_LIB
- VDO_INCLUDE
-+VDOIMPORT_PATH
-+VDOIMPORT
- VDO
- VALGRIND_POOL
- USRSBINDIR
-@@ -966,6 +968,7 @@ enable_dbus_service
- enable_pkgconfig
- enable_write_install
- enable_fsadm
-+enable_vdoimport
- enable_blkdeactivate
- enable_dmeventd
- enable_selinux
-@@ -1701,6 +1704,7 @@ Optional Features:
-   --enable-pkgconfig      install pkgconfig support
-   --enable-write_install  install user writable files
-   --disable-fsadm         disable fsadm
-+  --disable-vdoimport     disable vdoimport
-   --disable-blkdeactivate disable blkdeactivate
-   --enable-dmeventd       enable the device-mapper event daemon
-   --disable-selinux       disable selinux support
-@@ -3128,6 +3132,7 @@ case "$host_os" in
- 		DM_IOCTLS=yes
- 		SELINUX=yes
- 		FSADM=yes
-+		VDOIMPORT=yes
- 		BLKDEACTIVATE=yes
- 		;;
- 	darwin*)
-@@ -3141,6 +3146,7 @@ case "$host_os" in
- 		DM_IOCTLS=no
- 		SELINUX=no
- 		FSADM=no
-+		VDOIMPORT=no
- 		BLKDEACTIVATE=no
- 		;;
- 	*)
-@@ -12371,6 +12377,18 @@ fi
- { $as_echo "$as_me:${as_lineno-$LINENO}: result: $FSADM" >&5
- $as_echo "$FSADM" >&6; }
- 
-+
-+################################################################################
-+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to install vdoimport" >&5
-+$as_echo_n "checking whether to install vdoimport... " >&6; }
-+# Check whether --enable-vdoimport was given.
-+if test "${enable_vdoimport+set}" = set; then :
-+  enableval=$enable_vdoimport; VDOIMPORT=$enableval
-+fi
-+
-+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $VDOIMPORT" >&5
-+$as_echo "$VDOIMPORT" >&6; }
-+
- ################################################################################
- { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to install blkdeactivate" >&5
- $as_echo_n "checking whether to install blkdeactivate... " >&6; }
-@@ -13857,6 +13875,13 @@ cat >>confdefs.h <<_ACEOF
- _ACEOF
- 
- 
-+VDOIMPORT_PATH="$SBINDIR/vdoimport"
-+
-+cat >>confdefs.h <<_ACEOF
-+#define VDOIMPORT_PATH "$VDOIMPORT_PATH"
-+_ACEOF
-+
-+
- ################################################################################
- if test "$BUILD_DMEVENTD" = yes; then
- 
-diff --git a/configure.ac b/configure.ac
-index 1a49e7f..5a8b486 100644
---- a/configure.ac
-+++ b/configure.ac
-@@ -45,6 +45,7 @@ case "$host_os" in
- 		DM_IOCTLS=yes
- 		SELINUX=yes
- 		FSADM=yes
-+		VDOIMPORT=yes
- 		BLKDEACTIVATE=yes
- 		;;
- 	darwin*)
-@@ -58,6 +59,7 @@ case "$host_os" in
- 		DM_IOCTLS=no
- 		SELINUX=no
- 		FSADM=no
-+		VDOIMPORT=no
- 		BLKDEACTIVATE=no
- 		;;
- 	*)
-@@ -1291,6 +1293,14 @@ AC_ARG_ENABLE(fsadm, AC_HELP_STRING([--disable-fsadm], [disable fsadm]),
- 	      FSADM=$enableval)
- AC_MSG_RESULT($FSADM)
- 
-+
-+################################################################################
-+dnl -- Enable vdoimport
-+AC_MSG_CHECKING(whether to install vdoimport)
-+AC_ARG_ENABLE(vdoimport, AC_HELP_STRING([--disable-vdoimport], [disable vdoimport]),
-+	      VDOIMPORT=$enableval)
-+AC_MSG_RESULT($VDOIMPORT)
-+
- ################################################################################
- dnl -- Enable blkdeactivate
- AC_MSG_CHECKING(whether to install blkdeactivate)
-@@ -1646,6 +1656,9 @@ USRSBINDIR="$(eval echo $(eval echo $usrsbindir))"
- FSADM_PATH="$SBINDIR/fsadm"
- AC_DEFINE_UNQUOTED(FSADM_PATH, ["$FSADM_PATH"], [Path to fsadm binary.])
- 
-+VDOIMPORT_PATH="$SBINDIR/vdoimport"
-+AC_DEFINE_UNQUOTED(VDOIMPORT_PATH, ["$VDOIMPORT_PATH"], [Path to vdoimport binary.])
-+
- ################################################################################
- dnl -- dmeventd pidfile and executable path
- if test "$BUILD_DMEVENTD" = yes; then
-@@ -1882,6 +1895,8 @@ AC_SUBST(SILENT_RULES)
- AC_SUBST(USRSBINDIR)
- AC_SUBST(VALGRIND_POOL)
- AC_SUBST(VDO)
-+AC_SUBST(VDOIMPORT)
-+AC_SUBST(VDOIMPORT_PATH)
- AC_SUBST(VDO_FORMAT_CMD)
- AC_SUBST(VDO_INCLUDE)
- AC_SUBST(VDO_LIB)
-diff --git a/include/configure.h.in b/include/configure.h.in
-index 671d201..6df8d89 100644
---- a/include/configure.h.in
-+++ b/include/configure.h.in
-@@ -684,6 +684,9 @@
- /* Enable a valgrind aware build of pool */
- #undef VALGRIND_POOL
- 
-+/* Path to vdoimport binary. */
-+#undef VDOIMPORT_PATH
-+
- /* The path to 'vdoformat', if available. */
- #undef VDO_FORMAT_CMD
- 
-diff --git a/man/Makefile.in b/man/Makefile.in
-index 29afc77..d60a92c 100644
---- a/man/Makefile.in
-+++ b/man/Makefile.in
-@@ -23,6 +23,7 @@ else
- endif
- 
- FSADMMAN = fsadm.8
-+VDOIMPORTMAN = vdoimport.8
- BLKDEACTIVATEMAN = blkdeactivate.8
- DMEVENTDMAN = dmeventd.8
- DMFILEMAPDMAN = dmfilemapd.8
-@@ -50,7 +51,7 @@ MAN8SYSTEMD_GENERATORS=lvm2-activation-generator.8
- 
- ifeq (,$(findstring $(MAKECMDGOALS), distclean all_man install_all_man))
-   MAN7 += lvmcache.7 lvmthin.7 lvmvdo.7
--  MAN8+=$(FSADMMAN) $(LVMPOLLDMAN) $(LVMLOCKDMAN) $(LVMDBUSDMAN)
-+  MAN8+=$(FSADMMAN) $(LVMPOLLDMAN) $(LVMLOCKDMAN) $(LVMDBUSDMAN) $(VDOIMPORTMAN)
-   MAN8DM+=$(BLKDEACTIVATEMAN) $(DMEVENTDMAN) $(DMFILEMAPDMAN)
-   MAN8CLUSTER+=$(CMIRRORDMAN)
- else
-@@ -58,6 +59,10 @@ else
-     MAN8+=$(FSADMMAN)
-   endif
- 
-+  ifeq ("@VDOIMPORT@", "yes")
-+    MAN8+=$(VDOIMPORTMAN)
-+  endif
-+
-   ifeq ("@BUILD_LVMDBUSD@", "yes")
-     MAN8+=$(LVMDBUSDMAN)
-   endif
-diff --git a/scripts/Makefile.in b/scripts/Makefile.in
-index e8f6742..1fe88ca 100644
---- a/scripts/Makefile.in
-+++ b/scripts/Makefile.in
-@@ -31,6 +31,10 @@ ifeq ("@FSADM@", "yes")
- 	LVM_SCRIPTS += fsadm.sh
- endif
- 
-+ifeq ("@VDOIMPORT@", "yes")
-+	LVM_SCRIPTS += vdoimport.sh
-+endif
-+
- ifeq ("@BLKDEACTIVATE@", "yes")
- 	DM_SCRIPTS += blkdeactivate.sh
- endif
-diff --git a/scripts/vdoimport.sh b/scripts/vdoimport.sh
-new file mode 100755
-index 0000000..ef96591
---- /dev/null
-+++ b/scripts/vdoimport.sh
-@@ -0,0 +1,376 @@
-+#!/bin/bash
-+#
-+# Copyright (C) 2021 Red Hat, Inc. All rights reserved.
-+#
-+# This file is part of LVM2.
-+#
-+# This copyrighted material is made available to anyone wishing to use,
-+# modify, copy, or redistribute it subject to the terms and conditions
-+# of the GNU General Public License v.2.
-+#
-+# You should have received a copy of the GNU General Public License
-+# along with this program; if not, write to the Free Software Foundation,
-+# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
-+#
-+# Author: Zdenek Kabelac <zkabelac at redhat.com>
-+#
-+# Script for converting VDO volumes to lvm2 VDO LVs
-+#
-+# Needed utilities:
-+#  lvm, dmsetup,
-+#  vdo, vdo2lvm,
-+#  grep, awk, sed, blockdev, readlink, mkdir
-+#
-+# Conversion is using  'vdo convert' support from VDO manager to move
-+# existing VDO header by 2M which makes space to place in PV header
-+# and VG metadata area, and then create VDOPOOL LV and VDO LV in such VG.
-+#
-+
-+set -euE -o pipefail
-+
-+TOOL=vdoimport
-+
-+_SAVEPATH=$PATH
-+PATH="/sbin:/usr/sbin:/bin:/usr/sbin:$PATH"
-+
-+# user may override lvm location by setting LVM_BINARY
-+LVM=${LVM_BINARY:-lvm}
-+VDO=${VDO_BINARY:-vdo}
-+VDOCONF=${VDOCONF:-}
-+BLOCKDEV="blockdev"
-+READLINK="readlink"
-+READLINK_E="-e"
-+MKDIR="mkdir"
-+
-+TEMPDIR="${TMPDIR:-/tmp}/${TOOL}_${RANDOM}$$"
-+DM_DEV_DIR="${DM_DEV_DIR:-/dev}"
-+
-+DRY=0
-+VERB=""
-+FORCE=""
-+YES=""
-+
-+# default name for converted VG and its VDO LV
-+NAME="vdovg/vdolvol"
-+
-+# help message
-+tool_usage() {
-+	echo "${TOOL}: Utility to convert VDO volume to VDO LV."
-+	echo
-+	echo "	${TOOL} [options] <vdo_device_path>"
-+	echo
-+	echo "	Options:"
-+	echo "	  -f | --force	      Bypass sanity checks"
-+	echo "	  -h | --help	      Show this help message"
-+	echo "	  -n | --name	      Specifies VG/LV name for converted VDO volume"
-+	echo "	  -v | --verbose      Be verbose"
-+	echo "	  -y | --yes	      Answer \"yes\" at any prompts"
-+	echo "	       --dry-run      Print commands without running them"
-+
-+	exit
-+}
-+
-+verbose() {
-+	test -z "$VERB" || echo "$TOOL:" "$@"
-+}
-+
-+# Support multi-line error messages
-+error() {
-+	for i in "$@" ;  do
-+		echo "$TOOL: $i" >&2
-+	done
-+	cleanup 1
-+}
-+
-+dry() {
-+	if [ "$DRY" -ne 0 ]; then
-+		verbose "Dry execution" "$@"
-+		return 0
-+	fi
-+	verbose "Executing" "$@"
-+	"$@"
-+}
-+
-+cleanup() {
-+	trap '' 2
-+
-+	rm -rf "$TEMPDIR"
-+	# error exit status for break
-+	exit "${1:-1}"
-+}
-+
-+get_enabled_value_() {
-+	case "$1" in
-+	enabled) echo "1" ;;
-+	*) echo "0" ;;
-+	esac
-+}
-+
-+get_kb_size_with_unit_() {
-+	case "$1" in
-+	*[kK]) echo $(( ${1%[kK]} )) ;;
-+	*[mM]) echo $(( ${1%[mM]} * 1024 )) ;;
-+	*[gG]) echo $(( ${1%[gG]} * 1024 * 1024 )) ;;
-+	*[tT]) echo $(( ${1%[tT]} * 1024 * 1024 * 1024 )) ;;
-+	*[pP]) echo $(( ${1%[pP]} * 1024 * 1024 * 1024 * 1024 )) ;;
-+	esac
-+}
-+
-+get_mb_size_with_unit_() {
-+	case "$1" in
-+	*[mM]) echo $(( ${1%[mM]} )) ;;
-+	*[gG]) echo $(( ${1%[gG]} * 1024 )) ;;
-+	*[tT]) echo $(( ${1%[tT]} * 1024 * 1024 )) ;;
-+	*[pP]) echo $(( ${1%[pP]} * 1024 * 1024 * 1024 )) ;;
-+	esac
-+}
-+
-+# Figure out largest possible extent size usable for VG
-+# $1   physical size
-+# $2   logical size
-+get_largest_extent_size_() {
-+	local max=4
-+	local i
-+	local d
-+
-+	for i in 8 16 32 64 128 256 512 1024 2048 4096 ; do
-+		d=$(( $1 / i ))
-+		test $(( d * i )) -eq "$1" || break
-+		d=$(( $2 / i ))
-+		test $(( d * i )) -eq "$2" || break
-+		max=$i
-+	done
-+	echo "$max"
-+}
-+
-+# detect LV on the given device
-+# dereference device name if it is symbolic link
-+detect_lv_() {
-+	local DEVICE=$1
-+	local MAJOR
-+	local MINOR
-+	local SYSVOLUME
-+	local MAJORMINOR
-+
-+	DEVICE=${1/#"${DM_DEV_DIR}/"/}
-+	DEVICE=$("$READLINK" $READLINK_E "$DM_DEV_DIR/$DEVICE")
-+	test -n "$DEVICE" || error "Cannot get readlink \"$1\"."
-+	RDEVICE=$DEVICE
-+	case "$RDEVICE" in
-+	  # hardcoded /dev  since udev does not create these entries elsewhere
-+	  /dev/dm-[0-9]*)
-+		read -r <"/sys/block/${RDEVICE#/dev/}/dm/name" SYSVOLUME 2>&1 && DEVICE="$DM_DEV_DIR/mapper/$SYSVOLUME"
-+		read -r <"/sys/block/${RDEVICE#/dev/}/dev" MAJORMINOR 2>&1 || error "Cannot get major:minor for \"$DEVICE\"."
-+		MAJOR=${MAJORMINOR%%:*}
-+		MINOR=${MAJORMINOR##*:}
-+		;;
-+	  *)
-+		STAT=$(stat --format "MAJOR=\$((0x%t)) MINOR=\$((0x%T))" "$RDEVICE")
-+		test -n "$STAT" || error "Cannot get major:minor for \"$DEVICE\"."
-+		eval "$STAT"
-+		;;
-+	esac
-+
-+	eval "$(dmsetup info -c -j "$MAJOR" -m "$MINOR" -o uuid,name --noheadings --nameprefixes --separator ' ')"
-+}
-+
-+# parse yaml config files into 'prefix_yaml_part_names=("value")' strings
-+parse_yaml_() {
-+	local yaml_file=$1
-+	local prefix=$2
-+	local s
-+	local w
-+	local fs
-+
-+	s='[[:space:]]*'
-+	w='[a-zA-Z0-9_.-]*'
-+	fs="$(echo @|tr @ '\034')"
-+
-+	(
-+	    sed -ne '/^--/s|--||g; s|\"|\\\"|g; s/[[:space:]]*$//g;' \
-+		-e 's/\$/\\\$/g' \
-+		-e "/#.*[\"\']/!s| #.*||g; /^#/s|#.*||g;" \
-+		-e "s|^\($s\)\($w\)$s:$s\"\(.*\)\"$s\$|\1$fs\2$fs\3|p" \
-+		-e "s|^\($s\)\($w\)${s}[:-]$s\(.*\)$s\$|\1$fs\2$fs\3|p" |
-+
-+	    awk -F"$fs" '{
-+		indent = length($1)/2;
-+		if (length($2) == 0) { conj[indent]="+";} else {conj[indent]="";}
-+		vname[indent] = $2;
-+		for (i in vname) {if (i > indent) {delete vname[i]}}
-+		    if (length($3) > 0) {
-+			vn=""; for (i=0; i<indent; i++) {vn=(vn)(vname[i])("_")}
-+			printf("%s%s%s%s=(\"%s\")\n", "'"$prefix"'",vn, $2, conj[indent-1], $3);
-+		    }
-+		}' |
-+
-+	    sed -e 's/_=/+=/g' |
-+
-+	    awk 'BEGIN {
-+		    FS="=";
-+		    OFS="="
-+		}
-+		/(-|\.).*=/ {
-+		    gsub("-|\\.", "_", $1)
-+		}
-+		{ print }'
-+	) < "$yaml_file"
-+}
-+
-+# convert existing VDO volume into lvm2 volume
-+convert2lvm_() {
-+	local DEVICE=$1
-+	local VGNAME=${NAME%/*}
-+	local LVNAME=${NAME#*/}
-+	local VDONAME
-+	local TRVDONAME
-+	local EXTENTSZ
-+	local IS_LV=1
-+
-+	DM_UUID=""
-+	detect_lv_ "$DEVICE"
-+	case "$DM_UUID" in
-+		LVM-*)	eval "$(dmsetup splitname --nameprefixes --noheadings --separator ' ' "$DM_NAME")"
-+			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ]  ; then
-+				VGNAME=$DM_VG_NAME
-+			elif test "$VGNAME" != "$DM_VG_NAME" ; then
-+				error "Volume group name \"$VGNAME\" does not match name \"$DM_VG_NAME\" for device \"$DEVICE\"."
-+			fi
-+			;;
-+		*) IS_LV=0
-+			# Check $VGNANE does not already exists
-+			"$LVM" vgs "$VGNAME" && error "Cannot use already existing volume group name \"$VGNAME\"."
-+			;;
-+	esac
-+
-+	verbose "Checked whether device $1 is already LV ($IS_LV)."
-+
-+	"$MKDIR" -p -m 0000 "$TEMPDIR" || error "Failed to create $TEMPDIR."
-+
-+	verbose "Getting YAML VDO configuration."
-+	"$VDO" printConfigFile $VDOCONF >"$TEMPDIR/vdoconf.yml"
-+
-+	VDONAME=$(awk -v DNAME="$DEVICE" '/.*VDOService$/ {VNAME=substr($1, 0, length($1) - 1)} /[[:space:]]*device:/ { if ($2 ~ DNAME) {print VNAME}}' "$TEMPDIR/vdoconf.yml")
-+	TRVDONAME=$(echo "$VDONAME" | tr '-' '_')
-+
-+	# When VDO volume is 'active', check it's not mounted/being used
-+	eval "$(dmsetup info -c -o open  "$VDONAME" --noheadings --nameprefixes || true)"
-+	test "${DM_OPEN:-0}" -eq 0 || error "Cannot converted VDO volume \"$VDONAME\" which is in use!"
-+
-+	#parse_yaml_ "$TEMPDIR/vdoconf.yml" _
-+	eval "$(parse_yaml_ "$TEMPDIR/vdoconf.yml" _ | grep "$TRVDONAME" | sed -e "s/_config_vdos_$TRVDONAME/vdo/g")"
-+
-+	vdo_logicalSize=$(get_kb_size_with_unit_ "$vdo_logicalSize")
-+	vdo_physicalSize=$(get_kb_size_with_unit_ "$vdo_physicalSize")
-+
-+	verbose "Going to convert physical sized VDO device $vdo_physicalSize KiB."
-+	verbose "With logical volume of size $vdo_logicalSize KiB."
-+
-+	PARAMS=$(cat <<EOF
-+allocation {
-+	vdo_use_compression = $(get_enabled_value_ "$vdo_compression")
-+	vdo_use_deduplication = $(get_enabled_value_ "$vdo_deduplication")
-+	vdo_use_metadata_hints=1
-+	vdo_minimum_io_size = $vdo_logicalBlockSize
-+	vdo_block_map_cache_size_mb = $(get_mb_size_with_unit_ "$vdo_blockMapCacheSize")
-+	vdo_block_map_period = $vdo_blockMapPeriod
-+	vdo_check_point_frequency = $vdo_indexCfreq
-+	vdo_use_sparse_index = $(get_enabled_value_ "$vdo_indexSparse")
-+	vdo_index_memory_size_mb = $(awk "BEGIN {print $vdo_indexMemory * 1024}")
-+	vdo_slab_size_mb = $(get_mb_size_with_unit_ "$vdo_blockMapCacheSize")
-+	vdo_ack_threads = $vdo_ackThreads
-+	vdo_bio_threads = $vdo_bioThreads
-+	vdo_bio_rotation = $vdo_bioRotationInterval
-+	vdo_cpu_threads = $vdo_cpuThreads
-+	vdo_hash_zone_threads = $vdo_hashZoneThreads
-+	vdo_logical_threads = $vdo_logicalThreads
-+	vdo_physical_threads = $vdo_physicalThreads
-+	vdo_write_policy = $vdo_writePolicy
-+	vdo_max_discard = $(( $(get_kb_size_with_unit_ "$vdo_maxDiscardSize") * 1024 ))
-+	vdo_pool_header_size = 0
-+}
-+EOF
-+)
-+	verbose "VDO conversion paramaters: $PARAMS"
-+
-+	verbose "Stopping VDO volume."
-+	dry "$VDO" stop $VDOCONF --name "$VDONAME"
-+
-+	if [ "$IS_LV" = "0" ]; then
-+		verbose "Moving VDO header by 2MiB."
-+		dry "$VDO" convert $VDOCONF --force --name "$VDONAME"
-+
-+		dry "$LVM" pvcreate $YES --dataalignment 2M "$DEVICE" || {
-+			error "Creation of PV on \"$DEVICE\" failed, while VDO header has been already moved!"
-+		}
-+
-+		# Obtain free space in this new PV
-+		# after 'vdo convert/vdo2lvm' call there is +2M free space at the front of the device
-+		case "$DRY" in
-+		0) pvfree=$("$LVM" pvs -o devsize --units b --nosuffix --noheadings "$DEVICE") ;;
-+		*) pvfree=$("$BLOCKDEV" --getsize64 "$DEVICE") ;;
-+		esac
-+
-+		pvfree=$(( pvfree / 1024 - 2048 ))	# to KiB
-+	else
-+		pvfree=$("$LVM" lvs -o size --units b --nosuffix --noheadings "$VGNAME/$LVNAME")
-+		pvfree=$(( pvfree / 1024 ))		# to KiB
-+	fi
-+
-+	# select largest possible extent size that can exactly express both sizes
-+	EXTENTSZ=$(get_largest_extent_size_ "$pvfree" "$vdo_logicalSize")
-+
-+	if [ "$IS_LV" = "0" ]; then
-+		verbose "Creating VG \"${NAME%/*}\" with extent size $EXTENTSZ KiB."
-+		dry "$LVM" vgcreate $YES $VERB -s "${EXTENTSZ}k" "$VGNAME" "$DEVICE" || {
-+			error "Creation of VG \"$VGNAME\" failed, while VDO header has been already moved!"
-+		}
-+
-+		verbose "Creating VDO pool data LV from all extents in volume group $VGNAME."
-+		dry "$LVM" lvcreate -Zn -Wn $YES $VERB -l100%VG -n "${LVNAME}_vpool" "$VGNAME"
-+	else
-+		# validate existing  VG extent_size can express virtual VDO size
-+		vg_extent_size=$("$LVM" vgs -o vg_extent_size --units b --nosuffix --noheadings "$VGNAME" || true)
-+		vg_extent_size=$(( vg_extent_size / 1024 ))
-+
-+		test "$vg_extent_size" -le "$EXTENTSZ" || {
-+			error "Please vgchange extent_size to at most $EXTENTSZ KiB or extend and align virtual size on $vg_extent_size KiB."
-+		}
-+		verbose "Renaming existing LV to be used as _vdata volume for VDO pool LV."
-+		dry "$LVM" lvrename $YES $VERB "$VGNAME/$LVNAME" "$VGNAME/${LVNAME}_vpool" || {
-+			error "Rename of LV \"$VGNAME/$LVNAME\" failed, while VDO header has been already moved!"
-+		}
-+	fi
-+
-+	verbose "Converting to VDO pool."
-+	dry "$LVM" lvconvert $YES $VERB $FORCE --config "$PARAMS" -Zn -V "${vdo_logicalSize}k" -n "$LVNAME" --type vdo-pool "$VGNAME/${LVNAME}_vpool"
-+
-+	rm -fr "$TEMPDIR"
-+}
-+
-+#############################
-+# start point of this script
-+# - parsing parameters
-+#############################
-+trap "cleanup 2" 2
-+
-+test "$#" -eq 0 && tool_usage
-+
-+while [ "$#" -ne 0 ]
-+do
-+	 case "$1" in
-+	  "") ;;
-+	  "-f"|"--force"  ) FORCE="-f" ;;
-+	  "-h"|"--help"   ) tool_usage ;;
-+	  "-n"|"--name"   ) shift; NAME=$1 ;;
-+	  "-v"|"--verbose") VERB="-v" ;;
-+	  "-y"|"--yes"    ) YES="-y" ;;
-+	  "--dry-run"     ) DRY="1" ;;
-+	  "-*") error "Wrong argument \"$1\". (see: $TOOL --help)" ;;
-+	  *) DEVICENAME=$1 ;;  # device name does not start with '-'
-+	esac
-+	shift
-+done
-+
-+# do conversion
-+convert2lvm_ "$DEVICENAME"
-diff --git a/test/Makefile.in b/test/Makefile.in
-index e4cd3aa..6be03aa 100644
---- a/test/Makefile.in
-+++ b/test/Makefile.in
-@@ -353,6 +353,7 @@ LIB = $(addprefix lib/, $(LIB_SECURETEST) $(LIB_DMSECURETEST) $(LIB_SHARED) $(LI
- 	$(Q) $(LN_S) -f $(abs_top_srcdir)/conf/lvmdbusd.profile lib/
- 	$(Q) $(LN_S) -f $(abs_top_srcdir)/conf/thin-performance.profile lib/
- 	$(Q) $(LN_S) -f $(abs_top_srcdir)/scripts/fsadm.sh lib/fsadm
-+	$(Q) $(LN_S) -f $(abs_top_srcdir)/scripts/vdoimport.sh lib/vdoimport
- 	@test "$(srcdir)" = . || \
- 		for i in $(LIB_LVMLOCKD_CONF) $(LIB_MKE2FS_CONF); do \
- 			test -n "$(Q)" || echo "$(LN_S) -f $(abs_top_srcdir)/test/lib/$$i lib/"; \
-diff --git a/test/shell/vdo-convert.sh b/test/shell/vdo-convert.sh
-new file mode 100644
-index 0000000..538147b
---- /dev/null
-+++ b/test/shell/vdo-convert.sh
-@@ -0,0 +1,110 @@
-+#!/usr/bin/env bash
-+
-+# Copyright (C) 2021 Red Hat, Inc. All rights reserved.
-+#
-+# This copyrighted material is made available to anyone wishing to use,
-+# modify, copy, or redistribute it subject to the terms and conditions
-+# of the GNU General Public License v.2.
-+#
-+# You should have received a copy of the GNU General Public License
-+# along with this program; if not, write to the Free Software Foundation,
-+# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
-+
-+# Test conversion of VDO volumes made by vdo manager into VDO LV.
-+
-+
-+SKIP_WITH_LVMPOLLD=1
-+
-+. lib/inittest
-+
-+# Use local for this test vdo configuratoin
-+VDOCONF="-f vdotestconf.yml"
-+#VDOCONF=""
-+export VDOCONF
-+VDONAME="${PREFIX}-TESTVDO"
-+
-+# VDO automatically starts dmeventd
-+aux prepare_dmeventd
-+
-+#
-+# Main
-+#
-+which vdo || skip
-+which mkfs.ext4 || skip
-+export MKE2FS_CONFIG="$TESTDIR/lib/mke2fs.conf"
-+
-+aux have_vdo 6 2 0 || skip
-+
-+aux prepare_devs 2 10000
-+
-+aux extend_filter_LVMTEST
-+
-+
-+#
-+#  Check conversion of VDO volume made on some LV
-+#
-+#  In this case we do not need to move any VDO headers.
-+#
-+vgcreate $vg "$dev1"
-+
-+lvcreate -L5G -n $lv1 $vg
-+
-+vdo create $VDOCONF --name "$VDONAME" --device="$DM_DEV_DIR/$vg/$lv1" --vdoLogicalSize=10G
-+
-+mkfs -E nodiscard "$DM_DEV_DIR/mapper/$VDONAME"
-+
-+# Different VG name fails
-+not vdoimport -y -v --name $vg1/$lv1 "$DM_DEV_DIR/$vg/$lv1"
-+
-+# Try just dry run and observe logging
-+vdoimport --dry-run -y -v --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
-+
-+vdoimport -y --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
-+
-+# ATM needed - since we do not call 'vdo convert' in this case
-+vdo remove $VDOCONF --force --name "$VDONAME" || true
-+
-+vgremove -f $vg
-+
-+aux wipefs_a "$dev1"
-+
-+# prepare 'unused' $vg2
-+vgcreate $vg2 "$dev2"
-+
-+#
-+# Check conversion of VDO volume on  non-LV device
-+#
-+vdo create $VDOCONF --name "$VDONAME" --device="$dev1" --vdoLogicalSize=31G
-+
-+mkfs -E nodiscard "$DM_DEV_DIR/mapper/$VDONAME"
-+
-+# Fail with an already existing volume group $vg2
-+not vdoimport --dry-run -y -v --name $vg2/$lv1 "$dev1" |& tee err
-+grep "already existing volume group" err
-+
-+# User can also convert already stopped VDO volume
-+vdo stop $VDOCONF --name "$VDONAME"
-+
-+vdoimport -y -v --name $vg/$lv1 "$dev1"
-+
-+fsck -n "$DM_DEV_DIR/$vg/$lv1"
-+
-+vgremove -f $vg
-+
-+
-+#
-+# Try once again with different vgname/lvname and sizes
-+#
-+aux teardown_devs
-+aux prepare_devs 1 23456
-+
-+vdo create $VDOCONF --name "$VDONAME" --device="$dev1" --vdoLogicalSize=23G
-+
-+mkfs -E nodiscard "$DM_DEV_DIR/mapper/$VDONAME"
-+
-+vdoimport -y -v --name $vg1/$lv2 "$dev1"
-+
-+fsck -n "$DM_DEV_DIR/$vg1/$lv2"
-+
-+vgremove -f $vg1
-+
diff --git a/SOURCES/lvm2-2_03_13-vdo-fix-preload-of-kvdo.patch b/SOURCES/lvm2-2_03_13-vdo-fix-preload-of-kvdo.patch
deleted file mode 100644
index 042ef0e..0000000
--- a/SOURCES/lvm2-2_03_13-vdo-fix-preload-of-kvdo.patch
+++ /dev/null
@@ -1,37 +0,0 @@
- WHATS_NEW               |  4 ++++
- lib/activate/activate.c | 10 +++-------
- 2 files changed, 7 insertions(+), 7 deletions(-)
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index 6f339a5..04c6dcd 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,3 +1,7 @@
-+Version 2.03.13 - 
-+===============================
-+  Fix load of kvdo target when it is not present in memory (2.03.12).
-+
- Version 2.03.12 - 07th May 2021
- ===============================
-   Allow attaching cache to thin data volume.
-diff --git a/lib/activate/activate.c b/lib/activate/activate.c
-index 71db981..6bda738 100644
---- a/lib/activate/activate.c
-+++ b/lib/activate/activate.c
-@@ -574,13 +574,9 @@ int module_present(struct cmd_context *cmd, const char *target_name)
- 	}
- 
- #ifdef MODPROBE_CMD
--	if (strcmp(target_name, MODULE_NAME_VDO) == 0) {
--		argv[1] = target_name;		/* ATM kvdo is without dm- prefix */
--		if ((ret = exec_cmd(cmd, argv, NULL, 0)))
--			return ret;
--	}
--
--	if (dm_snprintf(module, sizeof(module), "dm-%s", target_name) < 0) {
-+	if (strcmp(target_name, TARGET_NAME_VDO) == 0)
-+		argv[1] = MODULE_NAME_VDO; /* ATM kvdo is without dm- prefix */
-+	else if (dm_snprintf(module, sizeof(module), "dm-%s", target_name) < 0) {
- 		log_error("module_present module name too long: %s",
- 			  target_name);
- 		return 0;
diff --git a/SOURCES/lvm2-2_03_13-vdo-rename-variable-vdo_pool_zero.patch b/SOURCES/lvm2-2_03_13-vdo-rename-variable-vdo_pool_zero.patch
deleted file mode 100644
index 74b141c..0000000
--- a/SOURCES/lvm2-2_03_13-vdo-rename-variable-vdo_pool_zero.patch
+++ /dev/null
@@ -1,50 +0,0 @@
- tools/lvconvert.c | 12 ++++++------
- 1 file changed, 6 insertions(+), 6 deletions(-)
-
-diff --git a/tools/lvconvert.c b/tools/lvconvert.c
-index 6066d1f..8488596 100644
---- a/tools/lvconvert.c
-+++ b/tools/lvconvert.c
-@@ -5438,7 +5438,7 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- 					struct processing_handle *handle)
- {
- 	const char *vg_name = NULL;
--	unsigned int zero_vdopool;
-+	unsigned int vdo_pool_zero;
- 	struct volume_group *vg = lv->vg;
- 	struct logical_volume *vdo_lv;
- 	struct dm_vdo_target_params vdo_params; /* vdo */
-@@ -5497,12 +5497,12 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- 		goto out;
- 	}
- 
--	zero_vdopool = arg_int_value(cmd, zero_ARG, 1);
-+	vdo_pool_zero = arg_int_value(cmd, zero_ARG, 1);
- 
- 	log_warn("WARNING: Converting logical volume %s to VDO pool volume %s formating.",
--		 display_lvname(lv), zero_vdopool ? "with" : "WITHOUT");
-+		 display_lvname(lv), vdo_pool_zero ? "with" : "WITHOUT");
- 
--	if (zero_vdopool)
-+	if (vdo_pool_zero)
- 		log_warn("THIS WILL DESTROY CONTENT OF LOGICAL VOLUME (filesystem etc.)");
- 	else
- 		log_warn("WARNING: Using invalid VDO pool data MAY DESTROY YOUR DATA!");
-@@ -5514,7 +5514,7 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- 		goto out;
- 	}
- 
--	if (zero_vdopool) {
-+	if (vdo_pool_zero) {
- 		if (!wipe_lv(lv, (struct wipe_params) { .do_zero = 1, .do_wipe_signatures = 1,
- 			     .yes = arg_count(cmd, yes_ARG),
- 			     .force = arg_count(cmd, force_ARG)})) {
-@@ -5526,7 +5526,7 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- 	if (!archive(vg))
- 		goto_out;
- 
--	if (!convert_vdo_pool_lv(lv, &vdo_params, &lvc.virtual_extents, zero_vdopool))
-+	if (!convert_vdo_pool_lv(lv, &vdo_params, &lvc.virtual_extents, vdo_pool_zero))
- 		goto_out;
- 
- 	dm_list_init(&lvc.tags);
diff --git a/SOURCES/lvm2-2_03_13-vdo-support-vdo_pool_header_size.patch b/SOURCES/lvm2-2_03_13-vdo-support-vdo_pool_header_size.patch
deleted file mode 100644
index 63235b0..0000000
--- a/SOURCES/lvm2-2_03_13-vdo-support-vdo_pool_header_size.patch
+++ /dev/null
@@ -1,197 +0,0 @@
- conf/example.conf.in             |  5 +++++
- lib/config/config_settings.h     |  3 +++
- lib/config/defaults.h            |  3 +--
- lib/metadata/lv_manip.c          |  3 ++-
- lib/metadata/metadata-exported.h |  5 ++++-
- lib/metadata/vdo_manip.c         | 13 ++++++++-----
- tools/lvconvert.c                |  6 ++++--
- tools/lvcreate.c                 |  2 +-
- 8 files changed, 28 insertions(+), 12 deletions(-)
-
-diff --git a/conf/example.conf.in b/conf/example.conf.in
-index aaf73a4..78547a6 100644
---- a/conf/example.conf.in
-+++ b/conf/example.conf.in
-@@ -734,6 +734,11 @@ allocation {
- 	# The default and minimum is 1. The maximum is UINT_MAX / 4096.
- 	# This configuration option has an automatic default value.
- 	# vdo_max_discard = 1
-+
-+	# Configuration option allocation/vdo_pool_header_size.
-+	# Specified the emptry header size in KiB at the front and end of vdo pool device.
-+	# This configuration option has an automatic default value.
-+	# vdo_pool_header_size = 512
- }
- 
- # Configuration section log.
-diff --git a/lib/config/config_settings.h b/lib/config/config_settings.h
-index f5dac4d..5217da8 100644
---- a/lib/config/config_settings.h
-+++ b/lib/config/config_settings.h
-@@ -816,6 +816,9 @@ cfg(allocation_vdo_max_discard_CFG, "vdo_max_discard", allocation_CFG_SECTION, C
- 	"increased latency for the individual discard requests.\n"
- 	"The default and minimum is 1. The maximum is UINT_MAX / 4096.\n")
- 
-+cfg(allocation_vdo_pool_header_size_CFG, "vdo_pool_header_size", allocation_CFG_SECTION, CFG_PROFILABLE | CFG_PROFILABLE_METADATA | CFG_DEFAULT_COMMENTED, CFG_TYPE_INT, DEFAULT_VDO_POOL_HEADER_SIZE_KB, vsn(2, 3, 12), NULL, 0, NULL,
-+	"Specified the emptry header size in KiB at the front and end of vdo pool device.\n")
-+
- cfg(log_report_command_log_CFG, "report_command_log", log_CFG_SECTION, CFG_PROFILABLE | CFG_DEFAULT_COMMENTED | CFG_DISALLOW_INTERACTIVE, CFG_TYPE_BOOL, DEFAULT_COMMAND_LOG_REPORT, vsn(2, 2, 158), NULL, 0, NULL,
- 	"Enable or disable LVM log reporting.\n"
- 	"If enabled, LVM will collect a log of operations, messages,\n"
-diff --git a/lib/config/defaults.h b/lib/config/defaults.h
-index 2870dee..d5e5b3b 100644
---- a/lib/config/defaults.h
-+++ b/lib/config/defaults.h
-@@ -181,8 +181,7 @@
-  * VDO pool will reverve some sectors in the front and the back of pool device to avoid
-  * seeing same device twice in the system.
-  */
--#define DEFAULT_VDO_POOL_HEADER_SIZE  (1024)   // 512KiB
--
-+#define DEFAULT_VDO_POOL_HEADER_SIZE_KB  (512)
- 
- 
- #define DEFAULT_FSADM_PATH FSADM_PATH
-diff --git a/lib/metadata/lv_manip.c b/lib/metadata/lv_manip.c
-index 37dd361..43af474 100644
---- a/lib/metadata/lv_manip.c
-+++ b/lib/metadata/lv_manip.c
-@@ -8766,7 +8766,8 @@ static struct logical_volume *_lv_create_an_lv(struct volume_group *vg,
- 	}
- 
- 	if (seg_is_vdo_pool(lp)) {
--		if (!convert_vdo_pool_lv(lv, &lp->vdo_params, &lp->virtual_extents, 1)) {
-+		if (!convert_vdo_pool_lv(lv, &lp->vdo_params, &lp->virtual_extents,
-+					 1, lp->vdo_pool_header_size)) {
- 			stack;
- 			goto deactivate_and_revert_new_lv;
- 		}
-diff --git a/lib/metadata/metadata-exported.h b/lib/metadata/metadata-exported.h
-index 54bc0d0..adbbe76 100644
---- a/lib/metadata/metadata-exported.h
-+++ b/lib/metadata/metadata-exported.h
-@@ -1033,6 +1033,7 @@ struct lvcreate_params {
- 	int approx_alloc;     /* all */
- 	alloc_policy_t alloc; /* all */
- 	struct dm_vdo_target_params vdo_params; /* vdo */
-+	uint64_t vdo_pool_header_size; /* VDO */
- 
- 	int raidintegrity;
- 	const char *raidintegritymode;
-@@ -1367,10 +1368,12 @@ int parse_vdo_pool_status(struct dm_pool *mem, const struct logical_volume *vdo_
- struct logical_volume *convert_vdo_pool_lv(struct logical_volume *data_lv,
- 					   const struct dm_vdo_target_params *vtp,
- 					   uint32_t *virtual_extents,
--					   int format);
-+					   int format,
-+					   uint64_t vdo_pool_header_size);
- int set_vdo_write_policy(enum dm_vdo_write_policy *vwp, const char *policy);
- int fill_vdo_target_params(struct cmd_context *cmd,
- 			   struct dm_vdo_target_params *vtp,
-+			   uint64_t *vdo_pool_header_size,
- 			   struct profile *profile);
- /* --  metadata/vdo_manip.c */
- 
-diff --git a/lib/metadata/vdo_manip.c b/lib/metadata/vdo_manip.c
-index afc513a..3f2de1a 100644
---- a/lib/metadata/vdo_manip.c
-+++ b/lib/metadata/vdo_manip.c
-@@ -356,9 +356,9 @@ static int _format_vdo_pool_data_lv(struct logical_volume *data_lv,
- struct logical_volume *convert_vdo_pool_lv(struct logical_volume *data_lv,
- 					   const struct dm_vdo_target_params *vtp,
- 					   uint32_t *virtual_extents,
--					   int format)
-+					   int format,
-+					   uint64_t vdo_pool_header_size)
- {
--	const uint64_t header_size = DEFAULT_VDO_POOL_HEADER_SIZE;
- 	const uint32_t extent_size = data_lv->vg->extent_size;
- 	struct cmd_context *cmd = data_lv->vg->cmd;
- 	struct logical_volume *vdo_pool_lv = data_lv;
-@@ -379,7 +379,7 @@ struct logical_volume *convert_vdo_pool_lv(struct logical_volume *data_lv,
- 
- 	if (*virtual_extents)
- 		vdo_logical_size =
--			_get_virtual_size(*virtual_extents, extent_size, header_size);
-+			_get_virtual_size(*virtual_extents, extent_size, vdo_pool_header_size);
- 
- 	if (!dm_vdo_validate_target_params(vtp, vdo_logical_size))
- 		return_0;
-@@ -403,7 +403,7 @@ struct logical_volume *convert_vdo_pool_lv(struct logical_volume *data_lv,
- 		return NULL;
- 	}
- 
--	vdo_logical_size -= 2 * header_size;
-+	vdo_logical_size -= 2 * vdo_pool_header_size;
- 
- 	if (vdo_logical_size < extent_size) {
- 		if (!*virtual_extents)
-@@ -426,7 +426,7 @@ struct logical_volume *convert_vdo_pool_lv(struct logical_volume *data_lv,
- 	vdo_pool_seg = first_seg(vdo_pool_lv);
- 	vdo_pool_seg->segtype = vdo_pool_segtype;
- 	vdo_pool_seg->vdo_params = *vtp;
--	vdo_pool_seg->vdo_pool_header_size = DEFAULT_VDO_POOL_HEADER_SIZE;
-+	vdo_pool_seg->vdo_pool_header_size = vdo_pool_header_size;
- 	vdo_pool_seg->vdo_pool_virtual_extents = *virtual_extents;
- 
- 	vdo_pool_lv->status |= LV_VDO_POOL;
-@@ -453,6 +453,7 @@ int set_vdo_write_policy(enum dm_vdo_write_policy *vwp, const char *policy)
- 
- int fill_vdo_target_params(struct cmd_context *cmd,
- 			   struct dm_vdo_target_params *vtp,
-+			   uint64_t *vdo_pool_header_size,
- 			   struct profile *profile)
- {
- 	const char *policy;
-@@ -501,5 +502,7 @@ int fill_vdo_target_params(struct cmd_context *cmd,
- 	if (!set_vdo_write_policy(&vtp->write_policy, policy))
- 		return_0;
- 
-+	*vdo_pool_header_size = 2 * find_config_tree_int64(cmd, allocation_vdo_pool_header_size_CFG, profile);
-+
- 	return 1;
- }
-diff --git a/tools/lvconvert.c b/tools/lvconvert.c
-index 8488596..f87ee78 100644
---- a/tools/lvconvert.c
-+++ b/tools/lvconvert.c
-@@ -5439,6 +5439,7 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- {
- 	const char *vg_name = NULL;
- 	unsigned int vdo_pool_zero;
-+	uint64_t vdo_pool_header_size;
- 	struct volume_group *vg = lv->vg;
- 	struct logical_volume *vdo_lv;
- 	struct dm_vdo_target_params vdo_params; /* vdo */
-@@ -5481,7 +5482,7 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- 		goto out;
- 	}
- 
--	if (!fill_vdo_target_params(cmd, &vdo_params, vg->profile))
-+	if (!fill_vdo_target_params(cmd, &vdo_params, &vdo_pool_header_size, vg->profile))
- 		goto_out;
- 
- 	if (arg_is_set(cmd, compression_ARG))
-@@ -5526,7 +5527,8 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- 	if (!archive(vg))
- 		goto_out;
- 
--	if (!convert_vdo_pool_lv(lv, &vdo_params, &lvc.virtual_extents, vdo_pool_zero))
-+	if (!convert_vdo_pool_lv(lv, &vdo_params, &lvc.virtual_extents,
-+				 vdo_pool_zero, vdo_pool_header_size))
- 		goto_out;
- 
- 	dm_list_init(&lvc.tags);
-diff --git a/tools/lvcreate.c b/tools/lvcreate.c
-index a28f093..0def236 100644
---- a/tools/lvcreate.c
-+++ b/tools/lvcreate.c
-@@ -1097,7 +1097,7 @@ static int _lvcreate_params(struct cmd_context *cmd,
- 
- 		// FIXME: prefiling here - this is wrong place
- 		// but will work for this moment
--		if (!fill_vdo_target_params(cmd, &lp->vdo_params, NULL))
-+		if (!fill_vdo_target_params(cmd, &lp->vdo_params, &lp->vdo_pool_header_size, NULL))
- 			return_0;
- 
- 		if (arg_is_set(cmd, compression_ARG))
diff --git a/SOURCES/lvm2-2_03_13-vgmerge-remove-one-of-merge-pmspare-LVs.patch b/SOURCES/lvm2-2_03_13-vgmerge-remove-one-of-merge-pmspare-LVs.patch
deleted file mode 100644
index 62d6686..0000000
--- a/SOURCES/lvm2-2_03_13-vgmerge-remove-one-of-merge-pmspare-LVs.patch
+++ /dev/null
@@ -1,28 +0,0 @@
- tools/vgmerge.c | 14 ++++++++++++++
- 1 file changed, 14 insertions(+)
-
-diff --git a/tools/vgmerge.c b/tools/vgmerge.c
-index 895018a..884ad4b 100644
---- a/tools/vgmerge.c
-+++ b/tools/vgmerge.c
-@@ -92,6 +92,20 @@ static int _vgmerge_single(struct cmd_context *cmd, const char *vg_name_to,
- 		}
- 	}
- 
-+	if (vg_from->pool_metadata_spare_lv &&
-+	    vg_to->pool_metadata_spare_lv) {
-+		if (vg_from->pool_metadata_spare_lv->le_count >
-+		    vg_to->pool_metadata_spare_lv->le_count)
-+			/* Preserve bigger pmspare from  VG_FROM */
-+			lv = vg_to->pool_metadata_spare_lv;
-+		else
-+			lv = vg_from->pool_metadata_spare_lv;
-+
-+		log_debug_metadata("Removing pool metadata spare %s.", display_lvname(lv));
-+		if (!lv_remove_single(cmd, lv, DONT_PROMPT, 0))
-+				return_ECMD_FAILED;
-+	}
-+
- 	if (!vgs_are_compatible(cmd, vg_from, vg_to))
- 		goto_bad;
- 
diff --git a/SOURCES/lvm2-2_03_13-vgmerge-support-option-poolmetadataspare.patch b/SOURCES/lvm2-2_03_13-vgmerge-support-option-poolmetadataspare.patch
deleted file mode 100644
index 002c060..0000000
--- a/SOURCES/lvm2-2_03_13-vgmerge-support-option-poolmetadataspare.patch
+++ /dev/null
@@ -1,82 +0,0 @@
- WHATS_NEW              | 2 +-
- man/vgmerge.8_pregen   | 9 +++++++++
- tools/command-lines.in | 2 +-
- tools/vgmerge.c        | 6 ++++++
- 4 files changed, 17 insertions(+), 2 deletions(-)
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index 0b8e3f2..5556789 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,6 +1,6 @@
- Version 2.03.13 - 
- ===============================
--  Support --poolmetadataspare with vgsplit.
-+  Support --poolmetadataspare with vgsplit and vgmerge.
-   Fix detection of active components of external origin volume.
-   Add vdoimport tool to support conversion of VDO volumes.
-   Support configurable allocation/vdo_pool_header_size.
-diff --git a/man/vgmerge.8_pregen b/man/vgmerge.8_pregen
-index 1264bb5..e229218 100644
---- a/man/vgmerge.8_pregen
-+++ b/man/vgmerge.8_pregen
-@@ -27,6 +27,8 @@ of both VGs fit into the destination VG's limits.
- .br
- [ \fB-l\fP|\fB--list\fP ]
- .br
-+[    \fB--poolmetadataspare\fP \fBy\fP|\fBn\fP ]
-+.br
- [ COMMON_OPTIONS ]
- .ad b
- .RE
-@@ -147,6 +149,13 @@ Display long help text.
- Disable locking.
- .
- .HP
-+\fB--poolmetadataspare\fP \fBy\fP|\fBn\fP
-+.br
-+Enable or disable the automatic creation and management of a
-+spare pool metadata LV in the VG. A spare metadata LV is reserved
-+space that can be used when repairing a pool.
-+.
-+.HP
- \fB--profile\fP \fIString\fP
- .br
- An alias for --commandprofile or --metadataprofile, depending
-diff --git a/tools/command-lines.in b/tools/command-lines.in
-index a4785b3..0bc5a49 100644
---- a/tools/command-lines.in
-+++ b/tools/command-lines.in
-@@ -1847,7 +1847,7 @@ DESC: Add devices from all accessible VGs to the devices file.
- ---
- 
- vgmerge VG VG
--OO: --autobackup Bool, --list
-+OO: --autobackup Bool, --list, --poolmetadataspare Bool
- ID: vgmerge_general
- 
- ---
-diff --git a/tools/vgmerge.c b/tools/vgmerge.c
-index 884ad4b..08615cd 100644
---- a/tools/vgmerge.c
-+++ b/tools/vgmerge.c
-@@ -64,6 +64,8 @@ static int _vgmerge_single(struct cmd_context *cmd, const char *vg_name_to,
- 	struct lv_list *lvl1, *lvl2;
- 	int r = ECMD_FAILED;
- 	int lock_vg_from_first = 0;
-+	struct logical_volume *lv;
-+	int poolmetadataspare = arg_int_value(cmd, poolmetadataspare_ARG, DEFAULT_POOL_METADATA_SPARE);
- 
- 	if (!strcmp(vg_name_to, vg_name_from)) {
- 		log_error("Duplicate volume group name \"%s\"", vg_name_from);
-@@ -185,6 +187,10 @@ static int _vgmerge_single(struct cmd_context *cmd, const char *vg_name_to,
- 	/* Flag up that some PVs have moved from another VG */
- 	vg_to->old_name = vg_from->name;
- 
-+        /* Check whether size of pmspare is big enough now for merged VG */
-+	if (!handle_pool_metadata_spare(vg_to, 0, &vg_to->pvs, poolmetadataspare))
-+		goto_bad;
-+
- 	/* store it on disks */
- 	log_verbose("Writing out updated volume group");
- 	if (!vg_write(vg_to) || !vg_commit(vg_to))
diff --git a/SOURCES/lvm2-2_03_13-vgremove-remove-forgotten-pmspare.patch b/SOURCES/lvm2-2_03_13-vgremove-remove-forgotten-pmspare.patch
deleted file mode 100644
index 53fa667..0000000
--- a/SOURCES/lvm2-2_03_13-vgremove-remove-forgotten-pmspare.patch
+++ /dev/null
@@ -1,18 +0,0 @@
- tools/vgremove.c | 4 ++++
- 1 file changed, 4 insertions(+)
-
-diff --git a/tools/vgremove.c b/tools/vgremove.c
-index 8f73297..b6685ae 100644
---- a/tools/vgremove.c
-+++ b/tools/vgremove.c
-@@ -65,6 +65,10 @@ static int _vgremove_single(struct cmd_context *cmd, const char *vg_name,
- 		}
- 	}
- 
-+	if (vg->pool_metadata_spare_lv &&
-+	    !lvremove_single(cmd, vg->pool_metadata_spare_lv, &void_handle))
-+		return_ECMD_FAILED;
-+
- 	if (!lockd_free_vg_before(cmd, vg, 0))
- 		return_ECMD_FAILED;
- 
diff --git a/SOURCES/lvm2-2_03_13-vgsplit-add-support-for-option-poolmetadataspare.patch b/SOURCES/lvm2-2_03_13-vgsplit-add-support-for-option-poolmetadataspare.patch
deleted file mode 100644
index 1a9d26b..0000000
--- a/SOURCES/lvm2-2_03_13-vgsplit-add-support-for-option-poolmetadataspare.patch
+++ /dev/null
@@ -1,106 +0,0 @@
- WHATS_NEW                 |  1 +
- lib/metadata/pool_manip.c | 11 +++++++++++
- man/vgsplit.8_pregen      |  9 +++++++++
- tools/command-lines.in    |  2 +-
- tools/vgsplit.c           |  8 ++++++++
- 5 files changed, 30 insertions(+), 1 deletion(-)
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index 097160e..0b8e3f2 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,5 +1,6 @@
- Version 2.03.13 - 
- ===============================
-+  Support --poolmetadataspare with vgsplit.
-   Fix detection of active components of external origin volume.
-   Add vdoimport tool to support conversion of VDO volumes.
-   Support configurable allocation/vdo_pool_header_size.
-diff --git a/lib/metadata/pool_manip.c b/lib/metadata/pool_manip.c
-index 9ceec3a..e451e92 100644
---- a/lib/metadata/pool_manip.c
-+++ b/lib/metadata/pool_manip.c
-@@ -722,6 +722,17 @@ int handle_pool_metadata_spare(struct volume_group *vg, uint32_t extents,
- 		return 1;
- 	}
- 
-+	if (!extents) {
-+		/* pmspare is not needed */
-+		if (lv) {
-+			log_debug_metadata("Dropping unused pool metadata spare LV %s.",
-+					   display_lvname(lv));
-+			if (!lv_remove_single(vg->cmd, lv, DONT_PROMPT, 0))
-+				return_0;
-+		}
-+		return 1;
-+	}
-+
- 	if (extents > MAX_SIZE)
- 		extents = MAX_SIZE;
- 
-diff --git a/man/vgsplit.8_pregen b/man/vgsplit.8_pregen
-index 331c6e4..8a0ae59 100644
---- a/man/vgsplit.8_pregen
-+++ b/man/vgsplit.8_pregen
-@@ -70,6 +70,8 @@ Common options for command:
- .hy
- ]
- .br
-+[    \fB--poolmetadataspare\fP \fBy\fP|\fBn\fP ]
-+.br
- [    \fB--\fP[\fBvg\fP]\fBmetadatacopies\fP \fBall\fP|\fBunmanaged\fP|\fINumber\fP ]
- .ad b
- .RE
-@@ -235,6 +237,13 @@ Move only PVs used by the named LV.
- Disable locking.
- .
- .HP
-+\fB--poolmetadataspare\fP \fBy\fP|\fBn\fP
-+.br
-+Enable or disable the automatic creation and management of a
-+spare pool metadata LV in the VG. A spare metadata LV is reserved
-+space that can be used when repairing a pool.
-+.
-+.HP
- \fB--profile\fP \fIString\fP
- .br
- An alias for --commandprofile or --metadataprofile, depending
-diff --git a/tools/command-lines.in b/tools/command-lines.in
-index 8607305..a4785b3 100644
---- a/tools/command-lines.in
-+++ b/tools/command-lines.in
-@@ -1912,7 +1912,7 @@ ID: vgscan_general
- 
- ---
- 
--OO_VGSPLIT: --autobackup Bool
-+OO_VGSPLIT: --autobackup Bool, --poolmetadataspare Bool
- 
- # used only when the destination VG is new
- OO_VGSPLIT_NEW: --alloc Alloc,
-diff --git a/tools/vgsplit.c b/tools/vgsplit.c
-index 296248e..a085ac2 100644
---- a/tools/vgsplit.c
-+++ b/tools/vgsplit.c
-@@ -525,6 +525,7 @@ int vgsplit(struct cmd_context *cmd, int argc, char **argv)
- 	int existing_vg = 0;
- 	int r = ECMD_FAILED;
- 	const char *lv_name;
-+	int poolmetadataspare = arg_int_value(cmd, poolmetadataspare_ARG, DEFAULT_POOL_METADATA_SPARE);
- 
- 	if ((arg_is_set(cmd, name_ARG) + argc) < 3) {
- 		log_error("Existing VG, new VG and either physical volumes "
-@@ -699,6 +700,13 @@ int vgsplit(struct cmd_context *cmd, int argc, char **argv)
- 	 */
- 	vg_to->status |= EXPORTED_VG;
- 
-+
-+	if (!handle_pool_metadata_spare(vg_to, 0, &vg_to->pvs, poolmetadataspare))
-+		goto_bad;
-+
-+	if (!handle_pool_metadata_spare(vg_from, 0, &vg_from->pvs, poolmetadataspare))
-+		goto_bad;
-+
- 	if (!archive(vg_to))
- 		goto_bad;
- 
diff --git a/SOURCES/lvm2-2_03_13-writecache-don-t-pvmove-device-used-by-writecache.patch b/SOURCES/lvm2-2_03_13-writecache-don-t-pvmove-device-used-by-writecache.patch
deleted file mode 100644
index 1457f7f..0000000
--- a/SOURCES/lvm2-2_03_13-writecache-don-t-pvmove-device-used-by-writecache.patch
+++ /dev/null
@@ -1,23 +0,0 @@
- tools/pvmove.c | 9 +++++++++
- 1 file changed, 9 insertions(+)
-
-diff --git a/tools/pvmove.c b/tools/pvmove.c
-index da635a6..bb372f7 100644
---- a/tools/pvmove.c
-+++ b/tools/pvmove.c
-@@ -387,6 +387,15 @@ static struct logical_volume *_set_up_pvmove_lv(struct cmd_context *cmd,
- 			return NULL;
- 		}
- 
-+		if (lv_is_writecache(lv)) {
-+			struct logical_volume *lv_cachevol = first_seg(lv)->writecache;
-+			if (lv_is_on_pvs(lv_cachevol, source_pvl)) {
-+				log_error("Unable to move device used for writecache cachevol %s.", display_lvname(lv_cachevol));
-+				return NULL;
-+			}
-+
-+		}
-+
- 		if (lv_is_raid(lv) && lv_raid_has_integrity(lv)) {
- 			log_error("Unable to pvmove device used for raid with integrity.");
- 			return NULL;
diff --git a/SOURCES/lvm2-2_03_13-writecache-fix-lv_on_pmem.patch b/SOURCES/lvm2-2_03_13-writecache-fix-lv_on_pmem.patch
deleted file mode 100644
index b926cac..0000000
--- a/SOURCES/lvm2-2_03_13-writecache-fix-lv_on_pmem.patch
+++ /dev/null
@@ -1,17 +0,0 @@
- lib/metadata/metadata.c | 3 +++
- 1 file changed, 3 insertions(+)
-
-diff --git a/lib/metadata/metadata.c b/lib/metadata/metadata.c
-index 002d80c..1f65045 100644
---- a/lib/metadata/metadata.c
-+++ b/lib/metadata/metadata.c
-@@ -4402,6 +4402,9 @@ int lv_on_pmem(struct logical_volume *lv)
- 
- 	dm_list_iterate_items(seg, &lv->segments) {
- 		for (s = 0; s < seg->area_count; s++) {
-+			if (seg_type(seg, s) != AREA_PV)
-+				continue;
-+
- 			pv = seg_pv(seg, s);
- 
- 			if (dev_is_pmem(lv->vg->cmd->dev_types, pv->dev)) {
diff --git a/SOURCES/lvm2-2_03_14-lvchange-fix-lvchange-refresh-failed-for-dm-suspend-.patch b/SOURCES/lvm2-2_03_14-lvchange-fix-lvchange-refresh-failed-for-dm-suspend-.patch
deleted file mode 100644
index 945b369..0000000
--- a/SOURCES/lvm2-2_03_14-lvchange-fix-lvchange-refresh-failed-for-dm-suspend-.patch
+++ /dev/null
@@ -1,35 +0,0 @@
-From 317bc732073134159bc74e126339f8e498bdb376 Mon Sep 17 00:00:00 2001
-From: Yi Wang <wang.yi59@zte.com.cn>
-Date: Fri, 13 Aug 2021 13:49:13 +0800
-Subject: [PATCH] lvchange: fix lvchange refresh failed for dm suspend or
- resume failed
-
-When multiple lvchange refresh processes executed at the same time,
-suspend/resume ioctl on the same dm, some of these commands will be failed
-for dm aready change status, and ioctl will return EINVAL in _do_dm_ioctl function.
-to avoid this problem, add READ_FOR_ACTIVATE flags in lvchange refresh process,
-it will hold LCK_WRITE lock and avoid suspend/resume dm at the same time.
-
-Signed-off-by: Long YunJian <long.yunjian@zte.com.cn>
-Signed-off-by: Yi Wang <wang.yi59@zte.com.cn>
-(cherry picked from commit 47bcb446b83f9aa4fca74301fda109a8bf670fbb)
----
- tools/lvchange.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/tools/lvchange.c b/tools/lvchange.c
-index 8293f5035..fb9ac895f 100644
---- a/tools/lvchange.c
-+++ b/tools/lvchange.c
-@@ -1620,7 +1620,7 @@ int lvchange_refresh_cmd(struct cmd_context *cmd, int argc, char **argv)
- 	cmd->handles_missing_pvs = 1;
- 	cmd->lockd_vg_default_sh = 1;
- 
--	return process_each_lv(cmd, argc, argv, NULL, NULL, 0,
-+	return process_each_lv(cmd, argc, argv, NULL, NULL, READ_FOR_ACTIVATE,
- 			       NULL, &_lvchange_refresh_check, &_lvchange_refresh_single);
- }
- 
--- 
-2.34.1
-
diff --git a/SOURCES/lvm2-2_03_14-tests-check-lvm2-parses-vdo-statistics.patch b/SOURCES/lvm2-2_03_14-tests-check-lvm2-parses-vdo-statistics.patch
deleted file mode 100644
index 1adbfdd..0000000
--- a/SOURCES/lvm2-2_03_14-tests-check-lvm2-parses-vdo-statistics.patch
+++ /dev/null
@@ -1,25 +0,0 @@
-From 155d8c55086b09528de799425e77f7aeafd9b165 Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Thu, 9 Sep 2021 15:22:20 +0200
-Subject: [PATCH 2/5] tests: check lvm2 parses vdo statistics
-
-(cherry picked from commit bd2dae464386033241afa35934cdeddfe47f6a77)
----
- test/shell/lvcreate-vdo.sh | 1 +
- 1 file changed, 1 insertion(+)
-
-diff --git a/test/shell/lvcreate-vdo.sh b/test/shell/lvcreate-vdo.sh
-index d66e353..5b370fb 100644
---- a/test/shell/lvcreate-vdo.sh
-+++ b/test/shell/lvcreate-vdo.sh
-@@ -47,6 +47,7 @@ fi
- check lv_field $vg/$lv1 size "<1.24g"
- check lv_field $vg/${lv2} size "4.00g"
- check lv_field $vg/${lv2}_vdata size "4.00g"
-+check lv_field $vg/${lv1} data_percent "0.00"
- lvremove -ff $vg
- 
- 
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-Rename-vdoimport-to-lvm_import_vdo.patch b/SOURCES/lvm2-2_03_14-vdo-Rename-vdoimport-to-lvm_import_vdo.patch
deleted file mode 100644
index 2250e1c..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-Rename-vdoimport-to-lvm_import_vdo.patch
+++ /dev/null
@@ -1,1137 +0,0 @@
- WHATS_NEW                 |   4 +
- configure                 |   6 +-
- configure.ac              |   8 +-
- include/configure.h.in    |   2 +-
- man/Makefile.in           |   2 +-
- man/lvm_import_vdo.8_main |  92 ++++++++++++
- man/vdoimport.8_main      |  92 ------------
- scripts/Makefile.in       |   2 +-
- scripts/lvm_import_vdo.sh | 376 ++++++++++++++++++++++++++++++++++++++++++++++
- scripts/vdoimport.sh      | 376 ----------------------------------------------
- test/Makefile.in          |   2 +-
- test/shell/vdo-convert.sh |  12 +-
- 12 files changed, 489 insertions(+), 485 deletions(-)
- create mode 100644 man/lvm_import_vdo.8_main
- delete mode 100644 man/vdoimport.8_main
- create mode 100755 scripts/lvm_import_vdo.sh
- delete mode 100755 scripts/vdoimport.sh
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index 5556789..3637e31 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,3 +1,7 @@
-+Version 2.03.14 - 
-+==================================
-+  Rename vdoimport to lvm_import_vdo.
-+
- Version 2.03.13 - 
- ===============================
-   Support --poolmetadataspare with vgsplit and vgmerge.
-diff --git a/configure b/configure
-index 661702d..897a810 100755
---- a/configure
-+++ b/configure
-@@ -12379,8 +12379,8 @@ $as_echo "$FSADM" >&6; }
- 
- 
- ################################################################################
--{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to install vdoimport" >&5
--$as_echo_n "checking whether to install vdoimport... " >&6; }
-+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to install lvm_import_vdo" >&5
-+$as_echo_n "checking whether to install lvm_import_vdo... " >&6; }
- # Check whether --enable-vdoimport was given.
- if test "${enable_vdoimport+set}" = set; then :
-   enableval=$enable_vdoimport; VDOIMPORT=$enableval
-@@ -13875,7 +13875,7 @@ cat >>confdefs.h <<_ACEOF
- _ACEOF
- 
- 
--VDOIMPORT_PATH="$SBINDIR/vdoimport"
-+VDOIMPORT_PATH="$SBINDIR/lvm_import_vdo"
- 
- cat >>confdefs.h <<_ACEOF
- #define VDOIMPORT_PATH "$VDOIMPORT_PATH"
-diff --git a/configure.ac b/configure.ac
-index 5a8b486..f769a63 100644
---- a/configure.ac
-+++ b/configure.ac
-@@ -1295,8 +1295,8 @@ AC_MSG_RESULT($FSADM)
- 
- 
- ################################################################################
--dnl -- Enable vdoimport
--AC_MSG_CHECKING(whether to install vdoimport)
-+dnl -- Enable lvm_import_vdo
-+AC_MSG_CHECKING(whether to install lvm_import_vdo)
- AC_ARG_ENABLE(vdoimport, AC_HELP_STRING([--disable-vdoimport], [disable vdoimport]),
- 	      VDOIMPORT=$enableval)
- AC_MSG_RESULT($VDOIMPORT)
-@@ -1656,8 +1656,8 @@ USRSBINDIR="$(eval echo $(eval echo $usrsbindir))"
- FSADM_PATH="$SBINDIR/fsadm"
- AC_DEFINE_UNQUOTED(FSADM_PATH, ["$FSADM_PATH"], [Path to fsadm binary.])
- 
--VDOIMPORT_PATH="$SBINDIR/vdoimport"
--AC_DEFINE_UNQUOTED(VDOIMPORT_PATH, ["$VDOIMPORT_PATH"], [Path to vdoimport binary.])
-+VDOIMPORT_PATH="$SBINDIR/lvm_import_vdo"
-+AC_DEFINE_UNQUOTED(VDOIMPORT_PATH, ["$VDOIMPORT_PATH"], [Path to lvm_import_vdo binary.])
- 
- ################################################################################
- dnl -- dmeventd pidfile and executable path
-diff --git a/include/configure.h.in b/include/configure.h.in
-index 6df8d89..028ae48 100644
---- a/include/configure.h.in
-+++ b/include/configure.h.in
-@@ -684,7 +684,7 @@
- /* Enable a valgrind aware build of pool */
- #undef VALGRIND_POOL
- 
--/* Path to vdoimport binary. */
-+/* Path to lvm_import_vdo binary. */
- #undef VDOIMPORT_PATH
- 
- /* The path to 'vdoformat', if available. */
-diff --git a/man/Makefile.in b/man/Makefile.in
-index d60a92c..45ebf54 100644
---- a/man/Makefile.in
-+++ b/man/Makefile.in
-@@ -23,7 +23,7 @@ else
- endif
- 
- FSADMMAN = fsadm.8
--VDOIMPORTMAN = vdoimport.8
-+VDOIMPORTMAN = lvm_import_vdo.8
- BLKDEACTIVATEMAN = blkdeactivate.8
- DMEVENTDMAN = dmeventd.8
- DMFILEMAPDMAN = dmfilemapd.8
-diff --git a/man/lvm_import_vdo.8_main b/man/lvm_import_vdo.8_main
-new file mode 100644
-index 0000000..ee817a0
---- /dev/null
-+++ b/man/lvm_import_vdo.8_main
-@@ -0,0 +1,92 @@
-+.TH "FSADM" "8" "LVM TOOLS #VERSION#" "Red Hat, Inc" "\""
-+.
-+.SH "NAME"
-+.
-+lvm_import_vdo \(em utility to import VDO volumes into a new volume group.
-+.
-+.SH SYNOPSIS
-+.
-+.PD 0
-+.ad l
-+.TP 10
-+.B lvm_import_vdo
-+.RI [ options ]
-+.IR device
-+.
-+.PD
-+.
-+.SH DESCRIPTION
-+.
-+lvm_import_vdo utility imports VDO volumes created and managed by
-+.BR vdo (8)
-+manager into
-+.BR lvm2 (8)
-+managed VDO LV. This is realized by moving VDO superblock by 2MiB
-+and creating lvm2 metadata at the front of this device. The operation is not reversible,
-+thus after conversion to lvm2 the access to VDO data is only possible with
-+.BR lvm2 (8)
-+commands,
-+.BR vdo (8)
-+manager no longer control such volume.
-+.
-+.SH OPTIONS
-+.
-+.TP
-+.BR -f | --force
-+Bypass some sanity checks.
-+.
-+.TP
-+.BR -h | --help
-+Display the help text.
-+.
-+.TP
-+.BR -n | --name
-+Specifies the name of converted VDO LV. When the name is not specified,
-+some automatic name is selected. In case the converted VDO volume is
-+already using LV a backend device, the name of this LV is used for VDO LV.
-+In this case also the of volume group must stay same.
-+.
-+.TP
-+.BR -v | --verbose
-+Be more verbose.
-+.
-+.TP
-+.BR -y | --yes
-+Answer "yes" at any prompts.
-+.
-+.TP
-+.BR --dry-run
-+Print commands without running them.
-+.
-+.
-+.SH DIAGNOSTICS
-+.
-+On successful completion, the status code is 0.
-+A status code of 1 is used for failure.
-+.
-+.SH EXAMPLES
-+.
-+Convert VDO volume created by vdo manager into logical volume LV1 with within volume group VG1.
-+.P
-+#
-+.B lvm_import_vdo --name VG1/LV1 /dev/mapper/vdo-volume
-+.
-+.SH ENVIRONMENT VARIABLES
-+.
-+.TP
-+.B TMPDIR
-+The temporary directory name for mount points. Defaults to "\fI/tmp\fP".
-+.TP
-+.B DM_DEV_DIR
-+The device directory name.
-+Defaults to "\fI/dev\fP" and must be an absolute path.
-+.
-+.SH SEE ALSO
-+.
-+.nh
-+.ad l
-+.BR lvm (8),
-+.BR lvm.conf (5),
-+.P
-+.BR vdo (8),
-+.BR vdo2lvm (8),
-diff --git a/man/vdoimport.8_main b/man/vdoimport.8_main
-deleted file mode 100644
-index 1f32909..0000000
---- a/man/vdoimport.8_main
-+++ /dev/null
-@@ -1,92 +0,0 @@
--.TH "FSADM" "8" "LVM TOOLS #VERSION#" "Red Hat, Inc" "\""
--.
--.SH "NAME"
--.
--vdoimport \(em utility to import VDO volumes into a new volume group.
--.
--.SH SYNOPSIS
--.
--.PD 0
--.ad l
--.TP 10
--.B vdoimport
--.RI [ options ]
--.IR device
--.
--.PD
--.
--.SH DESCRIPTION
--.
--vdoimport utility imports VDO volumes created and managed by
--.BR vdo (8)
--manager into
--.BR lvm2 (8)
--managed VDO LV. This is realized by moving VDO superblock by 2MiB
--and creating lvm2 metadata at the front of this device. The operation is not reversible,
--thus after conversion to lvm2 the access to VDO data is only possible with
--.BR lvm2 (8)
--commands,
--.BR vdo (8)
--manager no longer control such volume.
--.
--.SH OPTIONS
--.
--.TP
--.BR -f | --force
--Bypass some sanity checks.
--.
--.TP
--.BR -h | --help
--Display the help text.
--.
--.TP
--.BR -n | --name
--Specifies the name of converted VDO LV. When the name is not specified,
--some automatic name is selected. In case the converted VDO volume is
--already using LV a backend device, the name of this LV is used for VDO LV.
--In this case also the of volume group must stay same.
--.
--.TP
--.BR -v | --verbose
--Be more verbose.
--.
--.TP
--.BR -y | --yes
--Answer "yes" at any prompts.
--.
--.TP
--.BR --dry-run
--Print commands without running them.
--.
--.
--.SH DIAGNOSTICS
--.
--On successful completion, the status code is 0.
--A status code of 1 is used for failure.
--.
--.SH EXAMPLES
--.
--Convert VDO volume created by vdo manager into logical volume LV1 with within volume group VG1.
--.P
--#
--.B vdoimport --name VG1/LV1 /dev/mapper/vdo-volume
--.
--.SH ENVIRONMENT VARIABLES
--.
--.TP
--.B TMPDIR
--The temporary directory name for mount points. Defaults to "\fI/tmp\fP".
--.TP
--.B DM_DEV_DIR
--The device directory name.
--Defaults to "\fI/dev\fP" and must be an absolute path.
--.
--.SH SEE ALSO
--.
--.nh
--.ad l
--.BR lvm (8),
--.BR lvm.conf (5),
--.P
--.BR vdo (8),
--.BR vdo2lvm (8),
-diff --git a/scripts/Makefile.in b/scripts/Makefile.in
-index 1fe88ca..f16c37d 100644
---- a/scripts/Makefile.in
-+++ b/scripts/Makefile.in
-@@ -32,7 +32,7 @@ ifeq ("@FSADM@", "yes")
- endif
- 
- ifeq ("@VDOIMPORT@", "yes")
--	LVM_SCRIPTS += vdoimport.sh
-+	LVM_SCRIPTS += lvm_import_vdo.sh
- endif
- 
- ifeq ("@BLKDEACTIVATE@", "yes")
-diff --git a/scripts/lvm_import_vdo.sh b/scripts/lvm_import_vdo.sh
-new file mode 100755
-index 0000000..35140a0
---- /dev/null
-+++ b/scripts/lvm_import_vdo.sh
-@@ -0,0 +1,376 @@
-+#!/bin/bash
-+#
-+# Copyright (C) 2021 Red Hat, Inc. All rights reserved.
-+#
-+# This file is part of LVM2.
-+#
-+# This copyrighted material is made available to anyone wishing to use,
-+# modify, copy, or redistribute it subject to the terms and conditions
-+# of the GNU General Public License v.2.
-+#
-+# You should have received a copy of the GNU General Public License
-+# along with this program; if not, write to the Free Software Foundation,
-+# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
-+#
-+# Author: Zdenek Kabelac <zkabelac at redhat.com>
-+#
-+# Script for converting VDO volumes to lvm2 VDO LVs
-+#
-+# Needed utilities:
-+#  lvm, dmsetup,
-+#  vdo, vdo2lvm,
-+#  grep, awk, sed, blockdev, readlink, mkdir
-+#
-+# Conversion is using  'vdo convert' support from VDO manager to move
-+# existing VDO header by 2M which makes space to place in PV header
-+# and VG metadata area, and then create VDOPOOL LV and VDO LV in such VG.
-+#
-+
-+set -euE -o pipefail
-+
-+TOOL=lvm_import_vdo
-+
-+_SAVEPATH=$PATH
-+PATH="/sbin:/usr/sbin:/bin:/usr/sbin:$PATH"
-+
-+# user may override lvm location by setting LVM_BINARY
-+LVM=${LVM_BINARY:-lvm}
-+VDO=${VDO_BINARY:-vdo}
-+VDOCONF=${VDOCONF:-}
-+BLOCKDEV="blockdev"
-+READLINK="readlink"
-+READLINK_E="-e"
-+MKDIR="mkdir"
-+
-+TEMPDIR="${TMPDIR:-/tmp}/${TOOL}_${RANDOM}$$"
-+DM_DEV_DIR="${DM_DEV_DIR:-/dev}"
-+
-+DRY=0
-+VERB=""
-+FORCE=""
-+YES=""
-+
-+# default name for converted VG and its VDO LV
-+NAME="vdovg/vdolvol"
-+
-+# help message
-+tool_usage() {
-+	echo "${TOOL}: Utility to convert VDO volume to VDO LV."
-+	echo
-+	echo "	${TOOL} [options] <vdo_device_path>"
-+	echo
-+	echo "	Options:"
-+	echo "	  -f | --force	      Bypass sanity checks"
-+	echo "	  -h | --help	      Show this help message"
-+	echo "	  -n | --name	      Specifies VG/LV name for converted VDO volume"
-+	echo "	  -v | --verbose      Be verbose"
-+	echo "	  -y | --yes	      Answer \"yes\" at any prompts"
-+	echo "	       --dry-run      Print commands without running them"
-+
-+	exit
-+}
-+
-+verbose() {
-+	test -z "$VERB" || echo "$TOOL:" "$@"
-+}
-+
-+# Support multi-line error messages
-+error() {
-+	for i in "$@" ;  do
-+		echo "$TOOL: $i" >&2
-+	done
-+	cleanup 1
-+}
-+
-+dry() {
-+	if [ "$DRY" -ne 0 ]; then
-+		verbose "Dry execution" "$@"
-+		return 0
-+	fi
-+	verbose "Executing" "$@"
-+	"$@"
-+}
-+
-+cleanup() {
-+	trap '' 2
-+
-+	rm -rf "$TEMPDIR"
-+	# error exit status for break
-+	exit "${1:-1}"
-+}
-+
-+get_enabled_value_() {
-+	case "$1" in
-+	enabled) echo "1" ;;
-+	*) echo "0" ;;
-+	esac
-+}
-+
-+get_kb_size_with_unit_() {
-+	case "$1" in
-+	*[kK]) echo $(( ${1%[kK]} )) ;;
-+	*[mM]) echo $(( ${1%[mM]} * 1024 )) ;;
-+	*[gG]) echo $(( ${1%[gG]} * 1024 * 1024 )) ;;
-+	*[tT]) echo $(( ${1%[tT]} * 1024 * 1024 * 1024 )) ;;
-+	*[pP]) echo $(( ${1%[pP]} * 1024 * 1024 * 1024 * 1024 )) ;;
-+	esac
-+}
-+
-+get_mb_size_with_unit_() {
-+	case "$1" in
-+	*[mM]) echo $(( ${1%[mM]} )) ;;
-+	*[gG]) echo $(( ${1%[gG]} * 1024 )) ;;
-+	*[tT]) echo $(( ${1%[tT]} * 1024 * 1024 )) ;;
-+	*[pP]) echo $(( ${1%[pP]} * 1024 * 1024 * 1024 )) ;;
-+	esac
-+}
-+
-+# Figure out largest possible extent size usable for VG
-+# $1   physical size
-+# $2   logical size
-+get_largest_extent_size_() {
-+	local max=4
-+	local i
-+	local d
-+
-+	for i in 8 16 32 64 128 256 512 1024 2048 4096 ; do
-+		d=$(( $1 / i ))
-+		test $(( d * i )) -eq "$1" || break
-+		d=$(( $2 / i ))
-+		test $(( d * i )) -eq "$2" || break
-+		max=$i
-+	done
-+	echo "$max"
-+}
-+
-+# detect LV on the given device
-+# dereference device name if it is symbolic link
-+detect_lv_() {
-+	local DEVICE=$1
-+	local MAJOR
-+	local MINOR
-+	local SYSVOLUME
-+	local MAJORMINOR
-+
-+	DEVICE=${1/#"${DM_DEV_DIR}/"/}
-+	DEVICE=$("$READLINK" $READLINK_E "$DM_DEV_DIR/$DEVICE")
-+	test -n "$DEVICE" || error "Cannot get readlink \"$1\"."
-+	RDEVICE=$DEVICE
-+	case "$RDEVICE" in
-+	  # hardcoded /dev  since udev does not create these entries elsewhere
-+	  /dev/dm-[0-9]*)
-+		read -r <"/sys/block/${RDEVICE#/dev/}/dm/name" SYSVOLUME 2>&1 && DEVICE="$DM_DEV_DIR/mapper/$SYSVOLUME"
-+		read -r <"/sys/block/${RDEVICE#/dev/}/dev" MAJORMINOR 2>&1 || error "Cannot get major:minor for \"$DEVICE\"."
-+		MAJOR=${MAJORMINOR%%:*}
-+		MINOR=${MAJORMINOR##*:}
-+		;;
-+	  *)
-+		STAT=$(stat --format "MAJOR=\$((0x%t)) MINOR=\$((0x%T))" "$RDEVICE")
-+		test -n "$STAT" || error "Cannot get major:minor for \"$DEVICE\"."
-+		eval "$STAT"
-+		;;
-+	esac
-+
-+	eval "$(dmsetup info -c -j "$MAJOR" -m "$MINOR" -o uuid,name --noheadings --nameprefixes --separator ' ')"
-+}
-+
-+# parse yaml config files into 'prefix_yaml_part_names=("value")' strings
-+parse_yaml_() {
-+	local yaml_file=$1
-+	local prefix=$2
-+	local s
-+	local w
-+	local fs
-+
-+	s='[[:space:]]*'
-+	w='[a-zA-Z0-9_.-]*'
-+	fs="$(echo @|tr @ '\034')"
-+
-+	(
-+	    sed -ne '/^--/s|--||g; s|\"|\\\"|g; s/[[:space:]]*$//g;' \
-+		-e 's/\$/\\\$/g' \
-+		-e "/#.*[\"\']/!s| #.*||g; /^#/s|#.*||g;" \
-+		-e "s|^\($s\)\($w\)$s:$s\"\(.*\)\"$s\$|\1$fs\2$fs\3|p" \
-+		-e "s|^\($s\)\($w\)${s}[:-]$s\(.*\)$s\$|\1$fs\2$fs\3|p" |
-+
-+	    awk -F"$fs" '{
-+		indent = length($1)/2;
-+		if (length($2) == 0) { conj[indent]="+";} else {conj[indent]="";}
-+		vname[indent] = $2;
-+		for (i in vname) {if (i > indent) {delete vname[i]}}
-+		    if (length($3) > 0) {
-+			vn=""; for (i=0; i<indent; i++) {vn=(vn)(vname[i])("_")}
-+			printf("%s%s%s%s=(\"%s\")\n", "'"$prefix"'",vn, $2, conj[indent-1], $3);
-+		    }
-+		}' |
-+
-+	    sed -e 's/_=/+=/g' |
-+
-+	    awk 'BEGIN {
-+		    FS="=";
-+		    OFS="="
-+		}
-+		/(-|\.).*=/ {
-+		    gsub("-|\\.", "_", $1)
-+		}
-+		{ print }'
-+	) < "$yaml_file"
-+}
-+
-+# convert existing VDO volume into lvm2 volume
-+convert2lvm_() {
-+	local DEVICE=$1
-+	local VGNAME=${NAME%/*}
-+	local LVNAME=${NAME#*/}
-+	local VDONAME
-+	local TRVDONAME
-+	local EXTENTSZ
-+	local IS_LV=1
-+
-+	DM_UUID=""
-+	detect_lv_ "$DEVICE"
-+	case "$DM_UUID" in
-+		LVM-*)	eval "$(dmsetup splitname --nameprefixes --noheadings --separator ' ' "$DM_NAME")"
-+			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ]  ; then
-+				VGNAME=$DM_VG_NAME
-+			elif test "$VGNAME" != "$DM_VG_NAME" ; then
-+				error "Volume group name \"$VGNAME\" does not match name \"$DM_VG_NAME\" for device \"$DEVICE\"."
-+			fi
-+			;;
-+		*) IS_LV=0
-+			# Check $VGNANE does not already exists
-+			"$LVM" vgs "$VGNAME" && error "Cannot use already existing volume group name \"$VGNAME\"."
-+			;;
-+	esac
-+
-+	verbose "Checked whether device $1 is already LV ($IS_LV)."
-+
-+	"$MKDIR" -p -m 0000 "$TEMPDIR" || error "Failed to create $TEMPDIR."
-+
-+	verbose "Getting YAML VDO configuration."
-+	"$VDO" printConfigFile $VDOCONF >"$TEMPDIR/vdoconf.yml"
-+
-+	VDONAME=$(awk -v DNAME="$DEVICE" '/.*VDOService$/ {VNAME=substr($1, 0, length($1) - 1)} /[[:space:]]*device:/ { if ($2 ~ DNAME) {print VNAME}}' "$TEMPDIR/vdoconf.yml")
-+	TRVDONAME=$(echo "$VDONAME" | tr '-' '_')
-+
-+	# When VDO volume is 'active', check it's not mounted/being used
-+	eval "$(dmsetup info -c -o open  "$VDONAME" --noheadings --nameprefixes || true)"
-+	test "${DM_OPEN:-0}" -eq 0 || error "Cannot converted VDO volume \"$VDONAME\" which is in use!"
-+
-+	#parse_yaml_ "$TEMPDIR/vdoconf.yml" _
-+	eval "$(parse_yaml_ "$TEMPDIR/vdoconf.yml" _ | grep "$TRVDONAME" | sed -e "s/_config_vdos_$TRVDONAME/vdo/g")"
-+
-+	vdo_logicalSize=$(get_kb_size_with_unit_ "$vdo_logicalSize")
-+	vdo_physicalSize=$(get_kb_size_with_unit_ "$vdo_physicalSize")
-+
-+	verbose "Going to convert physical sized VDO device $vdo_physicalSize KiB."
-+	verbose "With logical volume of size $vdo_logicalSize KiB."
-+
-+	PARAMS=$(cat <<EOF
-+allocation {
-+	vdo_use_compression = $(get_enabled_value_ "$vdo_compression")
-+	vdo_use_deduplication = $(get_enabled_value_ "$vdo_deduplication")
-+	vdo_use_metadata_hints=1
-+	vdo_minimum_io_size = $vdo_logicalBlockSize
-+	vdo_block_map_cache_size_mb = $(get_mb_size_with_unit_ "$vdo_blockMapCacheSize")
-+	vdo_block_map_period = $vdo_blockMapPeriod
-+	vdo_check_point_frequency = $vdo_indexCfreq
-+	vdo_use_sparse_index = $(get_enabled_value_ "$vdo_indexSparse")
-+	vdo_index_memory_size_mb = $(awk "BEGIN {print $vdo_indexMemory * 1024}")
-+	vdo_slab_size_mb = $(get_mb_size_with_unit_ "$vdo_blockMapCacheSize")
-+	vdo_ack_threads = $vdo_ackThreads
-+	vdo_bio_threads = $vdo_bioThreads
-+	vdo_bio_rotation = $vdo_bioRotationInterval
-+	vdo_cpu_threads = $vdo_cpuThreads
-+	vdo_hash_zone_threads = $vdo_hashZoneThreads
-+	vdo_logical_threads = $vdo_logicalThreads
-+	vdo_physical_threads = $vdo_physicalThreads
-+	vdo_write_policy = $vdo_writePolicy
-+	vdo_max_discard = $(( $(get_kb_size_with_unit_ "$vdo_maxDiscardSize") * 1024 ))
-+	vdo_pool_header_size = 0
-+}
-+EOF
-+)
-+	verbose "VDO conversion paramaters: $PARAMS"
-+
-+	verbose "Stopping VDO volume."
-+	dry "$VDO" stop $VDOCONF --name "$VDONAME"
-+
-+	if [ "$IS_LV" = "0" ]; then
-+		verbose "Moving VDO header by 2MiB."
-+		dry "$VDO" convert $VDOCONF --force --name "$VDONAME"
-+
-+		dry "$LVM" pvcreate $YES --dataalignment 2M "$DEVICE" || {
-+			error "Creation of PV on \"$DEVICE\" failed, while VDO header has been already moved!"
-+		}
-+
-+		# Obtain free space in this new PV
-+		# after 'vdo convert/vdo2lvm' call there is +2M free space at the front of the device
-+		case "$DRY" in
-+		0) pvfree=$("$LVM" pvs -o devsize --units b --nosuffix --noheadings "$DEVICE") ;;
-+		*) pvfree=$("$BLOCKDEV" --getsize64 "$DEVICE") ;;
-+		esac
-+
-+		pvfree=$(( pvfree / 1024 - 2048 ))	# to KiB
-+	else
-+		pvfree=$("$LVM" lvs -o size --units b --nosuffix --noheadings "$VGNAME/$LVNAME")
-+		pvfree=$(( pvfree / 1024 ))		# to KiB
-+	fi
-+
-+	# select largest possible extent size that can exactly express both sizes
-+	EXTENTSZ=$(get_largest_extent_size_ "$pvfree" "$vdo_logicalSize")
-+
-+	if [ "$IS_LV" = "0" ]; then
-+		verbose "Creating VG \"${NAME%/*}\" with extent size $EXTENTSZ KiB."
-+		dry "$LVM" vgcreate $YES $VERB -s "${EXTENTSZ}k" "$VGNAME" "$DEVICE" || {
-+			error "Creation of VG \"$VGNAME\" failed, while VDO header has been already moved!"
-+		}
-+
-+		verbose "Creating VDO pool data LV from all extents in volume group $VGNAME."
-+		dry "$LVM" lvcreate -Zn -Wn $YES $VERB -l100%VG -n "${LVNAME}_vpool" "$VGNAME"
-+	else
-+		# validate existing  VG extent_size can express virtual VDO size
-+		vg_extent_size=$("$LVM" vgs -o vg_extent_size --units b --nosuffix --noheadings "$VGNAME" || true)
-+		vg_extent_size=$(( vg_extent_size / 1024 ))
-+
-+		test "$vg_extent_size" -le "$EXTENTSZ" || {
-+			error "Please vgchange extent_size to at most $EXTENTSZ KiB or extend and align virtual size on $vg_extent_size KiB."
-+		}
-+		verbose "Renaming existing LV to be used as _vdata volume for VDO pool LV."
-+		dry "$LVM" lvrename $YES $VERB "$VGNAME/$LVNAME" "$VGNAME/${LVNAME}_vpool" || {
-+			error "Rename of LV \"$VGNAME/$LVNAME\" failed, while VDO header has been already moved!"
-+		}
-+	fi
-+
-+	verbose "Converting to VDO pool."
-+	dry "$LVM" lvconvert $YES $VERB $FORCE --config "$PARAMS" -Zn -V "${vdo_logicalSize}k" -n "$LVNAME" --type vdo-pool "$VGNAME/${LVNAME}_vpool"
-+
-+	rm -fr "$TEMPDIR"
-+}
-+
-+#############################
-+# start point of this script
-+# - parsing parameters
-+#############################
-+trap "cleanup 2" 2
-+
-+test "$#" -eq 0 && tool_usage
-+
-+while [ "$#" -ne 0 ]
-+do
-+	 case "$1" in
-+	  "") ;;
-+	  "-f"|"--force"  ) FORCE="-f" ;;
-+	  "-h"|"--help"   ) tool_usage ;;
-+	  "-n"|"--name"   ) shift; NAME=$1 ;;
-+	  "-v"|"--verbose") VERB="-v" ;;
-+	  "-y"|"--yes"    ) YES="-y" ;;
-+	  "--dry-run"     ) DRY="1" ;;
-+	  "-*") error "Wrong argument \"$1\". (see: $TOOL --help)" ;;
-+	  *) DEVICENAME=$1 ;;  # device name does not start with '-'
-+	esac
-+	shift
-+done
-+
-+# do conversion
-+convert2lvm_ "$DEVICENAME"
-diff --git a/scripts/vdoimport.sh b/scripts/vdoimport.sh
-deleted file mode 100755
-index ef96591..0000000
---- a/scripts/vdoimport.sh
-+++ /dev/null
-@@ -1,376 +0,0 @@
--#!/bin/bash
--#
--# Copyright (C) 2021 Red Hat, Inc. All rights reserved.
--#
--# This file is part of LVM2.
--#
--# This copyrighted material is made available to anyone wishing to use,
--# modify, copy, or redistribute it subject to the terms and conditions
--# of the GNU General Public License v.2.
--#
--# You should have received a copy of the GNU General Public License
--# along with this program; if not, write to the Free Software Foundation,
--# Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
--#
--# Author: Zdenek Kabelac <zkabelac at redhat.com>
--#
--# Script for converting VDO volumes to lvm2 VDO LVs
--#
--# Needed utilities:
--#  lvm, dmsetup,
--#  vdo, vdo2lvm,
--#  grep, awk, sed, blockdev, readlink, mkdir
--#
--# Conversion is using  'vdo convert' support from VDO manager to move
--# existing VDO header by 2M which makes space to place in PV header
--# and VG metadata area, and then create VDOPOOL LV and VDO LV in such VG.
--#
--
--set -euE -o pipefail
--
--TOOL=vdoimport
--
--_SAVEPATH=$PATH
--PATH="/sbin:/usr/sbin:/bin:/usr/sbin:$PATH"
--
--# user may override lvm location by setting LVM_BINARY
--LVM=${LVM_BINARY:-lvm}
--VDO=${VDO_BINARY:-vdo}
--VDOCONF=${VDOCONF:-}
--BLOCKDEV="blockdev"
--READLINK="readlink"
--READLINK_E="-e"
--MKDIR="mkdir"
--
--TEMPDIR="${TMPDIR:-/tmp}/${TOOL}_${RANDOM}$$"
--DM_DEV_DIR="${DM_DEV_DIR:-/dev}"
--
--DRY=0
--VERB=""
--FORCE=""
--YES=""
--
--# default name for converted VG and its VDO LV
--NAME="vdovg/vdolvol"
--
--# help message
--tool_usage() {
--	echo "${TOOL}: Utility to convert VDO volume to VDO LV."
--	echo
--	echo "	${TOOL} [options] <vdo_device_path>"
--	echo
--	echo "	Options:"
--	echo "	  -f | --force	      Bypass sanity checks"
--	echo "	  -h | --help	      Show this help message"
--	echo "	  -n | --name	      Specifies VG/LV name for converted VDO volume"
--	echo "	  -v | --verbose      Be verbose"
--	echo "	  -y | --yes	      Answer \"yes\" at any prompts"
--	echo "	       --dry-run      Print commands without running them"
--
--	exit
--}
--
--verbose() {
--	test -z "$VERB" || echo "$TOOL:" "$@"
--}
--
--# Support multi-line error messages
--error() {
--	for i in "$@" ;  do
--		echo "$TOOL: $i" >&2
--	done
--	cleanup 1
--}
--
--dry() {
--	if [ "$DRY" -ne 0 ]; then
--		verbose "Dry execution" "$@"
--		return 0
--	fi
--	verbose "Executing" "$@"
--	"$@"
--}
--
--cleanup() {
--	trap '' 2
--
--	rm -rf "$TEMPDIR"
--	# error exit status for break
--	exit "${1:-1}"
--}
--
--get_enabled_value_() {
--	case "$1" in
--	enabled) echo "1" ;;
--	*) echo "0" ;;
--	esac
--}
--
--get_kb_size_with_unit_() {
--	case "$1" in
--	*[kK]) echo $(( ${1%[kK]} )) ;;
--	*[mM]) echo $(( ${1%[mM]} * 1024 )) ;;
--	*[gG]) echo $(( ${1%[gG]} * 1024 * 1024 )) ;;
--	*[tT]) echo $(( ${1%[tT]} * 1024 * 1024 * 1024 )) ;;
--	*[pP]) echo $(( ${1%[pP]} * 1024 * 1024 * 1024 * 1024 )) ;;
--	esac
--}
--
--get_mb_size_with_unit_() {
--	case "$1" in
--	*[mM]) echo $(( ${1%[mM]} )) ;;
--	*[gG]) echo $(( ${1%[gG]} * 1024 )) ;;
--	*[tT]) echo $(( ${1%[tT]} * 1024 * 1024 )) ;;
--	*[pP]) echo $(( ${1%[pP]} * 1024 * 1024 * 1024 )) ;;
--	esac
--}
--
--# Figure out largest possible extent size usable for VG
--# $1   physical size
--# $2   logical size
--get_largest_extent_size_() {
--	local max=4
--	local i
--	local d
--
--	for i in 8 16 32 64 128 256 512 1024 2048 4096 ; do
--		d=$(( $1 / i ))
--		test $(( d * i )) -eq "$1" || break
--		d=$(( $2 / i ))
--		test $(( d * i )) -eq "$2" || break
--		max=$i
--	done
--	echo "$max"
--}
--
--# detect LV on the given device
--# dereference device name if it is symbolic link
--detect_lv_() {
--	local DEVICE=$1
--	local MAJOR
--	local MINOR
--	local SYSVOLUME
--	local MAJORMINOR
--
--	DEVICE=${1/#"${DM_DEV_DIR}/"/}
--	DEVICE=$("$READLINK" $READLINK_E "$DM_DEV_DIR/$DEVICE")
--	test -n "$DEVICE" || error "Cannot get readlink \"$1\"."
--	RDEVICE=$DEVICE
--	case "$RDEVICE" in
--	  # hardcoded /dev  since udev does not create these entries elsewhere
--	  /dev/dm-[0-9]*)
--		read -r <"/sys/block/${RDEVICE#/dev/}/dm/name" SYSVOLUME 2>&1 && DEVICE="$DM_DEV_DIR/mapper/$SYSVOLUME"
--		read -r <"/sys/block/${RDEVICE#/dev/}/dev" MAJORMINOR 2>&1 || error "Cannot get major:minor for \"$DEVICE\"."
--		MAJOR=${MAJORMINOR%%:*}
--		MINOR=${MAJORMINOR##*:}
--		;;
--	  *)
--		STAT=$(stat --format "MAJOR=\$((0x%t)) MINOR=\$((0x%T))" "$RDEVICE")
--		test -n "$STAT" || error "Cannot get major:minor for \"$DEVICE\"."
--		eval "$STAT"
--		;;
--	esac
--
--	eval "$(dmsetup info -c -j "$MAJOR" -m "$MINOR" -o uuid,name --noheadings --nameprefixes --separator ' ')"
--}
--
--# parse yaml config files into 'prefix_yaml_part_names=("value")' strings
--parse_yaml_() {
--	local yaml_file=$1
--	local prefix=$2
--	local s
--	local w
--	local fs
--
--	s='[[:space:]]*'
--	w='[a-zA-Z0-9_.-]*'
--	fs="$(echo @|tr @ '\034')"
--
--	(
--	    sed -ne '/^--/s|--||g; s|\"|\\\"|g; s/[[:space:]]*$//g;' \
--		-e 's/\$/\\\$/g' \
--		-e "/#.*[\"\']/!s| #.*||g; /^#/s|#.*||g;" \
--		-e "s|^\($s\)\($w\)$s:$s\"\(.*\)\"$s\$|\1$fs\2$fs\3|p" \
--		-e "s|^\($s\)\($w\)${s}[:-]$s\(.*\)$s\$|\1$fs\2$fs\3|p" |
--
--	    awk -F"$fs" '{
--		indent = length($1)/2;
--		if (length($2) == 0) { conj[indent]="+";} else {conj[indent]="";}
--		vname[indent] = $2;
--		for (i in vname) {if (i > indent) {delete vname[i]}}
--		    if (length($3) > 0) {
--			vn=""; for (i=0; i<indent; i++) {vn=(vn)(vname[i])("_")}
--			printf("%s%s%s%s=(\"%s\")\n", "'"$prefix"'",vn, $2, conj[indent-1], $3);
--		    }
--		}' |
--
--	    sed -e 's/_=/+=/g' |
--
--	    awk 'BEGIN {
--		    FS="=";
--		    OFS="="
--		}
--		/(-|\.).*=/ {
--		    gsub("-|\\.", "_", $1)
--		}
--		{ print }'
--	) < "$yaml_file"
--}
--
--# convert existing VDO volume into lvm2 volume
--convert2lvm_() {
--	local DEVICE=$1
--	local VGNAME=${NAME%/*}
--	local LVNAME=${NAME#*/}
--	local VDONAME
--	local TRVDONAME
--	local EXTENTSZ
--	local IS_LV=1
--
--	DM_UUID=""
--	detect_lv_ "$DEVICE"
--	case "$DM_UUID" in
--		LVM-*)	eval "$(dmsetup splitname --nameprefixes --noheadings --separator ' ' "$DM_NAME")"
--			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ]  ; then
--				VGNAME=$DM_VG_NAME
--			elif test "$VGNAME" != "$DM_VG_NAME" ; then
--				error "Volume group name \"$VGNAME\" does not match name \"$DM_VG_NAME\" for device \"$DEVICE\"."
--			fi
--			;;
--		*) IS_LV=0
--			# Check $VGNANE does not already exists
--			"$LVM" vgs "$VGNAME" && error "Cannot use already existing volume group name \"$VGNAME\"."
--			;;
--	esac
--
--	verbose "Checked whether device $1 is already LV ($IS_LV)."
--
--	"$MKDIR" -p -m 0000 "$TEMPDIR" || error "Failed to create $TEMPDIR."
--
--	verbose "Getting YAML VDO configuration."
--	"$VDO" printConfigFile $VDOCONF >"$TEMPDIR/vdoconf.yml"
--
--	VDONAME=$(awk -v DNAME="$DEVICE" '/.*VDOService$/ {VNAME=substr($1, 0, length($1) - 1)} /[[:space:]]*device:/ { if ($2 ~ DNAME) {print VNAME}}' "$TEMPDIR/vdoconf.yml")
--	TRVDONAME=$(echo "$VDONAME" | tr '-' '_')
--
--	# When VDO volume is 'active', check it's not mounted/being used
--	eval "$(dmsetup info -c -o open  "$VDONAME" --noheadings --nameprefixes || true)"
--	test "${DM_OPEN:-0}" -eq 0 || error "Cannot converted VDO volume \"$VDONAME\" which is in use!"
--
--	#parse_yaml_ "$TEMPDIR/vdoconf.yml" _
--	eval "$(parse_yaml_ "$TEMPDIR/vdoconf.yml" _ | grep "$TRVDONAME" | sed -e "s/_config_vdos_$TRVDONAME/vdo/g")"
--
--	vdo_logicalSize=$(get_kb_size_with_unit_ "$vdo_logicalSize")
--	vdo_physicalSize=$(get_kb_size_with_unit_ "$vdo_physicalSize")
--
--	verbose "Going to convert physical sized VDO device $vdo_physicalSize KiB."
--	verbose "With logical volume of size $vdo_logicalSize KiB."
--
--	PARAMS=$(cat <<EOF
--allocation {
--	vdo_use_compression = $(get_enabled_value_ "$vdo_compression")
--	vdo_use_deduplication = $(get_enabled_value_ "$vdo_deduplication")
--	vdo_use_metadata_hints=1
--	vdo_minimum_io_size = $vdo_logicalBlockSize
--	vdo_block_map_cache_size_mb = $(get_mb_size_with_unit_ "$vdo_blockMapCacheSize")
--	vdo_block_map_period = $vdo_blockMapPeriod
--	vdo_check_point_frequency = $vdo_indexCfreq
--	vdo_use_sparse_index = $(get_enabled_value_ "$vdo_indexSparse")
--	vdo_index_memory_size_mb = $(awk "BEGIN {print $vdo_indexMemory * 1024}")
--	vdo_slab_size_mb = $(get_mb_size_with_unit_ "$vdo_blockMapCacheSize")
--	vdo_ack_threads = $vdo_ackThreads
--	vdo_bio_threads = $vdo_bioThreads
--	vdo_bio_rotation = $vdo_bioRotationInterval
--	vdo_cpu_threads = $vdo_cpuThreads
--	vdo_hash_zone_threads = $vdo_hashZoneThreads
--	vdo_logical_threads = $vdo_logicalThreads
--	vdo_physical_threads = $vdo_physicalThreads
--	vdo_write_policy = $vdo_writePolicy
--	vdo_max_discard = $(( $(get_kb_size_with_unit_ "$vdo_maxDiscardSize") * 1024 ))
--	vdo_pool_header_size = 0
--}
--EOF
--)
--	verbose "VDO conversion paramaters: $PARAMS"
--
--	verbose "Stopping VDO volume."
--	dry "$VDO" stop $VDOCONF --name "$VDONAME"
--
--	if [ "$IS_LV" = "0" ]; then
--		verbose "Moving VDO header by 2MiB."
--		dry "$VDO" convert $VDOCONF --force --name "$VDONAME"
--
--		dry "$LVM" pvcreate $YES --dataalignment 2M "$DEVICE" || {
--			error "Creation of PV on \"$DEVICE\" failed, while VDO header has been already moved!"
--		}
--
--		# Obtain free space in this new PV
--		# after 'vdo convert/vdo2lvm' call there is +2M free space at the front of the device
--		case "$DRY" in
--		0) pvfree=$("$LVM" pvs -o devsize --units b --nosuffix --noheadings "$DEVICE") ;;
--		*) pvfree=$("$BLOCKDEV" --getsize64 "$DEVICE") ;;
--		esac
--
--		pvfree=$(( pvfree / 1024 - 2048 ))	# to KiB
--	else
--		pvfree=$("$LVM" lvs -o size --units b --nosuffix --noheadings "$VGNAME/$LVNAME")
--		pvfree=$(( pvfree / 1024 ))		# to KiB
--	fi
--
--	# select largest possible extent size that can exactly express both sizes
--	EXTENTSZ=$(get_largest_extent_size_ "$pvfree" "$vdo_logicalSize")
--
--	if [ "$IS_LV" = "0" ]; then
--		verbose "Creating VG \"${NAME%/*}\" with extent size $EXTENTSZ KiB."
--		dry "$LVM" vgcreate $YES $VERB -s "${EXTENTSZ}k" "$VGNAME" "$DEVICE" || {
--			error "Creation of VG \"$VGNAME\" failed, while VDO header has been already moved!"
--		}
--
--		verbose "Creating VDO pool data LV from all extents in volume group $VGNAME."
--		dry "$LVM" lvcreate -Zn -Wn $YES $VERB -l100%VG -n "${LVNAME}_vpool" "$VGNAME"
--	else
--		# validate existing  VG extent_size can express virtual VDO size
--		vg_extent_size=$("$LVM" vgs -o vg_extent_size --units b --nosuffix --noheadings "$VGNAME" || true)
--		vg_extent_size=$(( vg_extent_size / 1024 ))
--
--		test "$vg_extent_size" -le "$EXTENTSZ" || {
--			error "Please vgchange extent_size to at most $EXTENTSZ KiB or extend and align virtual size on $vg_extent_size KiB."
--		}
--		verbose "Renaming existing LV to be used as _vdata volume for VDO pool LV."
--		dry "$LVM" lvrename $YES $VERB "$VGNAME/$LVNAME" "$VGNAME/${LVNAME}_vpool" || {
--			error "Rename of LV \"$VGNAME/$LVNAME\" failed, while VDO header has been already moved!"
--		}
--	fi
--
--	verbose "Converting to VDO pool."
--	dry "$LVM" lvconvert $YES $VERB $FORCE --config "$PARAMS" -Zn -V "${vdo_logicalSize}k" -n "$LVNAME" --type vdo-pool "$VGNAME/${LVNAME}_vpool"
--
--	rm -fr "$TEMPDIR"
--}
--
--#############################
--# start point of this script
--# - parsing parameters
--#############################
--trap "cleanup 2" 2
--
--test "$#" -eq 0 && tool_usage
--
--while [ "$#" -ne 0 ]
--do
--	 case "$1" in
--	  "") ;;
--	  "-f"|"--force"  ) FORCE="-f" ;;
--	  "-h"|"--help"   ) tool_usage ;;
--	  "-n"|"--name"   ) shift; NAME=$1 ;;
--	  "-v"|"--verbose") VERB="-v" ;;
--	  "-y"|"--yes"    ) YES="-y" ;;
--	  "--dry-run"     ) DRY="1" ;;
--	  "-*") error "Wrong argument \"$1\". (see: $TOOL --help)" ;;
--	  *) DEVICENAME=$1 ;;  # device name does not start with '-'
--	esac
--	shift
--done
--
--# do conversion
--convert2lvm_ "$DEVICENAME"
-diff --git a/test/Makefile.in b/test/Makefile.in
-index 6be03aa..0f2cc25 100644
---- a/test/Makefile.in
-+++ b/test/Makefile.in
-@@ -353,7 +353,7 @@ LIB = $(addprefix lib/, $(LIB_SECURETEST) $(LIB_DMSECURETEST) $(LIB_SHARED) $(LI
- 	$(Q) $(LN_S) -f $(abs_top_srcdir)/conf/lvmdbusd.profile lib/
- 	$(Q) $(LN_S) -f $(abs_top_srcdir)/conf/thin-performance.profile lib/
- 	$(Q) $(LN_S) -f $(abs_top_srcdir)/scripts/fsadm.sh lib/fsadm
--	$(Q) $(LN_S) -f $(abs_top_srcdir)/scripts/vdoimport.sh lib/vdoimport
-+	$(Q) $(LN_S) -f $(abs_top_srcdir)/scripts/lvm_import_vdo.sh lib/lvm_import_vdo
- 	@test "$(srcdir)" = . || \
- 		for i in $(LIB_LVMLOCKD_CONF) $(LIB_MKE2FS_CONF); do \
- 			test -n "$(Q)" || echo "$(LN_S) -f $(abs_top_srcdir)/test/lib/$$i lib/"; \
-diff --git a/test/shell/vdo-convert.sh b/test/shell/vdo-convert.sh
-index 538147b..2d16c97 100644
---- a/test/shell/vdo-convert.sh
-+++ b/test/shell/vdo-convert.sh
-@@ -54,12 +54,12 @@ vdo create $VDOCONF --name "$VDONAME" --device="$DM_DEV_DIR/$vg/$lv1" --vdoLogic
- mkfs -E nodiscard "$DM_DEV_DIR/mapper/$VDONAME"
- 
- # Different VG name fails
--not vdoimport -y -v --name $vg1/$lv1 "$DM_DEV_DIR/$vg/$lv1"
-+not lvm_import_vdo -y -v --name $vg1/$lv1 "$DM_DEV_DIR/$vg/$lv1"
- 
- # Try just dry run and observe logging
--vdoimport --dry-run -y -v --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
-+lvm_import_vdo --dry-run -y -v --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
- 
--vdoimport -y --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
-+lvm_import_vdo -y --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
- 
- # ATM needed - since we do not call 'vdo convert' in this case
- vdo remove $VDOCONF --force --name "$VDONAME" || true
-@@ -79,13 +79,13 @@ vdo create $VDOCONF --name "$VDONAME" --device="$dev1" --vdoLogicalSize=31G
- mkfs -E nodiscard "$DM_DEV_DIR/mapper/$VDONAME"
- 
- # Fail with an already existing volume group $vg2
--not vdoimport --dry-run -y -v --name $vg2/$lv1 "$dev1" |& tee err
-+not lvm_import_vdo --dry-run -y -v --name $vg2/$lv1 "$dev1" |& tee err
- grep "already existing volume group" err
- 
- # User can also convert already stopped VDO volume
- vdo stop $VDOCONF --name "$VDONAME"
- 
--vdoimport -y -v --name $vg/$lv1 "$dev1"
-+lvm_import_vdo -y -v --name $vg/$lv1 "$dev1"
- 
- fsck -n "$DM_DEV_DIR/$vg/$lv1"
- 
-@@ -102,7 +102,7 @@ vdo create $VDOCONF --name "$VDONAME" --device="$dev1" --vdoLogicalSize=23G
- 
- mkfs -E nodiscard "$DM_DEV_DIR/mapper/$VDONAME"
- 
--vdoimport -y -v --name $vg1/$lv2 "$dev1"
-+lvm_import_vdo -y -v --name $vg1/$lv2 "$dev1"
- 
- fsck -n "$DM_DEV_DIR/$vg1/$lv2"
- 
diff --git a/SOURCES/lvm2-2_03_14-vdo-better-message-for-missing-device.patch b/SOURCES/lvm2-2_03_14-vdo-better-message-for-missing-device.patch
deleted file mode 100644
index b973cc1..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-better-message-for-missing-device.patch
+++ /dev/null
@@ -1,86 +0,0 @@
-From deb36d236e2dd86ddc16b33d5ca8c648cc8ed369 Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Wed, 1 Sep 2021 15:46:04 +0200
-Subject: [PATCH 3/5] vdo: better message for missing device
-
-Show readable message when passed device cannot be accessed.
-And use STAT shell var wrapper to call 'stat' command.
-
-(cherry picked from commit 3287d37f440ca272b52f900fc60ee5effcf73697)
-
-Conflicts:
-	scripts/lvm_import_vdo.sh
----
- scripts/lvm_import_vdo.sh | 21 +++++++++++----------
- 1 file changed, 11 insertions(+), 10 deletions(-)
-
-diff --git a/scripts/lvm_import_vdo.sh b/scripts/lvm_import_vdo.sh
-index f8dd71f..dec32bc 100755
---- a/scripts/lvm_import_vdo.sh
-+++ b/scripts/lvm_import_vdo.sh
-@@ -18,8 +18,8 @@
- #
- # Needed utilities:
- #  lvm, dmsetup,
--#  vdo, vdo2lvm,
--#  grep, awk, sed, blockdev, readlink, mkdir
-+#  vdo,
-+#  grep, awk, sed, blockdev, readlink, stat, mkdir
- #
- # Conversion is using  'vdo convert' support from VDO manager to move
- # existing VDO header by 2M which makes space to place in PV header
-@@ -40,6 +40,7 @@ VDOCONF=${VDOCONF:-}
- BLOCKDEV="blockdev"
- READLINK="readlink"
- READLINK_E="-e"
-+STAT="stat"
- MKDIR="mkdir"
- DMSETUP="dmsetup"
- 
-@@ -156,8 +157,8 @@ detect_lv_() {
- 	local MAJORMINOR
- 
- 	DEVICE=${1/#"${DM_DEV_DIR}/"/}
--	DEVICE=$("$READLINK" $READLINK_E "$DM_DEV_DIR/$DEVICE")
--	test -n "$DEVICE" || error "Cannot get readlink \"$1\"."
-+	DEVICE=$("$READLINK" $READLINK_E "$DM_DEV_DIR/$DEVICE" || true)
-+	test -n "$DEVICE" || error "Readlink cannot access device \"$1\"."
- 	RDEVICE=$DEVICE
- 	case "$RDEVICE" in
- 	  # hardcoded /dev  since udev does not create these entries elsewhere
-@@ -168,9 +169,9 @@ detect_lv_() {
- 		DEVMINOR=${MAJORMINOR##*:}
- 		;;
- 	  *)
--		STAT=$(stat --format "DEVMAJOR=\$((0x%t)) DEVMINOR=\$((0x%T))" "$RDEVICE")
--		test -n "$STAT" || error "Cannot get major:minor for \"$DEVICE\"."
--		eval "$STAT"
-+		RSTAT=$("$STAT" --format "DEVMAJOR=\$((0x%t)) DEVMINOR=\$((0x%T))" "$RDEVICE" || true)
-+		test -n "$RSTAT" || error "Cannot get major:minor for \"$DEVICE\"."
-+		eval "$RSTAT"
- 		;;
- 	esac
- 
-@@ -269,8 +270,8 @@ convert2lvm_() {
- 	for i in $(awk '/.*device:/ {print $2}' "$TEMPDIR/vdoconf.yml") ; do
- 		local DEV
- 		DEV=$("$READLINK" $READLINK_E "$i") || continue
--		STAT=$(stat --format "MAJOR=\$((0x%t)) MINOR=\$((0x%T))" "$DEV" 2>/dev/null) || continue
--		eval "$STAT"
-+		RSTAT=$("$STAT" --format "MAJOR=\$((0x%t)) MINOR=\$((0x%T))" "$DEV" 2>/dev/null) || continue
-+		eval "$RSTAT"
- 		test "$MAJOR" = "$DEVMAJOR" && test "$MINOR" = "$DEVMINOR" && {
- 			test -z "$FOUND" || error "VDO configuration contains duplicate entries $FOUND and $i"
- 			FOUND=$i
-@@ -287,7 +288,7 @@ convert2lvm_() {
- 	DM_OPEN="$("$DMSETUP" info -c -o open  "$VDONAME" --noheadings --nameprefixes 2>/dev/null || true)"
- 	case "$DM_OPEN" in
- 	Device*) ;; # no devices
--	*) 	eval "$DM_OPEN"
-+	*)	eval "$DM_OPEN"
- 		test "${DM_OPEN:-0}" -eq 0 || error "Cannot converted VDO volume \"$VDONAME\" which is in use!"
- 		;;
- 	esac
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-fix-conversion-of-large-virtual-sizes.patch b/SOURCES/lvm2-2_03_14-vdo-fix-conversion-of-large-virtual-sizes.patch
deleted file mode 100644
index 9899966..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-fix-conversion-of-large-virtual-sizes.patch
+++ /dev/null
@@ -1,28 +0,0 @@
-From 70467e905cea0811c269faf7e84f24d4e1c758cc Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Mon, 30 Aug 2021 18:12:59 +0200
-Subject: [PATCH 5/5] vdo: fix conversion of large virtual sizes
-
-Properly accept virtual sizes above 2TiB.
-
-(cherry picked from commit 4afe872fd6c43fcfcd519c862574d010cdbda653)
----
- tools/lvconvert.c | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/tools/lvconvert.c b/tools/lvconvert.c
-index f87ee78..518b48f 100644
---- a/tools/lvconvert.c
-+++ b/tools/lvconvert.c
-@@ -5462,7 +5462,7 @@ static int _lvconvert_to_vdopool_single(struct cmd_context *cmd,
- 		return_0;
- 
- 	lvc.virtual_extents = extents_from_size(cmd,
--						arg_uint_value(cmd, virtualsize_ARG, 0),
-+						arg_uint64_value(cmd, virtualsize_ARG, UINT64_C(0)),
- 						vg->extent_size);
- 
- 	if (!(lvc.segtype = get_segtype_from_string(cmd, SEG_TYPE_NAME_VDO)))
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-fixes.patch b/SOURCES/lvm2-2_03_14-vdo-fixes.patch
deleted file mode 100644
index ac6acb5..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-fixes.patch
+++ /dev/null
@@ -1,256 +0,0 @@
-From 5d0756fc33bced8453fb5cf5807c5a3fa2b59dbb Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Tue, 31 Aug 2021 20:52:26 +0200
-Subject: [PATCH 1/5] vdo: fixes
-
-Better identify VDO device with major:minor.
-Handle different LV name from originally converted origin LV.
-Improve --dry-run handling.
-
-(cherry picked from commit 1ae157a0f67e984ef3037d19d62b84a3b0201c84)
----
- WHATS_NEW                 |  4 +++
- scripts/lvm_import_vdo.sh | 70 +++++++++++++++++++++++++++++++++++------------
- test/shell/vdo-convert.sh | 28 ++++++++++++++-----
- 3 files changed, 78 insertions(+), 24 deletions(-)
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index 3637e31..b751009 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,5 +1,9 @@
- Version 2.03.14 - 
- ==================================
-+  Improve lvm_import_vdo script.
-+  Support VDO LV with lvcreate -ky.
-+  Fix lvconvert for VDO LV bigger then 2T.
-+  Create VDO LVs automatically without zeroing.
-   Rename vdoimport to lvm_import_vdo.
- 
- Version 2.03.13 - 
-diff --git a/scripts/lvm_import_vdo.sh b/scripts/lvm_import_vdo.sh
-index 35140a0..bc73306 100755
---- a/scripts/lvm_import_vdo.sh
-+++ b/scripts/lvm_import_vdo.sh
-@@ -41,10 +41,15 @@ BLOCKDEV="blockdev"
- READLINK="readlink"
- READLINK_E="-e"
- MKDIR="mkdir"
-+DMSETUP="dmsetup"
- 
- TEMPDIR="${TMPDIR:-/tmp}/${TOOL}_${RANDOM}$$"
- DM_DEV_DIR="${DM_DEV_DIR:-/dev}"
- 
-+DEVICENAME=""
-+DEVMAJOR=0
-+DEVMINOR=0
-+
- DRY=0
- VERB=""
- FORCE=""
-@@ -147,8 +152,6 @@ get_largest_extent_size_() {
- # dereference device name if it is symbolic link
- detect_lv_() {
- 	local DEVICE=$1
--	local MAJOR
--	local MINOR
- 	local SYSVOLUME
- 	local MAJORMINOR
- 
-@@ -161,17 +164,21 @@ detect_lv_() {
- 	  /dev/dm-[0-9]*)
- 		read -r <"/sys/block/${RDEVICE#/dev/}/dm/name" SYSVOLUME 2>&1 && DEVICE="$DM_DEV_DIR/mapper/$SYSVOLUME"
- 		read -r <"/sys/block/${RDEVICE#/dev/}/dev" MAJORMINOR 2>&1 || error "Cannot get major:minor for \"$DEVICE\"."
--		MAJOR=${MAJORMINOR%%:*}
--		MINOR=${MAJORMINOR##*:}
-+		DEVMAJOR=${MAJORMINOR%%:*}
-+		DEVMINOR=${MAJORMINOR##*:}
- 		;;
- 	  *)
--		STAT=$(stat --format "MAJOR=\$((0x%t)) MINOR=\$((0x%T))" "$RDEVICE")
-+		STAT=$(stat --format "DEVMAJOR=\$((0x%t)) DEVMINOR=\$((0x%T))" "$RDEVICE")
- 		test -n "$STAT" || error "Cannot get major:minor for \"$DEVICE\"."
- 		eval "$STAT"
- 		;;
- 	esac
- 
--	eval "$(dmsetup info -c -j "$MAJOR" -m "$MINOR" -o uuid,name --noheadings --nameprefixes --separator ' ')"
-+	DEV="$("$DMSETUP" info -c -j "$DEVMAJOR" -m "$DEVMINOR" -o uuid,name --noheadings --nameprefixes --separator ' ' 2>/dev/null)"
-+	case "$DEV" in
-+	Device*)  ;; # no devices
-+	*)	eval "$DEV" ;;
-+	esac
- }
- 
- # parse yaml config files into 'prefix_yaml_part_names=("value")' strings
-@@ -226,20 +233,26 @@ convert2lvm_() {
- 	local TRVDONAME
- 	local EXTENTSZ
- 	local IS_LV=1
-+	local FOUND=""
-+	local MAJOR=0
-+	local MINOR=0
-+	local DM_VG_NAME
-+	local DM_LV_NAME
- 
- 	DM_UUID=""
- 	detect_lv_ "$DEVICE"
- 	case "$DM_UUID" in
--		LVM-*)	eval "$(dmsetup splitname --nameprefixes --noheadings --separator ' ' "$DM_NAME")"
-+		LVM-*)	eval "$("$DMSETUP" splitname --nameprefixes --noheadings --separator ' ' "$DM_NAME")"
- 			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ]  ; then
- 				VGNAME=$DM_VG_NAME
-+				LVNAME=$DM_LV_NAME
- 			elif test "$VGNAME" != "$DM_VG_NAME" ; then
- 				error "Volume group name \"$VGNAME\" does not match name \"$DM_VG_NAME\" for device \"$DEVICE\"."
- 			fi
- 			;;
- 		*) IS_LV=0
- 			# Check $VGNANE does not already exists
--			"$LVM" vgs "$VGNAME" && error "Cannot use already existing volume group name \"$VGNAME\"."
-+			"$LVM" vgs "$VGNAME" >/dev/null 2>&1 && error "Cannot use already existing volume group name \"$VGNAME\"."
- 			;;
- 	esac
- 
-@@ -247,15 +260,37 @@ convert2lvm_() {
- 
- 	"$MKDIR" -p -m 0000 "$TEMPDIR" || error "Failed to create $TEMPDIR."
- 
-+	# TODO: might use directly  /etc/vdoconf.yml (avoding need of 'vdo' manager)
- 	verbose "Getting YAML VDO configuration."
- 	"$VDO" printConfigFile $VDOCONF >"$TEMPDIR/vdoconf.yml"
- 
--	VDONAME=$(awk -v DNAME="$DEVICE" '/.*VDOService$/ {VNAME=substr($1, 0, length($1) - 1)} /[[:space:]]*device:/ { if ($2 ~ DNAME) {print VNAME}}' "$TEMPDIR/vdoconf.yml")
-+	# Check list of devices in VDO configure file for their major:minor
-+	# and match with given $DEVICE devmajor:devminor
-+	for i in $(awk '/.*device:/ {print $2}' "$TEMPDIR/vdoconf.yml") ; do
-+		local DEV
-+		DEV=$("$READLINK" $READLINK_E "$i") || continue
-+		STAT=$(stat --format "MAJOR=\$((0x%t)) MINOR=\$((0x%T))" "$DEV" 2>/dev/null) || continue
-+		eval "$STAT"
-+		test "$MAJOR" = "$DEVMAJOR" && test "$MINOR" = "$DEVMINOR" && {
-+			test -z "$FOUND" || error "VDO configuration contains duplicate entries $FOUND and $i"
-+			FOUND=$i
-+		}
-+	done
-+
-+	test -n "$FOUND" || error "Can't find matching device in vdo configuration file."
-+	verbose "Found matching device $FOUND  $MAJOR:$MINOR"
-+
-+	VDONAME=$(awk -v DNAME="$FOUND" '/.*VDOService$/ {VNAME=substr($1, 0, length($1) - 1)} /[[:space:]]*device:/ { if ($2 ~ DNAME) {print VNAME}}' "$TEMPDIR/vdoconf.yml")
- 	TRVDONAME=$(echo "$VDONAME" | tr '-' '_')
- 
- 	# When VDO volume is 'active', check it's not mounted/being used
--	eval "$(dmsetup info -c -o open  "$VDONAME" --noheadings --nameprefixes || true)"
--	test "${DM_OPEN:-0}" -eq 0 || error "Cannot converted VDO volume \"$VDONAME\" which is in use!"
-+	DM_OPEN="$("$DMSETUP" info -c -o open  "$VDONAME" --noheadings --nameprefixes 2>/dev/null || true)"
-+	case "$DM_OPEN" in
-+	Device*) ;; # no devices
-+	*) 	eval "$DM_OPEN"
-+		test "${DM_OPEN:-0}" -eq 0 || error "Cannot converted VDO volume \"$VDONAME\" which is in use!"
-+		;;
-+	esac
- 
- 	#parse_yaml_ "$TEMPDIR/vdoconf.yml" _
- 	eval "$(parse_yaml_ "$TEMPDIR/vdoconf.yml" _ | grep "$TRVDONAME" | sed -e "s/_config_vdos_$TRVDONAME/vdo/g")"
-@@ -263,8 +298,7 @@ convert2lvm_() {
- 	vdo_logicalSize=$(get_kb_size_with_unit_ "$vdo_logicalSize")
- 	vdo_physicalSize=$(get_kb_size_with_unit_ "$vdo_physicalSize")
- 
--	verbose "Going to convert physical sized VDO device $vdo_physicalSize KiB."
--	verbose "With logical volume of size $vdo_logicalSize KiB."
-+	verbose "Converted VDO device has logical/physical size $vdo_logicalSize/$vdo_physicalSize KiB."
- 
- 	PARAMS=$(cat <<EOF
- allocation {
-@@ -313,7 +347,7 @@ EOF
- 
- 		pvfree=$(( pvfree / 1024 - 2048 ))	# to KiB
- 	else
--		pvfree=$("$LVM" lvs -o size --units b --nosuffix --noheadings "$VGNAME/$LVNAME")
-+		pvfree=$("$LVM" lvs -o size --units b --nosuffix --noheadings "$DM_VG_NAME/$DM_LV_NAME")
- 		pvfree=$(( pvfree / 1024 ))		# to KiB
- 	fi
- 
-@@ -334,11 +368,11 @@ EOF
- 		vg_extent_size=$(( vg_extent_size / 1024 ))
- 
- 		test "$vg_extent_size" -le "$EXTENTSZ" || {
--			error "Please vgchange extent_size to at most $EXTENTSZ KiB or extend and align virtual size on $vg_extent_size KiB."
-+			error "Please vgchange extent_size to at most $EXTENTSZ KiB or extend and align virtual size of VDO device on $vg_extent_size KiB."
- 		}
- 		verbose "Renaming existing LV to be used as _vdata volume for VDO pool LV."
--		dry "$LVM" lvrename $YES $VERB "$VGNAME/$LVNAME" "$VGNAME/${LVNAME}_vpool" || {
--			error "Rename of LV \"$VGNAME/$LVNAME\" failed, while VDO header has been already moved!"
-+		dry "$LVM" lvrename $YES $VERB "$VGNAME/$DM_LV_NAME" "$VGNAME/${LVNAME}_vpool" || {
-+			error "Rename of LV \"$VGNAME/$DM_LV_NAME\" failed, while VDO header has been already moved!"
- 		}
- 	fi
- 
-@@ -372,5 +406,7 @@ do
- 	shift
- done
- 
-+test -n "$DEVICENAME" || error "Device name is not specified. (see: $TOOL --help)"
-+
- # do conversion
- convert2lvm_ "$DEVICENAME"
-diff --git a/test/shell/vdo-convert.sh b/test/shell/vdo-convert.sh
-index 2d16c97..493f415 100644
---- a/test/shell/vdo-convert.sh
-+++ b/test/shell/vdo-convert.sh
-@@ -61,22 +61,36 @@ lvm_import_vdo --dry-run -y -v --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
- 
- lvm_import_vdo -y --name $lv1 "$DM_DEV_DIR/$vg/$lv1"
- 
--# ATM needed - since we do not call 'vdo convert' in this case
--vdo remove $VDOCONF --force --name "$VDONAME" || true
-+# ensure VDO device is not left in config file
-+vdo remove $VDOCONF --force --name "$VDONAME" 2>/dev/null || true
-+
-+lvremove -f $vg
-+
-+
-+# Test user can specify different VDO LV name (so the original LV is renamed)
-+lvcreate -y -L5G -n $lv1 $vg
-+
-+vdo create $VDOCONF --name "$VDONAME" --device="$DM_DEV_DIR/$vg/$lv1" --vdoLogicalSize=10G
-+
-+lvm_import_vdo -y --name $vg/$lv2 "$DM_DEV_DIR/$vg/$lv1"
-+
-+check lv_exists $vg $lv2
-+check lv_not_exists $vg $lv1
- 
- vgremove -f $vg
- 
-+# ensure VDO device is not left in config file
-+vdo remove $VDOCONF --force --name "$VDONAME" 2>/dev/null || true
-+
- aux wipefs_a "$dev1"
- 
- # prepare 'unused' $vg2
- vgcreate $vg2 "$dev2"
- 
- #
--# Check conversion of VDO volume on  non-LV device
-+# Check conversion of VDO volume on non-LV device and with >2T size
- #
--vdo create $VDOCONF --name "$VDONAME" --device="$dev1" --vdoLogicalSize=31G
--
--mkfs -E nodiscard "$DM_DEV_DIR/mapper/$VDONAME"
-+vdo create $VDOCONF --name "$VDONAME" --device="$dev1" --vdoLogicalSize=3T
- 
- # Fail with an already existing volume group $vg2
- not lvm_import_vdo --dry-run -y -v --name $vg2/$lv1 "$dev1" |& tee err
-@@ -87,7 +101,7 @@ vdo stop $VDOCONF --name "$VDONAME"
- 
- lvm_import_vdo -y -v --name $vg/$lv1 "$dev1"
- 
--fsck -n "$DM_DEV_DIR/$vg/$lv1"
-+check lv_field $vg/$lv1 size "3.00t"
- 
- vgremove -f $vg
- 
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-lvm_import_vdo-fix-max_discard-size.patch b/SOURCES/lvm2-2_03_14-vdo-lvm_import_vdo-fix-max_discard-size.patch
deleted file mode 100644
index 0265448..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-lvm_import_vdo-fix-max_discard-size.patch
+++ /dev/null
@@ -1,28 +0,0 @@
-From 60eb37394b536e3b969496611ff4b59b71123476 Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Mon, 6 Sep 2021 14:57:43 +0200
-Subject: [PATCH 2/5] vdo: lvm_import_vdo fix max_discard size
-
-Use correct 4K units in lvm2 for max_discard VDO option.
-
-(cherry picked from commit 8d5b7de54f21ce5e34d533599f9d5a42f2977cd5)
----
- scripts/lvm_import_vdo.sh | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/scripts/lvm_import_vdo.sh b/scripts/lvm_import_vdo.sh
-index bc73306..f8dd71f 100755
---- a/scripts/lvm_import_vdo.sh
-+++ b/scripts/lvm_import_vdo.sh
-@@ -320,7 +320,7 @@ allocation {
- 	vdo_logical_threads = $vdo_logicalThreads
- 	vdo_physical_threads = $vdo_physicalThreads
- 	vdo_write_policy = $vdo_writePolicy
--	vdo_max_discard = $(( $(get_kb_size_with_unit_ "$vdo_maxDiscardSize") * 1024 ))
-+	vdo_max_discard = $(( $(get_kb_size_with_unit_ "$vdo_maxDiscardSize") / 4 ))
- 	vdo_pool_header_size = 0
- }
- EOF
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-lvm_import_vdo-script-needs-to-continue-when-vgn.patch b/SOURCES/lvm2-2_03_14-vdo-lvm_import_vdo-script-needs-to-continue-when-vgn.patch
deleted file mode 100644
index 02bd359..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-lvm_import_vdo-script-needs-to-continue-when-vgn.patch
+++ /dev/null
@@ -1,29 +0,0 @@
-From 4cf3e8bd846a171b4b945f289bf0c6f9c7b5864c Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Thu, 9 Sep 2021 18:10:13 +0200
-Subject: [PATCH 3/5] vdo: lvm_import_vdo script needs to continue when vgname
- does not exist
-
-When the script cannot find vgname - it needs to continue to run.
-
-(cherry picked from commit 9db4ddabc1cf912dee30e0e6293767f01c976a4a)
----
- scripts/lvm_import_vdo.sh | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/scripts/lvm_import_vdo.sh b/scripts/lvm_import_vdo.sh
-index 70904f7..e5b30d8 100755
---- a/scripts/lvm_import_vdo.sh
-+++ b/scripts/lvm_import_vdo.sh
-@@ -262,7 +262,7 @@ convert2lvm_() {
- 			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ] ; then
- 				VGNAME=${DEFAULT_NAME%/*}
- 				# Find largest matching VG name to our 'default' vgname
--				LASTVGNAME=$(LC_ALL=C "$LVM" vgs -oname -O-name --noheadings -S name=~${VGNAME} | grep -E "$VGNAME[0-9]? ?" | head -1)
-+				LASTVGNAME=$(LC_ALL=C "$LVM" vgs -oname -O-name --noheadings -S name=~${VGNAME} | grep -E "$VGNAME[0-9]? ?" | head -1 || true)
- 				if test -n "$LASTVGNAME" ; then
- 					LASTVGNAME=${LASTVGNAME#*${VGNAME}}
- 					# If the number is becoming too high, try some random number
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-man-page-updates.patch b/SOURCES/lvm2-2_03_14-vdo-man-page-updates.patch
deleted file mode 100644
index 03ca40a..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-man-page-updates.patch
+++ /dev/null
@@ -1,27 +0,0 @@
-From 073cdd0ba8c39a0330e73773c92d78546d06e687 Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Fri, 10 Sep 2021 01:15:01 +0200
-Subject: [PATCH 4/5] vdo: man page updates
-
-(cherry picked from commit 812653d59806439379d80bb8124f6962ae42d46a)
----
- man/lvm_import_vdo.8_main | 3 +++
- 1 file changed, 3 insertions(+)
-
-diff --git a/man/lvm_import_vdo.8_main b/man/lvm_import_vdo.8_main
-index ee817a0..c6cb5c3 100644
---- a/man/lvm_import_vdo.8_main
-+++ b/man/lvm_import_vdo.8_main
-@@ -45,6 +45,9 @@ Specifies the name of converted VDO LV. When the name is not specified,
- some automatic name is selected. In case the converted VDO volume is
- already using LV a backend device, the name of this LV is used for VDO LV.
- In this case also the of volume group must stay same.
-+Automatic name may change between releases and currently selects
-+"vdolv" as LV name and VG name is selected from sequence
-+"vdovg", "vdovg1", ...
- .
- .TP
- .BR -v | --verbose
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-more-lvm_import_vdo-fixes.patch b/SOURCES/lvm2-2_03_14-vdo-more-lvm_import_vdo-fixes.patch
deleted file mode 100644
index fb70af2..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-more-lvm_import_vdo-fixes.patch
+++ /dev/null
@@ -1,185 +0,0 @@
-From 6621116b61f4c9ee53166a994be2ef7d80a3c346 Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Mon, 6 Sep 2021 15:06:32 +0200
-Subject: [PATCH 4/5] vdo: more lvm_import_vdo fixes
-
-Do not call 'dmsetup info' for non-dm devices.
-
-Better handling for VGNAME and LVNAME - so when convering LV as
-backend device automatically recognize it and reuse LV name for VDOLV.
-
-Add prompt for final confirmation before actual conversion is started
-(once confirmed, lvm2 commands no longer prompts to avoid leaving
-conversion in the middle of its process.)
-
-(cherry picked from commit 89595a366554191c3df1a18e1f82b79c450a21ad)
----
- scripts/lvm_import_vdo.sh | 48 ++++++++++++++++++++++++++++++++++------
- test/shell/vdo-convert.sh | 56 +++++++++++++++++++++++++++++++++++++++++++++++
- 2 files changed, 97 insertions(+), 7 deletions(-)
-
-diff --git a/scripts/lvm_import_vdo.sh b/scripts/lvm_import_vdo.sh
-index dec32bc..70904f7 100755
---- a/scripts/lvm_import_vdo.sh
-+++ b/scripts/lvm_import_vdo.sh
-@@ -50,6 +50,7 @@ DM_DEV_DIR="${DM_DEV_DIR:-/dev}"
- DEVICENAME=""
- DEVMAJOR=0
- DEVMINOR=0
-+PROMPTING=""
- 
- DRY=0
- VERB=""
-@@ -57,7 +58,8 @@ FORCE=""
- YES=""
- 
- # default name for converted VG and its VDO LV
--NAME="vdovg/vdolvol"
-+DEFAULT_NAME="vdovg/vdolvol"
-+NAME=""
- 
- # help message
- tool_usage() {
-@@ -100,6 +102,7 @@ dry() {
- cleanup() {
- 	trap '' 2
- 
-+	test -z "$PROMPTING" || echo "No"
- 	rm -rf "$TEMPDIR"
- 	# error exit status for break
- 	exit "${1:-1}"
-@@ -175,7 +178,9 @@ detect_lv_() {
- 		;;
- 	esac
- 
--	DEV="$("$DMSETUP" info -c -j "$DEVMAJOR" -m "$DEVMINOR" -o uuid,name --noheadings --nameprefixes --separator ' ' 2>/dev/null)"
-+	test "$DEVMAJOR" != "$(grep device-mapper /proc/devices | cut -f1 -d' ')" && return
-+
-+	DEV="$("$DMSETUP" info -c -j "$DEVMAJOR" -m "$DEVMINOR" -o uuid,name --noheadings --nameprefixes --separator ' ')"
- 	case "$DEV" in
- 	Device*)  ;; # no devices
- 	*)	eval "$DEV" ;;
-@@ -244,15 +249,31 @@ convert2lvm_() {
- 	detect_lv_ "$DEVICE"
- 	case "$DM_UUID" in
- 		LVM-*)	eval "$("$DMSETUP" splitname --nameprefixes --noheadings --separator ' ' "$DM_NAME")"
--			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ]  ; then
-+			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ] ; then
- 				VGNAME=$DM_VG_NAME
--				LVNAME=$DM_LV_NAME
-+				verbose "Using existing volume group name $VGNAME."
-+				test -n "$LVNAME" || LVNAME=$DM_LV_NAME
- 			elif test "$VGNAME" != "$DM_VG_NAME" ; then
--				error "Volume group name \"$VGNAME\" does not match name \"$DM_VG_NAME\" for device \"$DEVICE\"."
-+				error "Volume group name \"$VGNAME\" does not match name \"$DM_VG_NAME\" for VDO device \"$DEVICE\"."
- 			fi
- 			;;
--		*) IS_LV=0
--			# Check $VGNANE does not already exists
-+		*)	IS_LV=0
-+			# Check if we need to generate unused $VGNANE
-+			if [ -z "$VGNAME" ] || [ "$VGNAME" = "$LVNAME" ] ; then
-+				VGNAME=${DEFAULT_NAME%/*}
-+				# Find largest matching VG name to our 'default' vgname
-+				LASTVGNAME=$(LC_ALL=C "$LVM" vgs -oname -O-name --noheadings -S name=~${VGNAME} | grep -E "$VGNAME[0-9]? ?" | head -1)
-+				if test -n "$LASTVGNAME" ; then
-+					LASTVGNAME=${LASTVGNAME#*${VGNAME}}
-+					# If the number is becoming too high, try some random number
-+					test "$LASTVGNAME" -gt 99999999 2>/dev/null && LASTVGNAME=$RANDOM
-+					# Generate new unused VG name
-+					VGNAME="${VGNAME}$(( ${LASTVGNAME} + 1 ))"
-+					verbose "Selected unused volume group name $VGNAME."
-+				fi
-+			fi
-+			# New VG is created, LV name should be always unused.
-+			test -n "$LVNAME" || LVNAME=${DEFAULT_NAME#*/}
- 			"$LVM" vgs "$VGNAME" >/dev/null 2>&1 && error "Cannot use already existing volume group name \"$VGNAME\"."
- 			;;
- 	esac
-@@ -328,6 +349,19 @@ EOF
- )
- 	verbose "VDO conversion paramaters: $PARAMS"
- 
-+	# If user has not provided '--yes', prompt before conversion
-+	if test -z "$YES" ; then
-+		PROMPTING=yes
-+		echo -n "Convert VDO device \"$DEVICE\" to VDO LV \"$VGNAME/$LVNAME\"? [y|N]: "
-+		read -n 1 -s ANSWER
-+		case "${ANSWER:0:1}" in
-+			y|Y )  echo "Yes" ;;
-+			* )    echo "No" ; PROMPTING=""; exit ;;
-+		esac
-+		PROMPTING=""
-+		YES="-y" # From now, now prompting
-+	fi
-+
- 	verbose "Stopping VDO volume."
- 	dry "$VDO" stop $VDOCONF --name "$VDONAME"
- 
-diff --git a/test/shell/vdo-convert.sh b/test/shell/vdo-convert.sh
-index 493f415..632f86a 100644
---- a/test/shell/vdo-convert.sh
-+++ b/test/shell/vdo-convert.sh
-@@ -122,3 +122,59 @@ fsck -n "$DM_DEV_DIR/$vg1/$lv2"
- 
- vgremove -f $vg1
- 
-+aux teardown_devs
-+
-+
-+# Check with some real non-DM device from system
-+# this needs to dropping DM_DEV_DIR
-+
-+aux prepare_loop 60000 || skip
-+
-+test -f LOOP
-+LOOP=$(< LOOP)
-+
-+aux extend_filter "a|$LOOP|"
-+aux extend_devices "$LOOP"
-+
-+#
-+# Unfortunatelly generates this in syslog:
-+#
-+# vdo-start-by-dev@loop0.service: Main process exited, code=exited, status=1/FAILURE
-+# vdo-start-by-dev@loop0.service: Failed with result 'exit-code'.
-+# Failed to start Start VDO volume backed by loop0.
-+#
-+# TODO:  Could be handled by:
-+#
-+# systemctl mask vdo-start-by-dev@
-+# systemctl unmask vdo-start-by-dev@
-+#
-+# automate...
-+#
-+vdo create $VDOCONF --name "$VDONAME" --device="$LOOP" --vdoLogicalSize=23G \
-+	--blockMapCacheSize 192 \
-+	--blockMapPeriod 2048 \
-+	--emulate512 disabled \
-+	--indexMem 0.5 \
-+	--maxDiscardSize 10 \
-+	--sparseIndex disabled \
-+	--vdoAckThreads 2 \
-+	--vdoBioRotationInterval 8 \
-+	--vdoBioThreads 2 \
-+	--vdoCpuThreads 5 \
-+	--vdoHashZoneThreads 3 \
-+	--vdoLogicalThreads 3 \
-+	--writePolicy async-unsafe
-+
-+# Get VDO table line
-+dmsetup table "$VDONAME" | tr " " "\n" | sed -e '5,6d' -e '12d' | tee vdo-orig
-+
-+DM_DEV_DIR= lvm_import_vdo -y --name $vg/$lv "$LOOP"
-+lvs -a $vg
-+
-+dmsetup table "$vg-${lv}_vpool-vpool" | tr " " "\n" | sed -e '5,6d' -e '12d' | tee new-vdo-lv
-+
-+# Check there is a match between VDO and LV managed volume
-+# (when differentiating parameters are deleted first)
-+diff -u vdo-orig new-vdo-lv || die "Found mismatching VDO table lines!"
-+
-+check lv_field $vg/$lv size "23.00g"
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-prompt-with-no-return-failure.patch b/SOURCES/lvm2-2_03_14-vdo-prompt-with-no-return-failure.patch
deleted file mode 100644
index 4642667..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-prompt-with-no-return-failure.patch
+++ /dev/null
@@ -1,28 +0,0 @@
-From f3f99d45b89d415528e21a66f94ab4576f95ba56 Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Fri, 10 Sep 2021 22:39:23 +0200
-Subject: [PATCH 5/5] vdo: prompt with no return failure
-
-Exit 1  (failure) when prompt for conversion is answered as 'No'.
-
-(cherry picked from commit 3b24c0fe4e197383101eae53b14f19586cf2eda1)
----
- scripts/lvm_import_vdo.sh | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/scripts/lvm_import_vdo.sh b/scripts/lvm_import_vdo.sh
-index e5b30d8..06a043c 100755
---- a/scripts/lvm_import_vdo.sh
-+++ b/scripts/lvm_import_vdo.sh
-@@ -356,7 +356,7 @@ EOF
- 		read -n 1 -s ANSWER
- 		case "${ANSWER:0:1}" in
- 			y|Y )  echo "Yes" ;;
--			* )    echo "No" ; PROMPTING=""; exit ;;
-+			* )    echo "No" ; PROMPTING=""; exit 1 ;;
- 		esac
- 		PROMPTING=""
- 		YES="-y" # From now, now prompting
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-2_03_14-vdo-read-new-sysfs-path.patch b/SOURCES/lvm2-2_03_14-vdo-read-new-sysfs-path.patch
deleted file mode 100644
index c2d5f72..0000000
--- a/SOURCES/lvm2-2_03_14-vdo-read-new-sysfs-path.patch
+++ /dev/null
@@ -1,184 +0,0 @@
-From 1c6992d37eff5af7134a11b662eacc1bab538ac2 Mon Sep 17 00:00:00 2001
-From: Zdenek Kabelac <zkabelac@redhat.com>
-Date: Thu, 9 Sep 2021 14:59:38 +0200
-Subject: [PATCH 1/5] vdo: read new sysfs path
-
-New versions of kvdo module exposes statistics at new location:
-/sys/block/dm-XXX/vdo/statistics/...
-
-Enhance lvm2 to access this location first.
-Also if the statistic info is missing - make it 'debug' level info,
-so it is not failing 'lvs' command.
-
-(cherry picked from commit e6f735d411e5911de186a610932c9bb9638275eb)
-
-Conflicts:
-	WHATS_NEW
----
- WHATS_NEW                        |  1 +
- lib/activate/dev_manager.c       |  7 +++---
- lib/metadata/metadata-exported.h |  3 ++-
- lib/metadata/vdo_manip.c         | 46 ++++++++++++++++++++++------------------
- 4 files changed, 32 insertions(+), 25 deletions(-)
-
-diff --git a/WHATS_NEW b/WHATS_NEW
-index b751009..c5a5ca5 100644
---- a/WHATS_NEW
-+++ b/WHATS_NEW
-@@ -1,5 +1,6 @@
- Version 2.03.14 - 
- ==================================
-+  Support newer location for VDO statistics.
-   Improve lvm_import_vdo script.
-   Support VDO LV with lvcreate -ky.
-   Fix lvconvert for VDO LV bigger then 2T.
-diff --git a/lib/activate/dev_manager.c b/lib/activate/dev_manager.c
-index c4a6739..0d954d1 100644
---- a/lib/activate/dev_manager.c
-+++ b/lib/activate/dev_manager.c
-@@ -157,6 +157,7 @@ out:
- 
- static int _get_segment_status_from_target_params(const char *target_name,
- 						  const char *params,
-+						  const struct dm_info *dminfo,
- 						  struct lv_seg_status *seg_status)
- {
- 	const struct lv_segment *seg = seg_status->seg;
-@@ -216,7 +217,7 @@ static int _get_segment_status_from_target_params(const char *target_name,
- 			return_0;
- 		seg_status->type = SEG_STATUS_SNAPSHOT;
- 	} else if (segtype_is_vdo_pool(segtype)) {
--		if (!parse_vdo_pool_status(seg_status->mem, seg->lv, params, &seg_status->vdo_pool))
-+		if (!parse_vdo_pool_status(seg_status->mem, seg->lv, params, dminfo, &seg_status->vdo_pool))
- 			return_0;
- 		seg_status->type = SEG_STATUS_VDO_POOL;
- 	} else if (segtype_is_writecache(segtype)) {
-@@ -320,7 +321,7 @@ static int _info_run(const char *dlid, struct dm_info *dminfo,
- 		} while (target);
- 
- 		if (!target_name ||
--		    !_get_segment_status_from_target_params(target_name, target_params, seg_status))
-+		    !_get_segment_status_from_target_params(target_name, target_params, dminfo, seg_status))
- 			stack;
- 	}
- 
-@@ -1886,7 +1887,7 @@ int dev_manager_vdo_pool_status(struct dev_manager *dm,
- 		goto out;
- 	}
- 
--	if (!parse_vdo_pool_status(dm->mem, lv, params, *status))
-+	if (!parse_vdo_pool_status(dm->mem, lv, params, &info, *status))
- 		goto_out;
- 
- 	(*status)->mem = dm->mem;
-diff --git a/lib/metadata/metadata-exported.h b/lib/metadata/metadata-exported.h
-index adbbe76..7c21b4d 100644
---- a/lib/metadata/metadata-exported.h
-+++ b/lib/metadata/metadata-exported.h
-@@ -1364,7 +1364,8 @@ const char *get_vdo_write_policy_name(enum dm_vdo_write_policy policy);
- uint64_t get_vdo_pool_virtual_size(const struct lv_segment *vdo_pool_seg);
- int update_vdo_pool_virtual_size(struct lv_segment *vdo_pool_seg);
- int parse_vdo_pool_status(struct dm_pool *mem, const struct logical_volume *vdo_pool_lv,
--			  const char *params, struct lv_status_vdo *status);
-+			  const char *params, const struct dm_info *dminfo,
-+			  struct lv_status_vdo *status);
- struct logical_volume *convert_vdo_pool_lv(struct logical_volume *data_lv,
- 					   const struct dm_vdo_target_params *vtp,
- 					   uint32_t *virtual_extents,
-diff --git a/lib/metadata/vdo_manip.c b/lib/metadata/vdo_manip.c
-index 3f2de1a..2917f29 100644
---- a/lib/metadata/vdo_manip.c
-+++ b/lib/metadata/vdo_manip.c
-@@ -123,48 +123,56 @@ int update_vdo_pool_virtual_size(struct lv_segment *vdo_pool_seg)
- 	return 1;
- }
- 
--static int _sysfs_get_kvdo_value(const char *dm_name, const char *vdo_param, uint64_t *value)
-+static int _sysfs_get_kvdo_value(const char *dm_name, const struct dm_info *dminfo,
-+				 const char *vdo_param, uint64_t *value)
- {
- 	char path[PATH_MAX];
- 	char temp[64];
- 	int fd, size, r = 0;
- 
--	if (dm_snprintf(path, sizeof(path), "%skvdo/%s/%s",
--			dm_sysfs_dir(), dm_name, vdo_param) < 0) {
--		log_error("Failed to build kmod path.");
-+	if (dm_snprintf(path, sizeof(path), "%s/block/dm-%d/vdo/%s",
-+			dm_sysfs_dir(), dminfo->minor, vdo_param) < 0) {
-+		log_debug("Failed to build kvdo path.");
- 		return 0;
- 	}
- 
- 	if ((fd = open(path, O_RDONLY)) < 0) {
--		if (errno != ENOENT)
--			log_sys_error("open", path);
--		else
-+		/* try with older location */
-+		if (dm_snprintf(path, sizeof(path), "%skvdo/%s/%s",
-+				dm_sysfs_dir(), dm_name, vdo_param) < 0) {
-+			log_debug("Failed to build kvdo path.");
-+			return 0;
-+		}
-+
-+		if ((fd = open(path, O_RDONLY)) < 0) {
- 			log_sys_debug("open", path);
--		goto bad;
-+			goto bad;
-+		}
- 	}
- 
- 	if ((size = read(fd, temp, sizeof(temp) - 1)) < 0) {
--		log_sys_error("read", path);
-+		log_sys_debug("read", path);
- 		goto bad;
- 	}
- 	temp[size] = 0;
- 	errno = 0;
- 	*value = strtoll(temp, NULL, 0);
- 	if (errno) {
--		log_sys_error("strtool", path);
-+		log_sys_debug("strtool", path);
- 		goto bad;
- 	}
- 
- 	r = 1;
- bad:
- 	if (fd >= 0 && close(fd))
--		log_sys_error("close", path);
-+		log_sys_debug("close", path);
- 
- 	return r;
- }
- 
- int parse_vdo_pool_status(struct dm_pool *mem, const struct logical_volume *vdo_pool_lv,
--			  const char *params, struct lv_status_vdo *status)
-+			  const char *params, const struct dm_info *dminfo,
-+			  struct lv_status_vdo *status)
- {
- 	struct dm_vdo_status_parse_result result;
- 	char *dm_name;
-@@ -188,15 +196,11 @@ int parse_vdo_pool_status(struct dm_pool *mem, const struct logical_volume *vdo_
- 
- 	status->vdo = result.status;
- 
--	if (result.status->operating_mode == DM_VDO_MODE_NORMAL) {
--		if (!_sysfs_get_kvdo_value(dm_name, "statistics/data_blocks_used",
--					   &status->data_blocks_used))
--			return_0;
--
--		if (!_sysfs_get_kvdo_value(dm_name, "statistics/logical_blocks_used",
--					   &status->logical_blocks_used))
--			return_0;
--
-+	if ((result.status->operating_mode == DM_VDO_MODE_NORMAL) &&
-+	    _sysfs_get_kvdo_value(dm_name, dminfo, "statistics/data_blocks_used",
-+				  &status->data_blocks_used) &&
-+	    _sysfs_get_kvdo_value(dm_name, dminfo, "statistics/logical_blocks_used",
-+				  &status->logical_blocks_used)) {
- 		status->usage = dm_make_percent(result.status->used_blocks,
- 						result.status->total_blocks);
- 		status->saving = dm_make_percent(status->logical_blocks_used - status->data_blocks_used,
--- 
-1.8.3.1
-
diff --git a/SOURCES/lvm2-make-generate.patch b/SOURCES/lvm2-make-generate.patch
deleted file mode 100644
index 0b37216..0000000
--- a/SOURCES/lvm2-make-generate.patch
+++ /dev/null
@@ -1,146 +0,0 @@
- man/lvconvert.8_pregen  |  2 +-
- man/lvmdevices.8_pregen | 79 ++++++++++++++++++++++++++++++++++++++++---------
- 2 files changed, 66 insertions(+), 15 deletions(-)
-
-diff --git a/man/lvconvert.8_pregen b/man/lvconvert.8_pregen
-index d733ab6..4fafe5d 100644
---- a/man/lvconvert.8_pregen
-+++ b/man/lvconvert.8_pregen
-@@ -670,7 +670,7 @@ Convert LV to type thin-pool.
- .RE
- .P
- .RS 4
--LV1 types: linear striped cache raid error zero
-+LV1 types: linear striped cache raid error zero writecache
- .RE
- .P
- \(em
-diff --git a/man/lvmdevices.8_pregen b/man/lvmdevices.8_pregen
-index 267ce96..fa85362 100644
---- a/man/lvmdevices.8_pregen
-+++ b/man/lvmdevices.8_pregen
-@@ -28,6 +28,8 @@ lvmdevices \(em Manage the devices file
- .br
-     \fB--delpvid\fP \fIString\fP
- .br
-+    \fB--deviceidtype\fP \fIString\fP
-+.br
-     \fB--devices\fP \fIPV\fP
- .br
-     \fB--devicesfile\fP \fIString\fP
-@@ -70,18 +72,18 @@ remove it from the devices file with lvmdevices --deldev.  The
- vgimportdevices(8) command adds all PVs from a VG to the devices file,
- and updates the VG metadata to include device IDs of the PVs.
- .P
--Commands adding new devices to the devices file necessarily look outside
--the existing devices file to find the devices to add.  pvcreate, vgcreate,
--and vgextend also look outside the devices file to create new PVs and add
--them to the devices file.
-+Commands that add new devices to the devices file necessarily look outside
-+the existing devices file to find the devices being added.  pvcreate,
-+vgcreate, and vgextend also look outside the devices file to create new
-+PVs and add those PVs to the devices file.
- .P
- LVM records devices in the devices file using hardware-specific IDs, such
- as the WWID, and attempts to use subsystem-specific IDs for virtual device
--types (which also aim to be as unique and stable as possible.)
--These device IDs are also written in the VG metadata.  When no hardware or
-+types (which also aim to be as unique and stable as possible.) These
-+device IDs are also written in the VG metadata.  When no hardware or
- virtual ID is available, lvm falls back using the unstable device name as
--the device ID.  When devnames are used, lvm performs extra scanning to
--find devices if their devname changes, e.g. after reboot.
-+the device ID.  When devnames are used as IDs, lvm performs extra scanning
-+to find devices if their devname changes, e.g. after reboot.
- .P
- When proper device IDs are used, an lvm command will not look at devices
- outside the devices file, but when devnames are used as a fallback, lvm
-@@ -95,12 +97,13 @@ overriding the devices file.  The listed devices act as a sort of devices
- file in terms of limiting which devices lvm will see and use.  Devices
- that are not listed will appear to be missing to the lvm command.
- .P
--Multiple devices files can be kept in \fI#DEFAULT_SYS_DIR#/devices\fP, which allows lvm
--to be used with different sets of devices, e.g. system devices do not need
--to be exposed to a specific application, and the application can use lvm on
--its own devices that are not exposed to the system.  The option
----devicesfile <filename> is used to select the devices file to use with the
--command.  Without the option set, the default system devices file is used.
-+Multiple devices files can be kept \fI#DEFAULT_SYS_DIR#/devices\fP, which
-+allows lvm to be used with different sets of devices.  For example, system
-+devices do not need to be exposed to a specific application, and the
-+application can use lvm on its own devices that are not exposed to the
-+system.  The option --devicesfile <filename> is used to select the devices
-+file to use with the command.  Without the option set, the default system
-+devices file is used.
- .P
- Setting --devicesfile "" causes lvm to not use a devices file.
- .P
-@@ -120,6 +123,45 @@ if it does not yet exist.
- .P
- It is recommended to use lvm commands to make changes to the devices file to
- ensure proper updates.
-+.P
-+The device ID and device ID type are included in the VG metadata and can
-+be reported with pvs -o deviceid,deviceidtype.  (Note that the lvmdevices
-+command does not update VG metadata, but subsequent lvm commands modifying
-+the metadata will include the device ID.)
-+.P
-+Possible device ID types are:
-+.br
-+.IP \[bu] 2
-+.B sys_wwid
-+uses the wwid reported by sysfs.  This is the first choice for non-virtual
-+devices.
-+.IP \[bu] 2
-+.B sys_serial
-+uses the serial number reported by sysfs.  This is the second choice for
-+non-virtual devices.
-+.IP \[bu] 2
-+.B mpath_uuid
-+is used for dm multipath devices, reported by sysfs.
-+.IP \[bu] 2
-+.B crypt_uuid
-+is used for dm crypt devices, reported by sysfs.
-+.IP \[bu] 2
-+.B md_uuid
-+is used for md devices, reported by sysfs.
-+.B lvmlv_uuid
-+is used if a PV is placed on top of an lvm LV, reported by sysfs.
-+.IP \[bu] 2
-+.B loop_file
-+is used for loop devices, the backing file name repored by sysfs.
-+.IP \[bu] 2
-+.B devname
-+the device name is used if no other type applies.
-+.P
-+
-+The default choice for device ID type can be overriden using lvmdevices
-+--addev --deviceidtype <type>.  If the specified type is available for the
-+device it will be used, otherwise the device will be added using the type
-+that would otherwise be chosen.
- .
- .SH USAGE
- .
-@@ -169,6 +211,8 @@ Add a device to the devices file.
- .br
- .RS 4
- .ad l
-+[    \fB--deviceidtype\fP \fIString\fP ]
-+.br
- [ COMMON_OPTIONS ]
- .ad b
- .RE
-@@ -308,6 +352,13 @@ Remove a device from the devices file.
- Remove a device with the PVID from the devices file.
- .
- .HP
-+\fB--deviceidtype\fP \fIString\fP
-+.br
-+The type of device ID to use for the device.
-+If the specified type is available for the device,
-+then it will override the default type that lvm would use.
-+.
-+.HP
- \fB--devices\fP \fIPV\fP
- .br
- Devices that the command can use. This option can be repeated
diff --git a/SOURCES/lvm2-rhel8.patch b/SOURCES/lvm2-rhel8.patch
index 8af2792..596b317 100644
--- a/SOURCES/lvm2-rhel8.patch
+++ b/SOURCES/lvm2-rhel8.patch
@@ -3,16 +3,16 @@
  2 files changed, 2 insertions(+), 2 deletions(-)
 
 diff --git a/VERSION b/VERSION
-index d9c3e23..2610861 100644
+index 0a36180..57ed15e 100644
 --- a/VERSION
 +++ b/VERSION
 @@ -1 +1 @@
--2.03.12(2) (2021-05-07)
-+2.03.12(2)-RHEL8 (2021-05-19)
+-2.03.14(2) (2021-10-20)
++2.03.14(2)-RHEL8 (2021-10-20)
 diff --git a/VERSION_DM b/VERSION_DM
-index 6105a0f..0991c69 100644
+index 52cb622..bf97bda 100644
 --- a/VERSION_DM
 +++ b/VERSION_DM
 @@ -1 +1 @@
--1.02.177 (2021-05-07)
-+1.02.177-RHEL8 (2021-05-19)
+-1.02.181 (2021-10-20)
++1.02.181-RHEL8 (2021-10-20)
diff --git a/SOURCES/lvm2-set-default-preferred_names.patch b/SOURCES/lvm2-set-default-preferred_names.patch
deleted file mode 100644
index 88912bb..0000000
--- a/SOURCES/lvm2-set-default-preferred_names.patch
+++ /dev/null
@@ -1,33 +0,0 @@
- conf/example.conf.in         | 5 +++--
- lib/config/config_settings.h | 2 +-
- 2 files changed, 4 insertions(+), 3 deletions(-)
-
-diff --git a/conf/example.conf.in b/conf/example.conf.in
-index b4a55ae..aaf73a4 100644
---- a/conf/example.conf.in
-+++ b/conf/example.conf.in
-@@ -121,8 +121,9 @@ devices {
- 	#
- 	# Example
- 	# preferred_names = [ "^/dev/mpath/", "^/dev/mapper/mpath", "^/dev/[hs]d" ]
--	#
--	# This configuration option does not have a default value defined.
-+	# 
-+	# This configuration option has an automatic default value.
-+	# preferred_names = [ "^/dev/mpath/", "^/dev/mapper/mpath", "^/dev/[hs]d" ]
- 
- 	# Configuration option devices/use_devicesfile.
- 	# Enable or disable the use of a devices file.
-diff --git a/lib/config/config_settings.h b/lib/config/config_settings.h
-index d3a42a1..f5dac4d 100644
---- a/lib/config/config_settings.h
-+++ b/lib/config/config_settings.h
-@@ -269,7 +269,7 @@ cfg(devices_hints_CFG, "hints", devices_CFG_SECTION, CFG_DEFAULT_COMMENTED, CFG_
- 	"    Use no hints.\n"
- 	"#\n")
- 
--cfg_array(devices_preferred_names_CFG, "preferred_names", devices_CFG_SECTION, CFG_ALLOW_EMPTY | CFG_DEFAULT_UNDEFINED , CFG_TYPE_STRING, NULL, vsn(1, 2, 19), NULL, 0, NULL,
-+cfg_array(devices_preferred_names_CFG, "preferred_names", devices_CFG_SECTION, CFG_ALLOW_EMPTY | CFG_DEFAULT_COMMENTED, CFG_TYPE_STRING, "#S^/dev/mpath/#S^/dev/mapper/mpath#S^/dev/[hs]d", vsn(1, 2, 19), NULL, 0, NULL,
- 	"Select which path name to display for a block device.\n"
- 	"If multiple path names exist for a block device, and LVM needs to\n"
- 	"display a name for the device, the path names are matched against\n"
diff --git a/SPECS/lvm2.spec b/SPECS/lvm2.spec
index ff07df2..52a8c2a 100644
--- a/SPECS/lvm2.spec
+++ b/SPECS/lvm2.spec
@@ -1,4 +1,4 @@
-%global device_mapper_version 1.02.177
+%global device_mapper_version 1.02.181
 
 %global enable_cache 1
 %global enable_cluster 1
@@ -41,6 +41,15 @@
   %endif
 %endif
 
+%if %{enable_cluster}
+  %global configure_cluster --with-cluster=internal
+  %if %{enable_cmirror}
+    %global configure_cmirror --enable-cmirrord
+  %endif
+%else
+    %global configure_cluster --with-cluster=internal
+%endif
+
 %global from_snapshot 0
 %if 0%{?from_snapshot}
 %global commit 4dc5d4ac7e7a9457ccc46ff04796b347e58bf4da
@@ -55,11 +64,11 @@ Name: lvm2
 %if 0%{?rhel}
 Epoch: %{rhel}
 %endif
-Version: 2.03.12
+Version: 2.03.14
 %if 0%{?from_snapshot}
 Release: 0.1.20210426git%{shortcommit}%{?dist}%{?rel_suffix}
 %else
-Release: 11%{?dist}%{?rel_suffix}
+Release: 3%{?dist}%{?rel_suffix}
 %endif
 License: GPLv2
 URL: http://sourceware.org/lvm2
@@ -69,55 +78,31 @@ Source0: lvm2-%{shortcommit}.tgz
 Source0: ftp://sourceware.org/pub/lvm2/releases/LVM2.%{version}.tgz
 Patch0: lvm2-rhel8.patch
 %endif
-Patch1: lvm2-set-default-preferred_names.patch
-Patch2: lvm2-test-skip-problematic-tests.patch
-# BZ 1961890
-Patch3: lvm2-2_03_13-vdo-fix-preload-of-kvdo.patch
-# BZ 1964622:
-Patch4: lvm2-2_03_13-lvremove-fix-removing-thin-pool-with-writecache-on-d.patch
-# BZ 1957898:
-Patch5: lvm2-2_03_13-enable-command-syntax-for-thin-and-writecache.patch
-# BZ 1872903:
-Patch6: lvm2-2_03_13-writecache-fix-lv_on_pmem.patch
-Patch7: lvm2-2_03_13-writecache-don-t-pvmove-device-used-by-writecache.patch
-# BZ 1957898:
-Patch8: lvm2-2_03_13-lvconvert-allow-writecache-with-other-thinpool-comma.patch
-# BZ 1922312:
-Patch9: lvm2-2_03_13-devices-don-t-use-deleted-loop-backing-file-for-devi.patch
-Patch10: lvm2-2_03_13-lvmdevices-add-deviceidtype-option.patch
-# BZ 1974901:
-Patch11: lvm2-2_03_13-device_id-handle-scsi_debug-wwid.patch
-# BZ 1930261:
-Patch12: lvm2-2_03_13-lvconvert-fix-vdo-virtual-size-when-specified.patch
-Patch13: lvm2-2_03_13-vdo-rename-variable-vdo_pool_zero.patch
-Patch14: lvm2-2_03_13-vdo-support-vdo_pool_header_size.patch
-Patch15: lvm2-2_03_13-vdo-add-vdoimport-support.patch
-Patch16: lvm2-2_03_13-man-vdoimport-page.patch
-Patch17: lvm2-make-generate.patch
-# BZ 1967744: 
-Patch18: lvm2-2_03_13-thin-fix-component-detection-of-external-origin.patch
-# BZ 1899263:
-Patch19: lvm2-2_03_13-vgremove-remove-forgotten-pmspare.patch
-Patch20: lvm2-2_03_13-vgsplit-add-support-for-option-poolmetadataspare.patch
-Patch21: lvm2-2_03_13-test.patch
-Patch22: lvm2-2_03_13-vgmerge-remove-one-of-merge-pmspare-LVs.patch
-Patch23: lvm2-2_03_13-vgmerge-support-option-poolmetadataspare.patch
-Patch24: lvm2-2_03_13-tests-extend-vgmerge-testing.patch
-# BZ 1986930:
-Patch25: lvm2-2_03_14-vdo-Rename-vdoimport-to-lvm_import_vdo.patch
-# BZs #1930261 #1986885 #1986915 #1988504 #1989650 #1996227:
-Patch26: lvm2-2_03_14-vdo-fixes.patch
-Patch27: lvm2-2_03_14-vdo-lvm_import_vdo-fix-max_discard-size.patch
-Patch28: lvm2-2_03_14-vdo-better-message-for-missing-device.patch
-Patch29: lvm2-2_03_14-vdo-more-lvm_import_vdo-fixes.patch
-Patch30: lvm2-2_03_14-vdo-fix-conversion-of-large-virtual-sizes.patch
-Patch31: lvm2-2_03_14-vdo-read-new-sysfs-path.patch
-Patch32: lvm2-2_03_14-tests-check-lvm2-parses-vdo-statistics.patch
-Patch33: lvm2-2_03_14-vdo-lvm_import_vdo-script-needs-to-continue-when-vgn.patch
-Patch34: lvm2-2_03_14-vdo-man-page-updates.patch
-Patch35: lvm2-2_03_14-vdo-prompt-with-no-return-failure.patch
-# BZ 2040514:
-Patch36: lvm2-2_03_14-lvchange-fix-lvchange-refresh-failed-for-dm-suspend-.patch
+Patch1: lvm2-test-skip-problematic-tests.patch
+Patch2: 0001-Revert-new-udev-autoactivation.patch
+Patch3: 0002-Revert-pvscan-only-add-device-args-to-dev-cache.patch
+Patch4: 0003-pvscan-fix-messages-from-coverity-changes.patch
+Patch5: 0004-vgimportdevices-skip-lvmlockd-locking.patch
+Patch6: 0005-hints-remove-the-cmd-hints-list.patch
+Patch7: 0006-filter-sysfs-skip-when-device-id-is-set.patch
+Patch8: 0007-lvmdevices-increase-open-file-limit.patch
+Patch9: 0008-filter-sysfs-support-old-kernels-without-sys-dev-blo.patch
+Patch10: 0009-device_id-match-different-dm-device-names.patch
+Patch11: 0010-device_id-fix-search-on-filtered-device.patch
+Patch12: 0011-device_id-searched_devnames-improvements.patch
+Patch13: 0012-tests-pv-ext-flags-work-with-devices-file.patch
+Patch14: 0013-display-ignore-reportformat.patch
+Patch15: 0014-fix-spelling-of-pruning.patch
+Patch16: 0015-man-lvmautoactivation.patch
+#Patch17: 0016-spec-Add-lvmautoactivation-man-page.patch
+Patch18: 0017-tests-devicesfile-devname.sh-drop-mdadm-chunk.patch
+Patch19: 0018-devices-file-don-t-write-in-test-mode.patch
+Patch20: 0019-print-warning-about-unrecognized-journal-option-valu.patch
+Patch21: 0020-device_id-handle-wwid-with-spaces-or-control-charact.patch
+Patch22: 0021-man-add-section-about-static-autoactivation.patch
+Patch23: 0022-lvcreate-include-recent-options.patch
+Patch24: 0023-man-lvmautoactivation-replace-systemctl-with-journal.patch
+Patch25: 0024-make-generate.patch
 
 BuildRequires: gcc
 %if %{enable_testsuite}
@@ -194,7 +179,7 @@ or more physical volumes and creating one or more logical volumes
 %patch14 -p1 -b .backup14
 %patch15 -p1 -b .backup15
 %patch16 -p1 -b .backup16
-%patch17 -p1 -b .backup17
+#%%patch17 -p1 -b .backup17
 %patch18 -p1 -b .backup18
 %patch19 -p1 -b .backup19
 %patch20 -p1 -b .backup20
@@ -203,17 +188,6 @@ or more physical volumes and creating one or more logical volumes
 %patch23 -p1 -b .backup23
 %patch24 -p1 -b .backup24
 %patch25 -p1 -b .backup25
-%patch26 -p1 -b .backup26
-%patch27 -p1 -b .backup27
-%patch28 -p1 -b .backup28
-%patch29 -p1 -b .backup29
-%patch30 -p1 -b .backup30
-%patch31 -p1 -b .backup31
-%patch32 -p1 -b .backup32
-%patch33 -p1 -b .backup33
-%patch34 -p1 -b .backup34
-%patch35 -p1 -b .backup35
-%patch36 -p1 -b .backup36
 
 %build
 %global _default_pid_dir /run
@@ -223,17 +197,7 @@ or more physical volumes and creating one or more logical volumes
 
 %global _udevdir %{_prefix}/lib/udev/rules.d
 
-# FIXME: Dropped in rhel9, do we need to keep this for "compatibility"?
-%if %{enable_cluster}
-  %global configure_cluster --with-cluster=internal
-  %if %{enable_cmirror}
-    %global configure_cmirror --enable-cmirrord
-  %endif
-%else
-    %global configure_cluster --with-cluster=internal
-%endif
-
-%configure\
+%configure \
   --with-default-dm-run-dir=%{_default_dm_run_dir} \
   --with-default-run-dir=%{_default_run_dir} \
   --with-default-pid-dir=%{_default_pid_dir} \
@@ -280,7 +244,6 @@ or more physical volumes and creating one or more logical volumes
 %if %{enable_vdo}
   --with-vdo=internal --with-vdo-format=%{_bindir}/vdoformat \
 %endif
-  %{?configure_integrity} \
 %if %{enable_integrity}
   --with-integrity=internal \
 %endif
@@ -400,6 +363,7 @@ systemctl start lvm2-lvmpolld.socket >/dev/null 2>&1 || :
 %{_sbindir}/vgscan
 %{_sbindir}/vgsplit
 %{_mandir}/man5/lvm.conf.5.gz
+%{_mandir}/man7/lvmautoactivation.7.gz
 %{_mandir}/man7/lvmcache.7.gz
 %{_mandir}/man7/lvmraid.7.gz
 %{_mandir}/man7/lvmreport.7.gz
@@ -842,8 +806,15 @@ An extensive functional testsuite for LVM2.
 %endif
 
 %changelog
-* Wed Feb 16 2022 Marian Csontos <mcsontos@redhat.com> - 2.03.12-11
-- Fix multiple concurrent LV refreshes failures.
+* Tue Jan 04 2022 Marian Csontos <mcsontos@redhat.com> - 2.03.14-3
+- Fix devices file and autoactivation related issues.
+
+* Fri Dec 17 2021 Marian Csontos <mcsontos@redhat.com> - 2.03.14-2
+- Revert autoactivation changes.
+
+* Wed Oct 20 2021 Marian Csontos <mcsontos@redhat.com> - 2.03.14-1
+- Update to upstream version 2.03.14.
+- See WHATS_NEW for list of changes.
 
 * Mon Sep 20 2021 Marian Csontos <mcsontos@redhat.com> - 2.03.12-10
 - Fix incorrect memory free.