device-mapper-multipath-0.8.5-4
Update Source to upstream version 0.8.5 plus post tag commits * Patches 0001-0121 are from https://github.com/openSUSE/multipath-tools/tree/queue and are already queued for upstream * Patches 0122&0123 have been posted for upstream inclusion Rename files * Previous patches 0103-0111 are now patches 0124-0132
This commit is contained in:
parent
13dea6f50c
commit
9fdf79cddf
@ -0,0 +1,46 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: lixiaokeng <lixiaokeng@huawei.com>
|
||||
Date: Sat, 23 Jan 2021 16:19:28 +0800
|
||||
Subject: [PATCH] libmultipath: fix NULL dereference in find_path_by_dev
|
||||
|
||||
When I test the 0.8.5 code with iscsi login/out, multipathd command
|
||||
and multipath command concurrently, there is a multipathd coredump.
|
||||
The stack is shown:
|
||||
|
||||
uxlsnrloop
|
||||
->cli_list_devices
|
||||
->show_devices
|
||||
->snprint_devices
|
||||
->find_path_by_dev
|
||||
|
||||
The reason is that devname is NULL in snprint_devices, then it will
|
||||
be dereference. Here we check dev in find_path_by_dev.
|
||||
|
||||
Reviewed-by: Martin Wilck <mwilck@suse.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/structs.c | 4 ++--
|
||||
1 file changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/libmultipath/structs.c b/libmultipath/structs.c
|
||||
index 464596fc..a3f27fd6 100644
|
||||
--- a/libmultipath/structs.c
|
||||
+++ b/libmultipath/structs.c
|
||||
@@ -453,12 +453,12 @@ find_mp_by_str (const struct _vector *mpvec, const char * str)
|
||||
}
|
||||
|
||||
struct path *
|
||||
-find_path_by_dev (const struct _vector *pathvec, const char * dev)
|
||||
+find_path_by_dev (const struct _vector *pathvec, const char *dev)
|
||||
{
|
||||
int i;
|
||||
struct path * pp;
|
||||
|
||||
- if (!pathvec)
|
||||
+ if (!pathvec || !dev)
|
||||
return NULL;
|
||||
|
||||
vector_foreach_slot (pathvec, pp, i)
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,38 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Mon, 25 Jan 2021 16:12:10 +0100
|
||||
Subject: [PATCH] libmultipath: snprint_devices(): avoid NULL dereference
|
||||
|
||||
All libudev functions may return NULL. Watch out for it.
|
||||
|
||||
Fixes: d041258 ("libmultipath: snprint_devices(): use udev_enumerate"
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/print.c | 8 ++++++++
|
||||
1 file changed, 8 insertions(+)
|
||||
|
||||
diff --git a/libmultipath/print.c b/libmultipath/print.c
|
||||
index 19de2c7c..8151e11e 100644
|
||||
--- a/libmultipath/print.c
|
||||
+++ b/libmultipath/print.c
|
||||
@@ -2055,8 +2055,16 @@ int snprint_devices(struct config *conf, char *buff, size_t len,
|
||||
struct udev_device *u_dev;
|
||||
|
||||
path = udev_list_entry_get_name(item);
|
||||
+ if (!path)
|
||||
+ continue;
|
||||
u_dev = udev_device_new_from_syspath(udev, path);
|
||||
+ if (!u_dev)
|
||||
+ continue;
|
||||
devname = udev_device_get_sysname(u_dev);
|
||||
+ if (!devname) {
|
||||
+ udev_device_unref(u_dev);
|
||||
+ continue;
|
||||
+ }
|
||||
|
||||
fwd += snprintf(buff + fwd, len - fwd, " %s", devname);
|
||||
if (fwd >= len)
|
||||
--
|
||||
2.17.2
|
||||
|
274
0105-libmpathpersist-fix-thread-safety-of-default-functio.patch
Normal file
274
0105-libmpathpersist-fix-thread-safety-of-default-functio.patch
Normal file
@ -0,0 +1,274 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Date: Mon, 25 Jan 2021 23:31:04 -0600
|
||||
Subject: [PATCH] libmpathpersist: fix thread safety of default functions
|
||||
|
||||
commit a839e39e ("libmpathpersist: factor out initialization and
|
||||
teardown") made mpath_presistent_reserve_{in,out} use share variables
|
||||
for curmp and pathvec. There are users of this library that call these
|
||||
functions in a multi-threaded process, and this change causes their
|
||||
application to crash. config and udev are also shared variables, but
|
||||
libmpathpersist doesn't write to the config in
|
||||
mpath_presistent_reserve_{in,out}, and looking into the libudev code, I
|
||||
don't see any place where libmpathpersist uses the udev object in a way
|
||||
that isn't thread-safe.
|
||||
|
||||
This patch makes mpath_presistent_reserve_{in,out} go back to using
|
||||
local variables for curmp and pathvec, so that multiple threads won't
|
||||
be operating on these variables at the same time.
|
||||
|
||||
Fixes: a839e39e ("libmpathpersist: factor out initialization and teardown")
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Reviewed-by: Martin Wilck <mwilck@suse.com>
|
||||
---
|
||||
libmpathpersist/mpath_persist.c | 116 +++++++++++++++++++++-----------
|
||||
libmpathpersist/mpath_persist.h | 24 +++++--
|
||||
2 files changed, 94 insertions(+), 46 deletions(-)
|
||||
|
||||
diff --git a/libmpathpersist/mpath_persist.c b/libmpathpersist/mpath_persist.c
|
||||
index 08077936..5c95af20 100644
|
||||
--- a/libmpathpersist/mpath_persist.c
|
||||
+++ b/libmpathpersist/mpath_persist.c
|
||||
@@ -133,69 +133,57 @@ mpath_prin_activepath (struct multipath *mpp, int rq_servact,
|
||||
return ret;
|
||||
}
|
||||
|
||||
-int mpath_persistent_reserve_in (int fd, int rq_servact,
|
||||
- struct prin_resp *resp, int noisy, int verbose)
|
||||
-{
|
||||
- int ret = mpath_persistent_reserve_init_vecs(verbose);
|
||||
-
|
||||
- if (ret != MPATH_PR_SUCCESS)
|
||||
- return ret;
|
||||
- ret = __mpath_persistent_reserve_in(fd, rq_servact, resp, noisy);
|
||||
- mpath_persistent_reserve_free_vecs();
|
||||
- return ret;
|
||||
-}
|
||||
-
|
||||
-int mpath_persistent_reserve_out ( int fd, int rq_servact, int rq_scope,
|
||||
- unsigned int rq_type, struct prout_param_descriptor *paramp, int noisy, int verbose)
|
||||
-{
|
||||
- int ret = mpath_persistent_reserve_init_vecs(verbose);
|
||||
-
|
||||
- if (ret != MPATH_PR_SUCCESS)
|
||||
- return ret;
|
||||
- ret = __mpath_persistent_reserve_out(fd, rq_servact, rq_scope, rq_type,
|
||||
- paramp, noisy);
|
||||
- mpath_persistent_reserve_free_vecs();
|
||||
- return ret;
|
||||
-}
|
||||
-
|
||||
static vector curmp;
|
||||
static vector pathvec;
|
||||
|
||||
-void mpath_persistent_reserve_free_vecs(void)
|
||||
+static void __mpath_persistent_reserve_free_vecs(vector curmp, vector pathvec)
|
||||
{
|
||||
free_multipathvec(curmp, KEEP_PATHS);
|
||||
free_pathvec(pathvec, FREE_PATHS);
|
||||
+}
|
||||
+
|
||||
+void mpath_persistent_reserve_free_vecs(void)
|
||||
+{
|
||||
+ __mpath_persistent_reserve_free_vecs(curmp, pathvec);
|
||||
curmp = pathvec = NULL;
|
||||
}
|
||||
|
||||
-int mpath_persistent_reserve_init_vecs(int verbose)
|
||||
+static int __mpath_persistent_reserve_init_vecs(vector *curmp_p,
|
||||
+ vector *pathvec_p, int verbose)
|
||||
{
|
||||
libmp_verbosity = verbose;
|
||||
|
||||
- if (curmp)
|
||||
+ if (*curmp_p)
|
||||
return MPATH_PR_SUCCESS;
|
||||
/*
|
||||
* allocate core vectors to store paths and multipaths
|
||||
*/
|
||||
- curmp = vector_alloc ();
|
||||
- pathvec = vector_alloc ();
|
||||
+ *curmp_p = vector_alloc ();
|
||||
+ *pathvec_p = vector_alloc ();
|
||||
|
||||
- if (!curmp || !pathvec){
|
||||
+ if (!*curmp_p || !*pathvec_p){
|
||||
condlog (0, "vector allocation failed.");
|
||||
goto err;
|
||||
}
|
||||
|
||||
- if (dm_get_maps(curmp))
|
||||
+ if (dm_get_maps(*curmp_p))
|
||||
goto err;
|
||||
|
||||
return MPATH_PR_SUCCESS;
|
||||
|
||||
err:
|
||||
- mpath_persistent_reserve_free_vecs();
|
||||
+ __mpath_persistent_reserve_free_vecs(*curmp_p, *pathvec_p);
|
||||
+ *curmp_p = *pathvec_p = NULL;
|
||||
return MPATH_PR_DMMP_ERROR;
|
||||
}
|
||||
|
||||
-static int mpath_get_map(int fd, char **palias, struct multipath **pmpp)
|
||||
+int mpath_persistent_reserve_init_vecs(int verbose)
|
||||
+{
|
||||
+ return __mpath_persistent_reserve_init_vecs(&curmp, &pathvec, verbose);
|
||||
+}
|
||||
+
|
||||
+static int mpath_get_map(vector curmp, vector pathvec, int fd, char **palias,
|
||||
+ struct multipath **pmpp)
|
||||
{
|
||||
int ret = MPATH_PR_DMMP_ERROR;
|
||||
struct stat info;
|
||||
@@ -255,13 +243,13 @@ out:
|
||||
return ret;
|
||||
}
|
||||
|
||||
-int __mpath_persistent_reserve_in (int fd, int rq_servact,
|
||||
- struct prin_resp *resp, int noisy)
|
||||
+static int do_mpath_persistent_reserve_in (vector curmp, vector pathvec,
|
||||
+ int fd, int rq_servact, struct prin_resp *resp, int noisy)
|
||||
{
|
||||
struct multipath *mpp;
|
||||
int ret;
|
||||
|
||||
- ret = mpath_get_map(fd, NULL, &mpp);
|
||||
+ ret = mpath_get_map(curmp, pathvec, fd, NULL, &mpp);
|
||||
if (ret != MPATH_PR_SUCCESS)
|
||||
return ret;
|
||||
|
||||
@@ -270,8 +258,17 @@ int __mpath_persistent_reserve_in (int fd, int rq_servact,
|
||||
return ret;
|
||||
}
|
||||
|
||||
-int __mpath_persistent_reserve_out ( int fd, int rq_servact, int rq_scope,
|
||||
- unsigned int rq_type, struct prout_param_descriptor *paramp, int noisy)
|
||||
+
|
||||
+int __mpath_persistent_reserve_in (int fd, int rq_servact,
|
||||
+ struct prin_resp *resp, int noisy)
|
||||
+{
|
||||
+ return do_mpath_persistent_reserve_in(curmp, pathvec, fd, rq_servact,
|
||||
+ resp, noisy);
|
||||
+}
|
||||
+
|
||||
+static int do_mpath_persistent_reserve_out(vector curmp, vector pathvec, int fd,
|
||||
+ int rq_servact, int rq_scope, unsigned int rq_type,
|
||||
+ struct prout_param_descriptor *paramp, int noisy)
|
||||
{
|
||||
struct multipath *mpp;
|
||||
char *alias;
|
||||
@@ -279,7 +276,7 @@ int __mpath_persistent_reserve_out ( int fd, int rq_servact, int rq_scope,
|
||||
uint64_t prkey;
|
||||
struct config *conf;
|
||||
|
||||
- ret = mpath_get_map(fd, &alias, &mpp);
|
||||
+ ret = mpath_get_map(curmp, pathvec, fd, &alias, &mpp);
|
||||
if (ret != MPATH_PR_SUCCESS)
|
||||
return ret;
|
||||
|
||||
@@ -349,6 +346,45 @@ out1:
|
||||
return ret;
|
||||
}
|
||||
|
||||
+
|
||||
+int __mpath_persistent_reserve_out ( int fd, int rq_servact, int rq_scope,
|
||||
+ unsigned int rq_type, struct prout_param_descriptor *paramp, int noisy)
|
||||
+{
|
||||
+ return do_mpath_persistent_reserve_out(curmp, pathvec, fd, rq_servact,
|
||||
+ rq_scope, rq_type, paramp,
|
||||
+ noisy);
|
||||
+}
|
||||
+
|
||||
+int mpath_persistent_reserve_in (int fd, int rq_servact,
|
||||
+ struct prin_resp *resp, int noisy, int verbose)
|
||||
+{
|
||||
+ vector curmp = NULL, pathvec;
|
||||
+ int ret = __mpath_persistent_reserve_init_vecs(&curmp, &pathvec,
|
||||
+ verbose);
|
||||
+
|
||||
+ if (ret != MPATH_PR_SUCCESS)
|
||||
+ return ret;
|
||||
+ ret = do_mpath_persistent_reserve_in(curmp, pathvec, fd, rq_servact,
|
||||
+ resp, noisy);
|
||||
+ __mpath_persistent_reserve_free_vecs(curmp, pathvec);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+int mpath_persistent_reserve_out ( int fd, int rq_servact, int rq_scope,
|
||||
+ unsigned int rq_type, struct prout_param_descriptor *paramp, int noisy, int verbose)
|
||||
+{
|
||||
+ vector curmp = NULL, pathvec;
|
||||
+ int ret = __mpath_persistent_reserve_init_vecs(&curmp, &pathvec,
|
||||
+ verbose);
|
||||
+
|
||||
+ if (ret != MPATH_PR_SUCCESS)
|
||||
+ return ret;
|
||||
+ ret = do_mpath_persistent_reserve_out(curmp, pathvec, fd, rq_servact,
|
||||
+ rq_scope, rq_type, paramp, noisy);
|
||||
+ __mpath_persistent_reserve_free_vecs(curmp, pathvec);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
int
|
||||
get_mpvec (vector curmp, vector pathvec, char * refwwid)
|
||||
{
|
||||
diff --git a/libmpathpersist/mpath_persist.h b/libmpathpersist/mpath_persist.h
|
||||
index 5435eae4..9e9c0a82 100644
|
||||
--- a/libmpathpersist/mpath_persist.h
|
||||
+++ b/libmpathpersist/mpath_persist.h
|
||||
@@ -246,9 +246,13 @@ extern int mpath_persistent_reserve_in (int fd, int rq_servact, struct prin_resp
|
||||
|
||||
/*
|
||||
* DESCRIPTION :
|
||||
- * This function is like mpath_persistent_reserve_in(), except that it doesn't call
|
||||
- * mpath_persistent_reserve_init_vecs() and mpath_persistent_reserve_free_vecs()
|
||||
- * before and after the actual PR call.
|
||||
+ * This function is like mpath_persistent_reserve_in(), except that it
|
||||
+ * requires mpath_persistent_reserve_init_vecs() to be called before the
|
||||
+ * PR call to set up internal variables. These must later be cleanup up
|
||||
+ * by calling mpath_persistent_reserve_free_vecs().
|
||||
+ *
|
||||
+ * RESTRICTIONS:
|
||||
+ * This function uses static internal variables, and is not thread-safe.
|
||||
*/
|
||||
extern int __mpath_persistent_reserve_in(int fd, int rq_servact,
|
||||
struct prin_resp *resp, int noisy);
|
||||
@@ -280,9 +284,13 @@ extern int mpath_persistent_reserve_out ( int fd, int rq_servact, int rq_scope,
|
||||
int verbose);
|
||||
/*
|
||||
* DESCRIPTION :
|
||||
- * This function is like mpath_persistent_reserve_out(), except that it doesn't call
|
||||
- * mpath_persistent_reserve_init_vecs() and mpath_persistent_reserve_free_vecs()
|
||||
- * before and after the actual PR call.
|
||||
+ * This function is like mpath_persistent_reserve_out(), except that it
|
||||
+ * requires mpath_persistent_reserve_init_vecs() to be called before the
|
||||
+ * PR call to set up internal variables. These must later be cleanup up
|
||||
+ * by calling mpath_persistent_reserve_free_vecs().
|
||||
+ *
|
||||
+ * RESTRICTIONS:
|
||||
+ * This function uses static internal variables, and is not thread-safe.
|
||||
*/
|
||||
extern int __mpath_persistent_reserve_out( int fd, int rq_servact, int rq_scope,
|
||||
unsigned int rq_type, struct prout_param_descriptor *paramp,
|
||||
@@ -296,6 +304,7 @@ extern int __mpath_persistent_reserve_out( int fd, int rq_servact, int rq_scope,
|
||||
* @verbose: Set verbosity level. Input argument. value:0 to 3. 0->disabled, 3->Max verbose
|
||||
*
|
||||
* RESTRICTIONS:
|
||||
+ * This function uses static internal variables, and is not thread-safe.
|
||||
*
|
||||
* RETURNS: MPATH_PR_SUCCESS if successful else returns any of the status specified
|
||||
* above in RETURN_STATUS.
|
||||
@@ -306,6 +315,9 @@ int mpath_persistent_reserve_init_vecs(int verbose);
|
||||
* DESCRIPTION :
|
||||
* This function frees data structures allocated by
|
||||
* mpath_persistent_reserve_init_vecs().
|
||||
+ *
|
||||
+ * RESTRICTIONS:
|
||||
+ * This function uses static internal variables, and is not thread-safe.
|
||||
*/
|
||||
void mpath_persistent_reserve_free_vecs(void);
|
||||
|
||||
--
|
||||
2.17.2
|
||||
|
37
0106-Added-github-action-for-building.patch
Normal file
37
0106-Added-github-action-for-building.patch
Normal file
@ -0,0 +1,37 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 18 Dec 2020 21:38:43 +0100
|
||||
Subject: [PATCH] Added github action for building
|
||||
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
.github/workflows/build-and-unittest.yaml | 17 +++++++++++++++++
|
||||
1 file changed, 17 insertions(+)
|
||||
create mode 100644 .github/workflows/build-and-unittest.yaml
|
||||
|
||||
diff --git a/.github/workflows/build-and-unittest.yaml b/.github/workflows/build-and-unittest.yaml
|
||||
new file mode 100644
|
||||
index 00000000..2b13c65c
|
||||
--- /dev/null
|
||||
+++ b/.github/workflows/build-and-unittest.yaml
|
||||
@@ -0,0 +1,17 @@
|
||||
+name: basic-build-and-ci
|
||||
+on: [push]
|
||||
+jobs:
|
||||
+ build:
|
||||
+ runs-on: ubuntu-latest
|
||||
+ steps:
|
||||
+ - uses: actions/checkout@v2
|
||||
+ - name: dependencies
|
||||
+ run: >
|
||||
+ sudo apt-get install --yes gcc
|
||||
+ make perl-base pkg-config
|
||||
+ libdevmapper-dev libreadline-dev libaio-dev libsystemd-dev
|
||||
+ libudev-dev libjson-c-dev liburcu-dev libcmocka-dev
|
||||
+ - name: build
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo)
|
||||
+ - name: test
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo) test
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,40 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 18 Dec 2020 22:18:20 +0100
|
||||
Subject: [PATCH] github workflow: use zram device as test block device
|
||||
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
.github/workflows/build-and-unittest.yaml | 12 ++++++++++++
|
||||
1 file changed, 12 insertions(+)
|
||||
|
||||
diff --git a/.github/workflows/build-and-unittest.yaml b/.github/workflows/build-and-unittest.yaml
|
||||
index 2b13c65c..ef55b8c1 100644
|
||||
--- a/.github/workflows/build-and-unittest.yaml
|
||||
+++ b/.github/workflows/build-and-unittest.yaml
|
||||
@@ -5,6 +5,14 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
+ - name: mpath
|
||||
+ run: sudo modprobe dm_multipath
|
||||
+ - name: zram
|
||||
+ run: sudo modprobe zram num_devices=0
|
||||
+ - name: zram-device
|
||||
+ run: echo ZRAM=$(sudo cat /sys/class/zram-control/hot_add) >> $GITHUB_ENV
|
||||
+ - name: set-zram-size
|
||||
+ run: echo 1G | sudo tee /sys/block/zram$ZRAM/disksize
|
||||
- name: dependencies
|
||||
run: >
|
||||
sudo apt-get install --yes gcc
|
||||
@@ -15,3 +23,7 @@ jobs:
|
||||
run: make -O -j$(grep -c ^processor /proc/cpuinfo)
|
||||
- name: test
|
||||
run: make -O -j$(grep -c ^processor /proc/cpuinfo) test
|
||||
+ - name: clean-nonroot-artifacts
|
||||
+ run: rm -f tests/dmevents.out tests/directio.out
|
||||
+ - name: root-test
|
||||
+ run: sudo make DIO_TEST_DEV=/dev/zram$ZRAM test
|
||||
--
|
||||
2.17.2
|
||||
|
26
0108-github-workflow-use-explicit-Ubuntu-version.patch
Normal file
26
0108-github-workflow-use-explicit-Ubuntu-version.patch
Normal file
@ -0,0 +1,26 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 18 Dec 2020 22:54:24 +0100
|
||||
Subject: [PATCH] github workflow: use explicit Ubuntu version
|
||||
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
.github/workflows/build-and-unittest.yaml | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/.github/workflows/build-and-unittest.yaml b/.github/workflows/build-and-unittest.yaml
|
||||
index ef55b8c1..577a14ac 100644
|
||||
--- a/.github/workflows/build-and-unittest.yaml
|
||||
+++ b/.github/workflows/build-and-unittest.yaml
|
||||
@@ -2,7 +2,7 @@ name: basic-build-and-ci
|
||||
on: [push]
|
||||
jobs:
|
||||
build:
|
||||
- runs-on: ubuntu-latest
|
||||
+ runs-on: ubuntu-18.04
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: mpath
|
||||
--
|
||||
2.17.2
|
||||
|
36
0109-github-workflow-add-valgrind-tests.patch
Normal file
36
0109-github-workflow-add-valgrind-tests.patch
Normal file
@ -0,0 +1,36 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 18 Dec 2020 23:21:16 +0100
|
||||
Subject: [PATCH] github workflow: add valgrind tests
|
||||
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
.github/workflows/build-and-unittest.yaml | 6 +++++-
|
||||
1 file changed, 5 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/.github/workflows/build-and-unittest.yaml b/.github/workflows/build-and-unittest.yaml
|
||||
index 577a14ac..929f63a6 100644
|
||||
--- a/.github/workflows/build-and-unittest.yaml
|
||||
+++ b/.github/workflows/build-and-unittest.yaml
|
||||
@@ -16,13 +16,17 @@ jobs:
|
||||
- name: dependencies
|
||||
run: >
|
||||
sudo apt-get install --yes gcc
|
||||
- make perl-base pkg-config
|
||||
+ make perl-base pkg-config valgrind
|
||||
libdevmapper-dev libreadline-dev libaio-dev libsystemd-dev
|
||||
libudev-dev libjson-c-dev liburcu-dev libcmocka-dev
|
||||
- name: build
|
||||
run: make -O -j$(grep -c ^processor /proc/cpuinfo)
|
||||
- name: test
|
||||
run: make -O -j$(grep -c ^processor /proc/cpuinfo) test
|
||||
+ - name: valgrind-test
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo) valgrind-test
|
||||
+ - name: valgrind-results
|
||||
+ run: cat tests/*.vgr
|
||||
- name: clean-nonroot-artifacts
|
||||
run: rm -f tests/dmevents.out tests/directio.out
|
||||
- name: root-test
|
||||
--
|
||||
2.17.2
|
||||
|
28
0110-github-workflow-run-apt-get-update.patch
Normal file
28
0110-github-workflow-run-apt-get-update.patch
Normal file
@ -0,0 +1,28 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 18 Dec 2020 23:26:16 +0100
|
||||
Subject: [PATCH] github workflow: run apt-get update
|
||||
|
||||
E: Failed to fetch http://azure.archive.ubuntu.com/ubuntu/pool/main/g/glibc/libc6-dbg_2.27-3ubuntu1.3_amd64.deb 404 Not Found [IP: 52.252.75.106 80]
|
||||
E: Unable to fetch some archives, maybe run apt-get update or try with --fix-missing?
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
.github/workflows/build-and-unittest.yaml | 2 ++
|
||||
1 file changed, 2 insertions(+)
|
||||
|
||||
diff --git a/.github/workflows/build-and-unittest.yaml b/.github/workflows/build-and-unittest.yaml
|
||||
index 929f63a6..389578be 100644
|
||||
--- a/.github/workflows/build-and-unittest.yaml
|
||||
+++ b/.github/workflows/build-and-unittest.yaml
|
||||
@@ -13,6 +13,8 @@ jobs:
|
||||
run: echo ZRAM=$(sudo cat /sys/class/zram-control/hot_add) >> $GITHUB_ENV
|
||||
- name: set-zram-size
|
||||
run: echo 1G | sudo tee /sys/block/zram$ZRAM/disksize
|
||||
+ - name: update
|
||||
+ run: sudo apt-get update
|
||||
- name: dependencies
|
||||
run: >
|
||||
sudo apt-get install --yes gcc
|
||||
--
|
||||
2.17.2
|
||||
|
90
0111-github-workflow-add-tests-with-gcc-10-and-clang.patch
Normal file
90
0111-github-workflow-add-tests-with-gcc-10-and-clang.patch
Normal file
@ -0,0 +1,90 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 18 Dec 2020 23:44:11 +0100
|
||||
Subject: [PATCH] github workflow: add tests with gcc 10 and clang
|
||||
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
.github/workflows/build-and-unittest.yaml | 62 ++++++++++++++++++++++-
|
||||
1 file changed, 61 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/.github/workflows/build-and-unittest.yaml b/.github/workflows/build-and-unittest.yaml
|
||||
index 389578be..4173576f 100644
|
||||
--- a/.github/workflows/build-and-unittest.yaml
|
||||
+++ b/.github/workflows/build-and-unittest.yaml
|
||||
@@ -1,7 +1,7 @@
|
||||
name: basic-build-and-ci
|
||||
on: [push]
|
||||
jobs:
|
||||
- build:
|
||||
+ bionic:
|
||||
runs-on: ubuntu-18.04
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
@@ -33,3 +33,63 @@ jobs:
|
||||
run: rm -f tests/dmevents.out tests/directio.out
|
||||
- name: root-test
|
||||
run: sudo make DIO_TEST_DEV=/dev/zram$ZRAM test
|
||||
+ focal-gcc10:
|
||||
+ runs-on: ubuntu-20.04
|
||||
+ steps:
|
||||
+ - uses: actions/checkout@v2
|
||||
+ - name: mpath
|
||||
+ run: sudo modprobe dm_multipath
|
||||
+ - name: brd
|
||||
+ run: sudo modprobe brd rd_nr=1 rd_size=65536
|
||||
+ - name: update
|
||||
+ run: sudo apt-get update
|
||||
+ - name: dependencies
|
||||
+ run: >
|
||||
+ sudo apt-get install --yes gcc-10
|
||||
+ make perl-base pkg-config valgrind
|
||||
+ libdevmapper-dev libreadline-dev libaio-dev libsystemd-dev
|
||||
+ libudev-dev libjson-c-dev liburcu-dev libcmocka-dev
|
||||
+ - name: set CC
|
||||
+ run: echo CC=gcc-10 >> $GITHUB_ENV
|
||||
+ - name: build
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo)
|
||||
+ - name: test
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo) test
|
||||
+ - name: valgrind-test
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo) valgrind-test
|
||||
+ - name: valgrind-results
|
||||
+ run: cat tests/*.vgr
|
||||
+ - name: clean-nonroot-artifacts
|
||||
+ run: rm -f tests/dmevents.out tests/directio.out
|
||||
+ - name: root-test
|
||||
+ run: sudo make DIO_TEST_DEV=/dev/ram0 test
|
||||
+ focal-clang10:
|
||||
+ runs-on: ubuntu-20.04
|
||||
+ steps:
|
||||
+ - uses: actions/checkout@v2
|
||||
+ - name: mpath
|
||||
+ run: sudo modprobe dm_multipath
|
||||
+ - name: brd
|
||||
+ run: sudo modprobe brd rd_nr=1 rd_size=65536
|
||||
+ - name: update
|
||||
+ run: sudo apt-get update
|
||||
+ - name: dependencies
|
||||
+ run: >
|
||||
+ sudo apt-get install --yes clang
|
||||
+ make perl-base pkg-config valgrind
|
||||
+ libdevmapper-dev libreadline-dev libaio-dev libsystemd-dev
|
||||
+ libudev-dev libjson-c-dev liburcu-dev libcmocka-dev
|
||||
+ - name: set CC
|
||||
+ run: echo CC=clang >> $GITHUB_ENV
|
||||
+ - name: build
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo)
|
||||
+ - name: test
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo) test
|
||||
+ - name: valgrind-test
|
||||
+ run: make -O -j$(grep -c ^processor /proc/cpuinfo) valgrind-test
|
||||
+ - name: valgrind-results
|
||||
+ run: cat tests/*.vgr
|
||||
+ - name: clean-nonroot-artifacts
|
||||
+ run: rm -f tests/dmevents.out tests/directio.out
|
||||
+ - name: root-test
|
||||
+ run: sudo make DIO_TEST_DEV=/dev/ram0 test
|
||||
--
|
||||
2.17.2
|
||||
|
38
0112-multipathd-Fix-multipathd-stopping-on-shutdown.patch
Normal file
38
0112-multipathd-Fix-multipathd-stopping-on-shutdown.patch
Normal file
@ -0,0 +1,38 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Date: Fri, 18 Dec 2020 17:06:41 -0600
|
||||
Subject: [PATCH] multipathd: Fix multipathd stopping on shutdown
|
||||
|
||||
According to man "systemd.special"
|
||||
|
||||
"shutdown.target: ... Services that shall be terminated on system
|
||||
shutdown shall add Conflicts= and Before= dependencies to this unit for
|
||||
their service unit, which is implicitly done when
|
||||
DefaultDependencies=yes is set (the default)."
|
||||
|
||||
multipathd.service sets DefaultDependencies=no and includes the
|
||||
Conflits= dependency, but not the Before= one. This can cause multipathd
|
||||
to continue running past when it is supposed to during shutdown.
|
||||
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Reviewed-by: Martin Wilck <mwilck@suse.com>
|
||||
---
|
||||
multipathd/multipathd.service | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/multipathd/multipathd.service b/multipathd/multipathd.service
|
||||
index ba24983e..7d547fa7 100644
|
||||
--- a/multipathd/multipathd.service
|
||||
+++ b/multipathd/multipathd.service
|
||||
@@ -2,7 +2,7 @@
|
||||
Description=Device-Mapper Multipath Device Controller
|
||||
Wants=systemd-udev-trigger.service systemd-udev-settle.service
|
||||
Before=iscsi.service iscsid.service lvm2-activation-early.service
|
||||
-Before=local-fs-pre.target blk-availability.service
|
||||
+Before=local-fs-pre.target blk-availability.service shutdown.target
|
||||
After=multipathd.socket systemd-udev-trigger.service systemd-udev-settle.service
|
||||
DefaultDependencies=no
|
||||
Conflicts=shutdown.target
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,45 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 13 Nov 2020 22:34:41 +0100
|
||||
Subject: [PATCH] libmultipath: use 3rd digit as transport_id for expanders
|
||||
|
||||
On SAS expanders, node id's have 3 digits. sysfs paths look like this:
|
||||
|
||||
/sys/devices/pci0000:80/0000:80:02.0/0000:8b:00.0/0000:8c:09.0/0000:8f:00.0/host9/port-9:0/expander-9:0/port-9:0:13/expander-9:1/port-9:1:12/expander-9:2/port-9:2:4/end_device-9:2:4/target9:0:29/9:0:29:0/block/sdac
|
||||
|
||||
In that case, we should use the last digit as transport id.
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/discovery.c | 13 ++++++++++---
|
||||
1 file changed, 10 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/libmultipath/discovery.c b/libmultipath/discovery.c
|
||||
index e818585a..6d74cc07 100644
|
||||
--- a/libmultipath/discovery.c
|
||||
+++ b/libmultipath/discovery.c
|
||||
@@ -358,10 +358,17 @@ sysfs_get_tgt_nodename(struct path *pp, char *node)
|
||||
if (value) {
|
||||
tgtdev = udev_device_get_parent(parent);
|
||||
while (tgtdev) {
|
||||
+ char c;
|
||||
+
|
||||
tgtname = udev_device_get_sysname(tgtdev);
|
||||
- if (tgtname && sscanf(tgtname, "end_device-%d:%d",
|
||||
- &host, &tgtid) == 2)
|
||||
- break;
|
||||
+ if (tgtname) {
|
||||
+ if (sscanf(tgtname, "end_device-%d:%d:%d%c",
|
||||
+ &host, &channel, &tgtid, &c) == 3)
|
||||
+ break;
|
||||
+ if (sscanf(tgtname, "end_device-%d:%d%c",
|
||||
+ &host, &tgtid, &c) == 2)
|
||||
+ break;
|
||||
+ }
|
||||
tgtdev = udev_device_get_parent(tgtdev);
|
||||
tgtid = -1;
|
||||
}
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,57 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Fri, 13 Nov 2020 22:38:21 +0100
|
||||
Subject: [PATCH] libmultipath: sysfs_set_nexus_loss_tmo(): support SAS
|
||||
expanders
|
||||
|
||||
With SAS expanders, SAS node names have 3 digits. libmultipath
|
||||
would fail to discover the sas_end_device matching a given SCSI
|
||||
target in this case. Fix it.
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/discovery.c | 24 +++++++++++++++++++-----
|
||||
1 file changed, 19 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/libmultipath/discovery.c b/libmultipath/discovery.c
|
||||
index 6d74cc07..921025d4 100644
|
||||
--- a/libmultipath/discovery.c
|
||||
+++ b/libmultipath/discovery.c
|
||||
@@ -789,14 +789,28 @@ sysfs_set_session_tmo(struct multipath *mpp, struct path *pp)
|
||||
static void
|
||||
sysfs_set_nexus_loss_tmo(struct multipath *mpp, struct path *pp)
|
||||
{
|
||||
- struct udev_device *sas_dev = NULL;
|
||||
- char end_dev_id[64];
|
||||
+ struct udev_device *parent, *sas_dev = NULL;
|
||||
+ const char *end_dev_id = NULL;
|
||||
char value[11];
|
||||
+ static const char ed_str[] = "end_device-";
|
||||
|
||||
- if (mpp->dev_loss == DEV_LOSS_TMO_UNSET)
|
||||
+ if (!pp->udev || mpp->dev_loss == DEV_LOSS_TMO_UNSET)
|
||||
return;
|
||||
- sprintf(end_dev_id, "end_device-%d:%d",
|
||||
- pp->sg_id.host_no, pp->sg_id.transport_id);
|
||||
+
|
||||
+ for (parent = udev_device_get_parent(pp->udev);
|
||||
+ parent;
|
||||
+ parent = udev_device_get_parent(parent)) {
|
||||
+ const char *ed = udev_device_get_sysname(parent);
|
||||
+
|
||||
+ if (!strncmp(ed, ed_str, sizeof(ed_str) - 1)) {
|
||||
+ end_dev_id = ed;
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+ if (!end_dev_id) {
|
||||
+ condlog(1, "%s: No SAS end device", pp->dev);
|
||||
+ return;
|
||||
+ }
|
||||
sas_dev = udev_device_new_from_subsystem_sysname(udev,
|
||||
"sas_end_device", end_dev_id);
|
||||
if (!sas_dev) {
|
||||
--
|
||||
2.17.2
|
||||
|
134
0115-multipathd-add-code-to-initalize-unwinder.patch
Normal file
134
0115-multipathd-add-code-to-initalize-unwinder.patch
Normal file
@ -0,0 +1,134 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Thu, 17 Dec 2020 16:50:06 +0100
|
||||
Subject: [PATCH] multipathd: add code to initalize unwinder
|
||||
|
||||
glibc's implementation of pthread_cancel() loads symbols from
|
||||
libgcc_s.so using dlopen() when pthread_cancel() is called
|
||||
for the first time. This happens even with LD_BIND_NOW=1.
|
||||
This may imply the need for file system access when a thread is
|
||||
cancelled, which in the case of multipath-tools might be in a
|
||||
dangerous situation where multipathd must avoid blocking.
|
||||
|
||||
Call load_unwinder() during startup to make sure the dynamic
|
||||
linker has all necessary symbols resolved early on.
|
||||
|
||||
This implementation simply creates a dummy thread and cancels
|
||||
it. This way all necessary symbols for thread cancellation
|
||||
will be loaded, no matter what the C library needs to implement
|
||||
cancellation.
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
multipathd/Makefile | 2 +-
|
||||
multipathd/init_unwinder.c | 34 ++++++++++++++++++++++++++++++++++
|
||||
multipathd/init_unwinder.h | 21 +++++++++++++++++++++
|
||||
multipathd/main.c | 2 ++
|
||||
4 files changed, 58 insertions(+), 1 deletion(-)
|
||||
create mode 100644 multipathd/init_unwinder.c
|
||||
create mode 100644 multipathd/init_unwinder.h
|
||||
|
||||
diff --git a/multipathd/Makefile b/multipathd/Makefile
|
||||
index 632b82b1..d053c1ed 100644
|
||||
--- a/multipathd/Makefile
|
||||
+++ b/multipathd/Makefile
|
||||
@@ -30,7 +30,7 @@ ifeq ($(ENABLE_DMEVENTS_POLL),0)
|
||||
endif
|
||||
|
||||
OBJS = main.o pidfile.o uxlsnr.o uxclnt.o cli.o cli_handlers.o waiter.o \
|
||||
- dmevents.o
|
||||
+ dmevents.o init_unwinder.o
|
||||
|
||||
EXEC = multipathd
|
||||
|
||||
diff --git a/multipathd/init_unwinder.c b/multipathd/init_unwinder.c
|
||||
new file mode 100644
|
||||
index 00000000..14467f3d
|
||||
--- /dev/null
|
||||
+++ b/multipathd/init_unwinder.c
|
||||
@@ -0,0 +1,34 @@
|
||||
+#include <pthread.h>
|
||||
+#include <unistd.h>
|
||||
+#include "init_unwinder.h"
|
||||
+
|
||||
+static pthread_mutex_t dummy_mtx = PTHREAD_MUTEX_INITIALIZER;
|
||||
+static pthread_cond_t dummy_cond = PTHREAD_COND_INITIALIZER;
|
||||
+
|
||||
+static void *dummy_thread(void *arg __attribute__((unused)))
|
||||
+{
|
||||
+ pthread_mutex_lock(&dummy_mtx);
|
||||
+ pthread_cond_broadcast(&dummy_cond);
|
||||
+ pthread_mutex_unlock(&dummy_mtx);
|
||||
+ pause();
|
||||
+ return NULL;
|
||||
+}
|
||||
+
|
||||
+int init_unwinder(void)
|
||||
+{
|
||||
+ pthread_t dummy;
|
||||
+ int rc;
|
||||
+
|
||||
+ pthread_mutex_lock(&dummy_mtx);
|
||||
+
|
||||
+ rc = pthread_create(&dummy, NULL, dummy_thread, NULL);
|
||||
+ if (rc != 0) {
|
||||
+ pthread_mutex_unlock(&dummy_mtx);
|
||||
+ return rc;
|
||||
+ }
|
||||
+
|
||||
+ pthread_cond_wait(&dummy_cond, &dummy_mtx);
|
||||
+ pthread_mutex_unlock(&dummy_mtx);
|
||||
+
|
||||
+ return pthread_cancel(dummy);
|
||||
+}
|
||||
diff --git a/multipathd/init_unwinder.h b/multipathd/init_unwinder.h
|
||||
new file mode 100644
|
||||
index 00000000..ada09f82
|
||||
--- /dev/null
|
||||
+++ b/multipathd/init_unwinder.h
|
||||
@@ -0,0 +1,21 @@
|
||||
+#ifndef _INIT_UNWINDER_H
|
||||
+#define _INIT_UNWINDER_H 1
|
||||
+
|
||||
+/*
|
||||
+ * init_unwinder(): make sure unwinder symbols are loaded
|
||||
+ *
|
||||
+ * libc's implementation of pthread_cancel() loads symbols from
|
||||
+ * libgcc_s.so using dlopen() when pthread_cancel() is called
|
||||
+ * for the first time. This happens even with LD_BIND_NOW=1.
|
||||
+ * This may imply the need for file system access when a thread is
|
||||
+ * cancelled, which in the case of multipath-tools might be in a
|
||||
+ * dangerous situation where multipathd must avoid blocking.
|
||||
+ *
|
||||
+ * Call load_unwinder() during startup to make sure the dynamic
|
||||
+ * linker has all necessary symbols resolved early on.
|
||||
+ *
|
||||
+ * Return: 0 if successful, an error number otherwise.
|
||||
+ */
|
||||
+int init_unwinder(void);
|
||||
+
|
||||
+#endif
|
||||
diff --git a/multipathd/main.c b/multipathd/main.c
|
||||
index 99a89a69..6f851ae8 100644
|
||||
--- a/multipathd/main.c
|
||||
+++ b/multipathd/main.c
|
||||
@@ -83,6 +83,7 @@
|
||||
#include "wwids.h"
|
||||
#include "foreign.h"
|
||||
#include "../third-party/valgrind/drd.h"
|
||||
+#include "init_unwinder.h"
|
||||
|
||||
#define FILE_NAME_SIZE 256
|
||||
#define CMDSIZE 160
|
||||
@@ -3041,6 +3042,7 @@ child (__attribute__((unused)) void *param)
|
||||
enum daemon_status state;
|
||||
int exit_code = 1;
|
||||
|
||||
+ init_unwinder();
|
||||
mlockall(MCL_CURRENT | MCL_FUTURE);
|
||||
signal_init();
|
||||
mp_rcu_data = setup_rcu();
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,57 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Tue, 2 Feb 2021 11:12:21 +0100
|
||||
Subject: [PATCH] libmultipath: check if adopt_path() really added current path
|
||||
|
||||
The description of 2d32d6f ("libmultipath: adopt_paths(): don't bail out on
|
||||
single path failure") said "we need to check after successful call to
|
||||
adopt_paths() if that specific path had been actually added, and fail in the
|
||||
caller otherwise". But the commit failed to actually implement this check.
|
||||
Instead, it just checked if the path was member of the pathvec, which will
|
||||
almost always be the case.
|
||||
|
||||
Fix it by checking what actually needs to be checked, membership of the
|
||||
path to be added in mpp->paths.
|
||||
|
||||
Fixes: 2d32d6f ("libmultipath: adopt_paths(): don't bail out on single path failure")
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/structs_vec.c | 4 ++--
|
||||
multipathd/main.c | 4 ++--
|
||||
2 files changed, 4 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/libmultipath/structs_vec.c b/libmultipath/structs_vec.c
|
||||
index f7f45f11..47b1d03e 100644
|
||||
--- a/libmultipath/structs_vec.c
|
||||
+++ b/libmultipath/structs_vec.c
|
||||
@@ -707,8 +707,8 @@ struct multipath *add_map_with_path(struct vectors *vecs, struct path *pp,
|
||||
goto out;
|
||||
mpp->size = pp->size;
|
||||
|
||||
- if (adopt_paths(vecs->pathvec, mpp) ||
|
||||
- find_slot(vecs->pathvec, pp) == -1)
|
||||
+ if (adopt_paths(vecs->pathvec, mpp) || pp->mpp != mpp ||
|
||||
+ find_slot(mpp->paths, pp) == -1)
|
||||
goto out;
|
||||
|
||||
if (add_vec) {
|
||||
diff --git a/multipathd/main.c b/multipathd/main.c
|
||||
index 6f851ae8..43d77688 100644
|
||||
--- a/multipathd/main.c
|
||||
+++ b/multipathd/main.c
|
||||
@@ -1008,8 +1008,8 @@ rescan:
|
||||
if (mpp) {
|
||||
condlog(4,"%s: adopting all paths for path %s",
|
||||
mpp->alias, pp->dev);
|
||||
- if (adopt_paths(vecs->pathvec, mpp) ||
|
||||
- find_slot(vecs->pathvec, pp) == -1)
|
||||
+ if (adopt_paths(vecs->pathvec, mpp) || pp->mpp != mpp ||
|
||||
+ find_slot(mpp->paths, pp) == -1)
|
||||
goto fail; /* leave path added to pathvec */
|
||||
|
||||
verify_paths(mpp);
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,31 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Mon, 1 Feb 2021 13:10:46 +0100
|
||||
Subject: [PATCH] multipathd: ev_add_path: fail if add_map_with_path() fails
|
||||
|
||||
If start_waiter was set before and the "rescan" label was used,
|
||||
we may try to set up an empty/invalid map.
|
||||
Always fail if add_map_with_path() isn't successful.
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
multipathd/main.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/multipathd/main.c b/multipathd/main.c
|
||||
index 43d77688..425492a9 100644
|
||||
--- a/multipathd/main.c
|
||||
+++ b/multipathd/main.c
|
||||
@@ -1028,7 +1028,7 @@ rescan:
|
||||
*/
|
||||
start_waiter = 1;
|
||||
}
|
||||
- if (!start_waiter)
|
||||
+ else
|
||||
goto fail; /* leave path added to pathvec */
|
||||
}
|
||||
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,31 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Tue, 2 Feb 2021 15:18:33 +0100
|
||||
Subject: [PATCH] libmultipath: check return value of udev_device_get_devnum()
|
||||
|
||||
udev_device_get_devnum() may fail, in which case it returns
|
||||
makedev(0, 0).
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/discovery.c | 3 +++
|
||||
1 file changed, 3 insertions(+)
|
||||
|
||||
diff --git a/libmultipath/discovery.c b/libmultipath/discovery.c
|
||||
index 921025d4..15cf6413 100644
|
||||
--- a/libmultipath/discovery.c
|
||||
+++ b/libmultipath/discovery.c
|
||||
@@ -1659,6 +1659,9 @@ common_sysfs_pathinfo (struct path * pp)
|
||||
return PATHINFO_FAILED;
|
||||
}
|
||||
devt = udev_device_get_devnum(pp->udev);
|
||||
+ if (major(devt) == 0 && minor(devt) == 0)
|
||||
+ return PATHINFO_FAILED;
|
||||
+
|
||||
snprintf(pp->dev_t, BLK_DEV_SIZE, "%d:%d", major(devt), minor(devt));
|
||||
|
||||
condlog(4, "%s: dev_t = %s", pp->dev, pp->dev_t);
|
||||
--
|
||||
2.17.2
|
||||
|
281
0119-pathinfo-call-filter_property-after-sysfs_pathinfo.patch
Normal file
281
0119-pathinfo-call-filter_property-after-sysfs_pathinfo.patch
Normal file
@ -0,0 +1,281 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Tue, 2 Feb 2021 17:07:37 +0100
|
||||
Subject: [PATCH] pathinfo: call filter_property() after sysfs_pathinfo()
|
||||
|
||||
The of filter_property() depends on the value of pp->uid_attribute.
|
||||
This may in turn depend on pp->hwe, which is initialized in
|
||||
sysfs_pathinfo(). To obtain consistent results from pathinfo(),
|
||||
make sure uid_attribute is correctly set before calling filter_property().
|
||||
|
||||
filter_property() is now called from pathinfo() with properly set
|
||||
uid_attribute, thus we don't need to call it from is_path_valid() any more.
|
||||
|
||||
Thes changes require modifications to the unit tests. The is_path_valid()
|
||||
test now wouldn't need to test filter_property() any more, because
|
||||
is_path_valid() calls filter_property() no more. But that doesn't feel
|
||||
right. Instead, test_filter_property() is modified to test the behavior
|
||||
with the filter_property() test called indirectly from pathinfo().
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/discovery.c | 21 +++++++++-
|
||||
libmultipath/valid.c | 4 --
|
||||
tests/Makefile | 2 +-
|
||||
tests/test-lib.c | 5 ++-
|
||||
tests/valid.c | 91 ++++++++++++++++++++++++++++++++++++----
|
||||
5 files changed, 105 insertions(+), 18 deletions(-)
|
||||
|
||||
diff --git a/libmultipath/discovery.c b/libmultipath/discovery.c
|
||||
index 15cf6413..febcd0ae 100644
|
||||
--- a/libmultipath/discovery.c
|
||||
+++ b/libmultipath/discovery.c
|
||||
@@ -2247,9 +2247,17 @@ int pathinfo(struct path *pp, struct config *conf, int mask)
|
||||
condlog(4, "%s: hidden", pp->dev);
|
||||
return PATHINFO_SKIPPED;
|
||||
}
|
||||
- if (is_claimed_by_foreign(pp->udev) ||
|
||||
- filter_property(conf, pp->udev, 4, pp->uid_attribute) > 0)
|
||||
+
|
||||
+ if (is_claimed_by_foreign(pp->udev))
|
||||
return PATHINFO_SKIPPED;
|
||||
+
|
||||
+ /*
|
||||
+ * uid_attribute is required for filter_property below,
|
||||
+ * and needs access to pp->hwe.
|
||||
+ */
|
||||
+ if (!(mask & DI_SYSFS) && !pp->uid_attribute &&
|
||||
+ VECTOR_SIZE(pp->hwe) == 0)
|
||||
+ mask |= DI_SYSFS;
|
||||
}
|
||||
|
||||
if (strlen(pp->dev) != 0 && filter_devnode(conf->blist_devnode,
|
||||
@@ -2287,6 +2295,15 @@ int pathinfo(struct path *pp, struct config *conf, int mask)
|
||||
}
|
||||
}
|
||||
|
||||
+ if (pp->udev) {
|
||||
+ /* uid_attribute is required for filter_property() */
|
||||
+ if (!pp->uid_attribute)
|
||||
+ select_getuid(conf, pp);
|
||||
+
|
||||
+ if (filter_property(conf, pp->udev, 4, pp->uid_attribute) > 0)
|
||||
+ return PATHINFO_SKIPPED;
|
||||
+ }
|
||||
+
|
||||
if (mask & DI_BLACKLIST && mask & DI_SYSFS) {
|
||||
if (filter_device(conf->blist_device, conf->elist_device,
|
||||
pp->vendor_id, pp->product_id, pp->dev) > 0 ||
|
||||
diff --git a/libmultipath/valid.c b/libmultipath/valid.c
|
||||
index 456b1f6e..a6aa9215 100644
|
||||
--- a/libmultipath/valid.c
|
||||
+++ b/libmultipath/valid.c
|
||||
@@ -89,10 +89,6 @@ is_path_valid(const char *name, struct config *conf, struct path *pp,
|
||||
if (pp->wwid[0] == '\0')
|
||||
return PATH_IS_NOT_VALID;
|
||||
|
||||
- if (pp->udev && pp->uid_attribute &&
|
||||
- filter_property(conf, pp->udev, 3, pp->uid_attribute) > 0)
|
||||
- return PATH_IS_NOT_VALID;
|
||||
-
|
||||
r = is_failed_wwid(pp->wwid);
|
||||
if (r != WWID_IS_NOT_FAILED) {
|
||||
if (r == WWID_IS_FAILED)
|
||||
diff --git a/tests/Makefile b/tests/Makefile
|
||||
index 50673fae..11ca1be5 100644
|
||||
--- a/tests/Makefile
|
||||
+++ b/tests/Makefile
|
||||
@@ -54,7 +54,7 @@ vpd-test_OBJDEPS := ../libmultipath/discovery.o
|
||||
vpd-test_LIBDEPS := -ludev -lpthread -ldl
|
||||
alias-test_TESTDEPS := test-log.o
|
||||
alias-test_LIBDEPS := -lpthread -ldl
|
||||
-valid-test_OBJDEPS := ../libmultipath/valid.o
|
||||
+valid-test_OBJDEPS := ../libmultipath/valid.o ../libmultipath/discovery.o
|
||||
valid-test_LIBDEPS := -ludev -lpthread -ldl
|
||||
devt-test_LIBDEPS := -ludev
|
||||
mpathvalid-test_LIBDEPS := -ludev -lpthread -ldl
|
||||
diff --git a/tests/test-lib.c b/tests/test-lib.c
|
||||
index e7663f9a..960a7665 100644
|
||||
--- a/tests/test-lib.c
|
||||
+++ b/tests/test-lib.c
|
||||
@@ -257,6 +257,9 @@ void mock_pathinfo(int mask, const struct mocked_path *mp)
|
||||
} else
|
||||
will_return(__wrap_udev_device_get_sysattr_value, "0");
|
||||
|
||||
+ if (mask & DI_SYSFS)
|
||||
+ mock_sysfs_pathinfo(mp);
|
||||
+
|
||||
/* filter_property */
|
||||
will_return(__wrap_udev_device_get_sysname, mp->devnode);
|
||||
if (mp->flags & BL_BY_PROPERTY) {
|
||||
@@ -265,8 +268,6 @@ void mock_pathinfo(int mask, const struct mocked_path *mp)
|
||||
} else
|
||||
will_return(__wrap_udev_list_entry_get_name,
|
||||
"SCSI_IDENT_LUN_NAA_EXT");
|
||||
- if (mask & DI_SYSFS)
|
||||
- mock_sysfs_pathinfo(mp);
|
||||
|
||||
if (mp->flags & BL_BY_DEVICE &&
|
||||
(mask & DI_BLACKLIST && mask & DI_SYSFS))
|
||||
diff --git a/tests/valid.c b/tests/valid.c
|
||||
index 693c72c5..8ec803e8 100644
|
||||
--- a/tests/valid.c
|
||||
+++ b/tests/valid.c
|
||||
@@ -25,13 +25,18 @@
|
||||
#include <stdlib.h>
|
||||
#include <errno.h>
|
||||
#include <cmocka.h>
|
||||
+#include <sys/sysmacros.h>
|
||||
+
|
||||
#include "globals.c"
|
||||
#include "util.h"
|
||||
#include "discovery.h"
|
||||
#include "wwids.h"
|
||||
#include "blacklist.h"
|
||||
+#include "foreign.h"
|
||||
#include "valid.h"
|
||||
|
||||
+#define PATHINFO_REAL 9999
|
||||
+
|
||||
int test_fd;
|
||||
struct udev_device {
|
||||
int unused;
|
||||
@@ -78,12 +83,66 @@ struct udev_device *__wrap_udev_device_new_from_subsystem_sysname(struct udev *u
|
||||
return NULL;
|
||||
}
|
||||
|
||||
+/* For the "hidden" check in pathinfo() */
|
||||
+const char *__wrap_udev_device_get_sysattr_value(struct udev_device *udev_device,
|
||||
+ const char *sysattr)
|
||||
+{
|
||||
+ check_expected(sysattr);
|
||||
+ return mock_ptr_type(char *);
|
||||
+}
|
||||
+
|
||||
+/* For pathinfo() -> is_claimed_by_foreign() */
|
||||
+int __wrap_add_foreign(struct udev_device *udev_device)
|
||||
+{
|
||||
+ return mock_type(int);
|
||||
+}
|
||||
+
|
||||
+/* called from pathinfo() */
|
||||
+int __wrap_filter_devnode(struct config *conf, const struct _vector *elist,
|
||||
+ const char *vendor, const char * product, const char *dev)
|
||||
+{
|
||||
+ return mock_type(int);
|
||||
+}
|
||||
+
|
||||
+/* called from pathinfo() */
|
||||
+int __wrap_filter_device(const struct _vector *blist, const struct _vector *elist,
|
||||
+ const char *vendor, const char * product, const char *dev)
|
||||
+{
|
||||
+ return mock_type(int);
|
||||
+}
|
||||
+
|
||||
+/* for common_sysfs_pathinfo() */
|
||||
+dev_t __wrap_udev_device_get_devnum(struct udev_device *ud)
|
||||
+{
|
||||
+ return mock_type(dev_t);
|
||||
+}
|
||||
+
|
||||
+/* for common_sysfs_pathinfo() */
|
||||
+int __wrap_sysfs_get_size(struct path *pp, unsigned long long * size)
|
||||
+{
|
||||
+ return mock_type(int);
|
||||
+}
|
||||
+
|
||||
+/* called in pathinfo() before filter_property() */
|
||||
+int __wrap_select_getuid(struct config *conf, struct path *pp)
|
||||
+{
|
||||
+ pp->uid_attribute = mock_ptr_type(char *);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+int __real_pathinfo(struct path *pp, struct config *conf, int mask);
|
||||
+
|
||||
int __wrap_pathinfo(struct path *pp, struct config *conf, int mask)
|
||||
{
|
||||
int ret = mock_type(int);
|
||||
+
|
||||
assert_string_equal(pp->dev, mock_ptr_type(char *));
|
||||
assert_int_equal(mask, DI_SYSFS | DI_WWID | DI_BLACKLIST);
|
||||
- if (ret == PATHINFO_OK) {
|
||||
+ if (ret == PATHINFO_REAL) {
|
||||
+ /* for test_filter_property() */
|
||||
+ ret = __real_pathinfo(pp, conf, mask);
|
||||
+ return ret;
|
||||
+ } else if (ret == PATHINFO_OK) {
|
||||
pp->uid_attribute = "ID_TEST";
|
||||
strlcpy(pp->wwid, mock_ptr_type(char *), WWID_SIZE);
|
||||
} else
|
||||
@@ -128,6 +187,7 @@ enum {
|
||||
STAGE_IS_MULTIPATHED,
|
||||
STAGE_CHECK_MULTIPATHD,
|
||||
STAGE_GET_UDEV_DEVICE,
|
||||
+ STAGE_PATHINFO_REAL,
|
||||
STAGE_PATHINFO,
|
||||
STAGE_FILTER_PROPERTY,
|
||||
STAGE_IS_FAILED,
|
||||
@@ -167,12 +227,25 @@ static void setup_passing(char *name, char *wwid, unsigned int check_multipathd,
|
||||
name);
|
||||
if (stage == STAGE_GET_UDEV_DEVICE)
|
||||
return;
|
||||
+ if (stage == STAGE_PATHINFO_REAL) {
|
||||
+ /* special case for test_filter_property() */
|
||||
+ will_return(__wrap_pathinfo, PATHINFO_REAL);
|
||||
+ will_return(__wrap_pathinfo, name);
|
||||
+ expect_string(__wrap_udev_device_get_sysattr_value,
|
||||
+ sysattr, "hidden");
|
||||
+ will_return(__wrap_udev_device_get_sysattr_value, NULL);
|
||||
+ will_return(__wrap_add_foreign, FOREIGN_IGNORED);
|
||||
+ will_return(__wrap_filter_devnode, MATCH_NOTHING);
|
||||
+ will_return(__wrap_udev_device_get_devnum, makedev(259, 0));
|
||||
+ will_return(__wrap_sysfs_get_size, 0);
|
||||
+ will_return(__wrap_select_getuid, "ID_TEST");
|
||||
+ return;
|
||||
+ }
|
||||
will_return(__wrap_pathinfo, PATHINFO_OK);
|
||||
will_return(__wrap_pathinfo, name);
|
||||
will_return(__wrap_pathinfo, wwid);
|
||||
if (stage == STAGE_PATHINFO)
|
||||
return;
|
||||
- will_return(__wrap_filter_property, MATCH_PROPERTY_BLIST_EXCEPT);
|
||||
if (stage == STAGE_FILTER_PROPERTY)
|
||||
return;
|
||||
will_return(__wrap_is_failed_wwid, WWID_IS_NOT_FAILED);
|
||||
@@ -317,24 +390,24 @@ static void test_filter_property(void **state)
|
||||
/* test blacklist property */
|
||||
memset(&pp, 0, sizeof(pp));
|
||||
conf.find_multipaths = FIND_MULTIPATHS_STRICT;
|
||||
- setup_passing(name, wwid, CHECK_MPATHD_SKIP, STAGE_PATHINFO);
|
||||
+ setup_passing(name, wwid, CHECK_MPATHD_SKIP, STAGE_PATHINFO_REAL);
|
||||
will_return(__wrap_filter_property, MATCH_PROPERTY_BLIST);
|
||||
assert_int_equal(is_path_valid(name, &conf, &pp, false),
|
||||
PATH_IS_NOT_VALID);
|
||||
assert_ptr_equal(pp.udev, &test_udev);
|
||||
- assert_string_equal(pp.wwid, wwid);
|
||||
+
|
||||
/* test missing property */
|
||||
memset(&pp, 0, sizeof(pp));
|
||||
- setup_passing(name, wwid, CHECK_MPATHD_SKIP, STAGE_PATHINFO);
|
||||
+ setup_passing(name, wwid, CHECK_MPATHD_SKIP, STAGE_PATHINFO_REAL);
|
||||
will_return(__wrap_filter_property, MATCH_PROPERTY_BLIST_MISSING);
|
||||
assert_int_equal(is_path_valid(name, &conf, &pp, false),
|
||||
PATH_IS_NOT_VALID);
|
||||
- /* test MATCH_NOTHING fail on is_failed_wwid */
|
||||
+
|
||||
+ /* test MATCH_NOTHING fail on filter_device */
|
||||
memset(&pp, 0, sizeof(pp));
|
||||
- setup_passing(name, wwid, CHECK_MPATHD_SKIP, STAGE_PATHINFO);
|
||||
+ setup_passing(name, wwid, CHECK_MPATHD_SKIP, STAGE_PATHINFO_REAL);
|
||||
will_return(__wrap_filter_property, MATCH_NOTHING);
|
||||
- will_return(__wrap_is_failed_wwid, WWID_IS_FAILED);
|
||||
- will_return(__wrap_is_failed_wwid, wwid);
|
||||
+ will_return(__wrap_filter_device, MATCH_DEVICE_BLIST);
|
||||
assert_int_equal(is_path_valid(name, &conf, &pp, false),
|
||||
PATH_IS_NOT_VALID);
|
||||
}
|
||||
--
|
||||
2.17.2
|
||||
|
@ -0,0 +1,88 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Tue, 2 Feb 2021 19:55:28 +0100
|
||||
Subject: [PATCH] libmultipath: pathinfo: call filter_property only with
|
||||
DI_BLACKLIST
|
||||
|
||||
With the previous change to call filter_property() after sysfs_pathinfo(),
|
||||
it can't happen any more that filter_property() is called from pathinfo
|
||||
with uid_attribute not set. This may cause pathinfo() to return failure
|
||||
in some cases where it should actually proceed (e.g. when called from
|
||||
"multipath -m" -> get_refwwid(). Therefore, don't call filter_property()
|
||||
any more unless DI_BLACKLIST is set.
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/discovery.c | 16 ++++++----------
|
||||
tests/test-lib.c | 17 +++++++++--------
|
||||
2 files changed, 15 insertions(+), 18 deletions(-)
|
||||
|
||||
diff --git a/libmultipath/discovery.c b/libmultipath/discovery.c
|
||||
index febcd0ae..9be94cd1 100644
|
||||
--- a/libmultipath/discovery.c
|
||||
+++ b/libmultipath/discovery.c
|
||||
@@ -2255,8 +2255,8 @@ int pathinfo(struct path *pp, struct config *conf, int mask)
|
||||
* uid_attribute is required for filter_property below,
|
||||
* and needs access to pp->hwe.
|
||||
*/
|
||||
- if (!(mask & DI_SYSFS) && !pp->uid_attribute &&
|
||||
- VECTOR_SIZE(pp->hwe) == 0)
|
||||
+ if (!(mask & DI_SYSFS) && (mask & DI_BLACKLIST) &&
|
||||
+ !pp->uid_attribute && VECTOR_SIZE(pp->hwe) == 0)
|
||||
mask |= DI_SYSFS;
|
||||
}
|
||||
|
||||
@@ -2295,17 +2295,13 @@ int pathinfo(struct path *pp, struct config *conf, int mask)
|
||||
}
|
||||
}
|
||||
|
||||
- if (pp->udev) {
|
||||
+ if (mask & DI_BLACKLIST && mask & DI_SYSFS) {
|
||||
/* uid_attribute is required for filter_property() */
|
||||
- if (!pp->uid_attribute)
|
||||
+ if (pp->udev && !pp->uid_attribute)
|
||||
select_getuid(conf, pp);
|
||||
|
||||
- if (filter_property(conf, pp->udev, 4, pp->uid_attribute) > 0)
|
||||
- return PATHINFO_SKIPPED;
|
||||
- }
|
||||
-
|
||||
- if (mask & DI_BLACKLIST && mask & DI_SYSFS) {
|
||||
- if (filter_device(conf->blist_device, conf->elist_device,
|
||||
+ if (filter_property(conf, pp->udev, 4, pp->uid_attribute) > 0 ||
|
||||
+ filter_device(conf->blist_device, conf->elist_device,
|
||||
pp->vendor_id, pp->product_id, pp->dev) > 0 ||
|
||||
filter_protocol(conf->blist_protocol, conf->elist_protocol,
|
||||
pp) > 0)
|
||||
diff --git a/tests/test-lib.c b/tests/test-lib.c
|
||||
index 960a7665..f5542ed0 100644
|
||||
--- a/tests/test-lib.c
|
||||
+++ b/tests/test-lib.c
|
||||
@@ -260,14 +260,15 @@ void mock_pathinfo(int mask, const struct mocked_path *mp)
|
||||
if (mask & DI_SYSFS)
|
||||
mock_sysfs_pathinfo(mp);
|
||||
|
||||
- /* filter_property */
|
||||
- will_return(__wrap_udev_device_get_sysname, mp->devnode);
|
||||
- if (mp->flags & BL_BY_PROPERTY) {
|
||||
- will_return(__wrap_udev_list_entry_get_name, "BAZ");
|
||||
- return;
|
||||
- } else
|
||||
- will_return(__wrap_udev_list_entry_get_name,
|
||||
- "SCSI_IDENT_LUN_NAA_EXT");
|
||||
+ if (mask & DI_BLACKLIST) {
|
||||
+ will_return(__wrap_udev_device_get_sysname, mp->devnode);
|
||||
+ if (mp->flags & BL_BY_PROPERTY) {
|
||||
+ will_return(__wrap_udev_list_entry_get_name, "BAZ");
|
||||
+ return;
|
||||
+ } else
|
||||
+ will_return(__wrap_udev_list_entry_get_name,
|
||||
+ "SCSI_IDENT_LUN_NAA_EXT");
|
||||
+ }
|
||||
|
||||
if (mp->flags & BL_BY_DEVICE &&
|
||||
(mask & DI_BLACKLIST && mask & DI_SYSFS))
|
||||
--
|
||||
2.17.2
|
||||
|
39
0121-multipath-w-allow-removing-blacklisted-paths.patch
Normal file
39
0121-multipath-w-allow-removing-blacklisted-paths.patch
Normal file
@ -0,0 +1,39 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Martin Wilck <mwilck@suse.com>
|
||||
Date: Tue, 2 Feb 2021 21:54:37 +0100
|
||||
Subject: [PATCH] multipath -w: allow removing blacklisted paths
|
||||
|
||||
multipath should allow removing WWIDs of paths even if they
|
||||
are blacklisted.
|
||||
|
||||
Reviewed-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
libmultipath/configure.c | 4 ++--
|
||||
1 file changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/libmultipath/configure.c b/libmultipath/configure.c
|
||||
index 3263bb01..598efe05 100644
|
||||
--- a/libmultipath/configure.c
|
||||
+++ b/libmultipath/configure.c
|
||||
@@ -1441,7 +1441,7 @@ static int _get_refwwid(enum mpath_cmds cmd, const char *dev,
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
- if (pp->udev && pp->uid_attribute &&
|
||||
+ if (flags & DI_BLACKLIST &&
|
||||
filter_property(conf, pp->udev, 3, pp->uid_attribute) > 0)
|
||||
return PATHINFO_SKIPPED;
|
||||
refwwid = pp->wwid;
|
||||
@@ -1466,7 +1466,7 @@ static int _get_refwwid(enum mpath_cmds cmd, const char *dev,
|
||||
refwwid = dev;
|
||||
}
|
||||
|
||||
- if (refwwid && strlen(refwwid) &&
|
||||
+ if (flags & DI_BLACKLIST && refwwid && strlen(refwwid) &&
|
||||
filter_wwid(conf->blist_wwid, conf->elist_wwid, refwwid,
|
||||
NULL) > 0)
|
||||
return PATHINFO_SKIPPED;
|
||||
--
|
||||
2.17.2
|
||||
|
53
0122-libmultipath-fix-use-after-free-in-uev_add_path.patch
Normal file
53
0122-libmultipath-fix-use-after-free-in-uev_add_path.patch
Normal file
@ -0,0 +1,53 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Date: Mon, 1 Feb 2021 19:47:11 -0600
|
||||
Subject: [PATCH] libmultipath: fix use-after-free in uev_add_path
|
||||
|
||||
if ev_remove_path() returns success the path has very likely been
|
||||
deleted. However, if pathinfo() returned something besides PATHINFO_OK,
|
||||
but ev_remove_path() succeeded, uev_add_path() was still accessing the
|
||||
the path afterwards, which would likely cause a use-after-free error.
|
||||
Insted, uev_add_path() should only continue to access the path if
|
||||
ev_remove_path() didn't succeed.
|
||||
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
multipathd/main.c | 15 +++++++--------
|
||||
1 file changed, 7 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/multipathd/main.c b/multipathd/main.c
|
||||
index 425492a9..19679848 100644
|
||||
--- a/multipathd/main.c
|
||||
+++ b/multipathd/main.c
|
||||
@@ -890,13 +890,7 @@ uev_add_path (struct uevent *uev, struct vectors * vecs, int need_do_map)
|
||||
*/
|
||||
pp->mpp = prev_mpp;
|
||||
ret = ev_remove_path(pp, vecs, true);
|
||||
- if (r == PATHINFO_OK && !ret)
|
||||
- /*
|
||||
- * Path successfully freed, move on to
|
||||
- * "new path" code path below
|
||||
- */
|
||||
- pp = NULL;
|
||||
- else {
|
||||
+ if (ret != 0) {
|
||||
/*
|
||||
* Failure in ev_remove_path will keep
|
||||
* path in pathvec in INIT_REMOVED state
|
||||
@@ -907,7 +901,12 @@ uev_add_path (struct uevent *uev, struct vectors * vecs, int need_do_map)
|
||||
dm_fail_path(pp->mpp->alias, pp->dev_t);
|
||||
condlog(1, "%s: failed to re-add path still mapped in %s",
|
||||
pp->dev, pp->mpp->alias);
|
||||
- }
|
||||
+ } else if (r == PATHINFO_OK)
|
||||
+ /*
|
||||
+ * Path successfully freed, move on to
|
||||
+ * "new path" code path below
|
||||
+ */
|
||||
+ pp = NULL;
|
||||
} else if (r == PATHINFO_SKIPPED) {
|
||||
condlog(3, "%s: remove blacklisted path",
|
||||
uev->kernel);
|
||||
--
|
||||
2.17.2
|
||||
|
61
0123-kpartx-free-loop-device-after-listing-partitions.patch
Normal file
61
0123-kpartx-free-loop-device-after-listing-partitions.patch
Normal file
@ -0,0 +1,61 @@
|
||||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
Date: Tue, 9 Feb 2021 17:16:04 -0600
|
||||
Subject: [PATCH] kpartx: free loop device after listing partitions
|
||||
|
||||
If "kpartx -l" is run on a file that doesn't already have a loop device
|
||||
associated with it, it will create a loop device to run the command.
|
||||
Starting with da59d15c6 ("Fix loopback file with kpartx -av"), it will
|
||||
not free the loop device when exitting. This is because it checks if the
|
||||
the file it stat()ed is a regular file, before freeing the loop device.
|
||||
However, after da59d15c6, stat() is rerun on the loop device itself, so
|
||||
the check fails. There is no need to check this, if loopcreated is
|
||||
true, then the file will be a kpartx created loop device, and should be
|
||||
freed.
|
||||
|
||||
Also, keep kpartx from printing that the loop device has been removed
|
||||
at normal verbosity.
|
||||
|
||||
Fixes: da59d15c6 ("Fix loopback file with kpartx -av")
|
||||
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
||||
---
|
||||
kpartx/kpartx.c | 9 +++++----
|
||||
1 file changed, 5 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/kpartx/kpartx.c b/kpartx/kpartx.c
|
||||
index 6a7933fa..8ff116b8 100644
|
||||
--- a/kpartx/kpartx.c
|
||||
+++ b/kpartx/kpartx.c
|
||||
@@ -424,7 +424,7 @@ main(int argc, char **argv){
|
||||
fprintf(stderr, "can't del loop : %s\n",
|
||||
loopdev);
|
||||
r = 1;
|
||||
- } else
|
||||
+ } else if (verbose)
|
||||
fprintf(stderr, "loop deleted : %s\n", loopdev);
|
||||
}
|
||||
goto end;
|
||||
@@ -668,16 +668,17 @@ main(int argc, char **argv){
|
||||
if (n > 0)
|
||||
break;
|
||||
}
|
||||
- if (what == LIST && loopcreated && S_ISREG (buf.st_mode)) {
|
||||
+ if (what == LIST && loopcreated) {
|
||||
if (fd != -1)
|
||||
close(fd);
|
||||
if (del_loop(device)) {
|
||||
if (verbose)
|
||||
- printf("can't del loop : %s\n",
|
||||
+ fprintf(stderr, "can't del loop : %s\n",
|
||||
device);
|
||||
exit(1);
|
||||
}
|
||||
- printf("loop deleted : %s\n", device);
|
||||
+ if (verbose)
|
||||
+ fprintf(stderr, "loop deleted : %s\n", device);
|
||||
}
|
||||
|
||||
end:
|
||||
--
|
||||
2.17.2
|
||||
|
@ -81,12 +81,12 @@ index 048a838d..8bd47a80 100644
|
||||
.
|
||||
.\" ----------------------------------------------------------------------------
|
||||
diff --git a/multipathd/multipathd.service b/multipathd/multipathd.service
|
||||
index ba24983e..17434cef 100644
|
||||
index 7d547fa7..af592057 100644
|
||||
--- a/multipathd/multipathd.service
|
||||
+++ b/multipathd/multipathd.service
|
||||
@@ -4,6 +4,7 @@ Wants=systemd-udev-trigger.service systemd-udev-settle.service
|
||||
Before=iscsi.service iscsid.service lvm2-activation-early.service
|
||||
Before=local-fs-pre.target blk-availability.service
|
||||
Before=local-fs-pre.target blk-availability.service shutdown.target
|
||||
After=multipathd.socket systemd-udev-trigger.service systemd-udev-settle.service
|
||||
+ConditionPathExists=/etc/multipath.conf
|
||||
DefaultDependencies=no
|
@ -69,7 +69,7 @@ index b9bbb3cf..e720c7f6 100644
|
||||
$(RM) core *.o $(EXEC) *.gz
|
||||
diff --git a/multipath/mpathconf b/multipath/mpathconf
|
||||
new file mode 100644
|
||||
index 00000000..f34003c9
|
||||
index 00000000..2f4f3eaf
|
||||
--- /dev/null
|
||||
+++ b/multipath/mpathconf
|
||||
@@ -0,0 +1,555 @@
|
||||
@ -129,7 +129,7 @@ index 00000000..f34003c9
|
||||
+ echo "Disable: --disable"
|
||||
+ echo "Only allow certain wwids (instead of enable): --allow <WWID>"
|
||||
+ echo "Set user_friendly_names (Default y): --user_friendly_names <y|n>"
|
||||
+ echo "Set find_multipaths (Default y): --find_multipaths <y|n>"
|
||||
+ echo "Set find_multipaths (Default y): --find_multipaths <yes|no|strict|greedy|smart>"
|
||||
+ echo "Set default property blacklist (Default y): --property_blacklist <y|n>"
|
||||
+ echo "Set enable_foreign to show foreign devices (Default n): --enable_foreign <y|n>"
|
||||
+ echo "Load the dm-multipath modules on enable (Default y): --with_module <y|n>"
|
||||
@ -299,8 +299,12 @@ index 00000000..f34003c9
|
||||
+ echo "--user_friendly_names must be either 'y' or 'n'"
|
||||
+ exit 1
|
||||
+ fi
|
||||
+ if [ -n "$FIND" ] && [ "$FIND" != "y" -a "$FIND" != "n" ]; then
|
||||
+ echo "--find_multipaths must be either 'y' or 'n'"
|
||||
+ if [ "$FIND" = "y" ]; then
|
||||
+ FIND="yes"
|
||||
+ elif [ "$FIND" = "n" ]; then
|
||||
+ FIND="no"
|
||||
+ elif [ -n "$FIND" ] && [ "$FIND" != "yes" -a "$FIND" != "no" -a "$FIND" != "strict" -a "$FIND" != "greedy" -a "$FIND" != "smart" ]; then
|
||||
+ echo "--find_multipaths must be one of 'yes' 'no' 'strict' 'greedy' or 'smart'"
|
||||
+ exit 1
|
||||
+ fi
|
||||
+ if [ -n "$PROPERTY" ] && [ "$PROPERTY" != "y" -a "$PROPERTY" != "n" ]; then
|
||||
@ -402,10 +406,11 @@ index 00000000..f34003c9
|
||||
+fi
|
||||
+
|
||||
+if [ "$HAVE_DEFAULTS" = "1" ]; then
|
||||
+ if sed -n '/^defaults[[:space:]]*{/,/^}/ p' $TMPFILE | grep -q "^[[:space:]]*find_multipaths[[:space:]]*\(yes\|1\)" ; then
|
||||
+ HAVE_FIND=1
|
||||
+ elif sed -n '/^defaults[[:space:]]*{/,/^}/ p' $TMPFILE | grep -q "^[[:space:]]*find_multipaths[[:space:]]*\(no\|0\)" ; then
|
||||
+ HAVE_FIND=0
|
||||
+ HAVE_FIND=`sed -n '/^defaults[[:space:]]*{/,/^}/ p' $TMPFILE | sed -n 's/^[[:blank:]]*find_multipaths[[:blank:]]*\([^[:blank:]]*\).*$/\1/p' | sed -n 1p`
|
||||
+ if [ "$HAVE_FIND" = "1" ]; then
|
||||
+ HAVE_FIND="yes"
|
||||
+ elif [ "$HAVE_FIND" = "0" ]; then
|
||||
+ HAVE_FIND="no"
|
||||
+ fi
|
||||
+ if sed -n '/^defaults[[:space:]]*{/,/^}/ p' $TMPFILE | grep -q "^[[:space:]]*user_friendly_names[[:space:]]*\(yes\|1\)" ; then
|
||||
+ HAVE_FRIENDLY=1
|
||||
@ -435,10 +440,10 @@ index 00000000..f34003c9
|
||||
+ else
|
||||
+ echo "multipath is disabled"
|
||||
+ fi
|
||||
+ if [ -z "$HAVE_FIND" -o "$HAVE_FIND" = 0 ]; then
|
||||
+ echo "find_multipaths is disabled"
|
||||
+ if [ -z "$HAVE_FIND" ]; then
|
||||
+ echo "find_multipaths is no"
|
||||
+ else
|
||||
+ echo "find_multipaths is enabled"
|
||||
+ echo "find_multipaths is $HAVE_FIND"
|
||||
+ fi
|
||||
+ if [ -z "$HAVE_FRIENDLY" -o "$HAVE_FRIENDLY" = 0 ]; then
|
||||
+ echo "user_friendly_names is disabled"
|
||||
@ -530,19 +535,14 @@ index 00000000..f34003c9
|
||||
+ fi
|
||||
+fi
|
||||
+
|
||||
+if [ "$FIND" = "n" ]; then
|
||||
+ if [ "$HAVE_FIND" = 1 ]; then
|
||||
+ sed -i '/^defaults[[:space:]]*{/,/^}/ s/^[[:space:]]*find_multipaths[[:space:]]*\(yes\|1\)/ find_multipaths no/' $TMPFILE
|
||||
+ CHANGED_CONFIG=1
|
||||
+ fi
|
||||
+elif [ "$FIND" = "y" ]; then
|
||||
+if [ -n "$FIND" ]; then
|
||||
+ if [ -z "$HAVE_FIND" ]; then
|
||||
+ sed -i '/^defaults[[:space:]]*{/ a\
|
||||
+ find_multipaths yes
|
||||
+ find_multipaths '"$FIND"'
|
||||
+' $TMPFILE
|
||||
+ CHANGED_CONFIG=1
|
||||
+ elif [ "$HAVE_FIND" = 0 ]; then
|
||||
+ sed -i '/^defaults[[:space:]]*{/,/^}/ s/^[[:space:]]*find_multipaths[[:space:]]*\(no\|0\)/ find_multipaths yes/' $TMPFILE
|
||||
+ elif [ "$FIND" != "$HAVE_FIND" ]; then
|
||||
+ sed -i '/^defaults[[:space:]]*{/,/^}/ s/^[[:blank:]]*find_multipaths[[:blank:]]*[^[:blank:]]*/ find_multipaths '"$FIND"'/' $TMPFILE
|
||||
+ CHANGED_CONFIG=1
|
||||
+ fi
|
||||
+fi
|
||||
@ -630,7 +630,7 @@ index 00000000..f34003c9
|
||||
+fi
|
||||
diff --git a/multipath/mpathconf.8 b/multipath/mpathconf.8
|
||||
new file mode 100644
|
||||
index 00000000..b82961d6
|
||||
index 00000000..83515eb4
|
||||
--- /dev/null
|
||||
+++ b/multipath/mpathconf.8
|
||||
@@ -0,0 +1,135 @@
|
||||
@ -674,9 +674,9 @@ index 00000000..b82961d6
|
||||
+already exists, mpathconf will edit it. If it does not exist, mpathconf will
|
||||
+create a default file with
|
||||
+.B user_friendly_names
|
||||
+and
|
||||
+set and
|
||||
+.B find_multipaths
|
||||
+set. To disable these, use the
|
||||
+set to \fByes\fP. To disable these, use the
|
||||
+.B --user_friendly_names n
|
||||
+and
|
||||
+.B --find_multipaths n
|
||||
@ -713,13 +713,13 @@ index 00000000..b82961d6
|
||||
+defaults section. If set to \fBn\fP, this removes the line, if present. This
|
||||
+command can be used along with any other command.
|
||||
+.TP
|
||||
+.B --find_multipaths\fP { \fBy\fP | \fBn\fP }
|
||||
+If set to \fBy\fP, this adds the line
|
||||
+.B find_multipaths yes
|
||||
+.B --find_multipaths\fP { \fByes\fP | \fBno\fP | \fBstrict\fP | \fBgreedy\fP | \fBsmart\fP }
|
||||
+If set to \fB<value>\fP, this adds the line
|
||||
+.B find_multipaths <value>
|
||||
+to the
|
||||
+.B /etc/multipath.conf
|
||||
+defaults section. If set to \fBn\fP, this removes the line, if present. This
|
||||
+command can be used along with any other command.
|
||||
+defaults section. This command can be used along with any other command.
|
||||
+\fBy\fP and \fBn\fP can be used instead of \fByes\fP and \fBno\fP.
|
||||
+.TP
|
||||
+.B --property_blacklist \fP { \fBy\fP | \fBn\fP }
|
||||
+If set to \fBy\fP, this adds the line
|
@ -138,7 +138,7 @@ index 5b29a5d9..0478f4e7 100644
|
||||
Remove the WWID for the specified device from the WWIDs file.
|
||||
.
|
||||
diff --git a/multipathd/multipathd.service b/multipathd/multipathd.service
|
||||
index 17434cef..0fbcc46b 100644
|
||||
index af592057..bc8fa07a 100644
|
||||
--- a/multipathd/multipathd.service
|
||||
+++ b/multipathd/multipathd.service
|
||||
@@ -15,6 +15,7 @@ Type=notify
|
@ -1,6 +1,6 @@
|
||||
Name: device-mapper-multipath
|
||||
Version: 0.8.5
|
||||
Release: 3%{?dist}
|
||||
Release: 4%{?dist}
|
||||
Summary: Tools to manage multipath devices using device-mapper
|
||||
License: GPLv2
|
||||
URL: http://christophe.varoqui.free.fr/
|
||||
@ -112,15 +112,36 @@ Patch0099: 0099-multipathd-avoid-io_err_stat-ABBA-deadlock.patch
|
||||
Patch0100: 0100-multipathd-use-get_monotonic_time-in-io_err_stat-cod.patch
|
||||
Patch0101: 0101-multipathd-combine-free_io_err_stat_path-and-destroy.patch
|
||||
Patch0102: 0102-multipathd-cleanup-logging-for-marginal-paths.patch
|
||||
Patch0103: 0103-RH-fixup-udev-rules-for-redhat.patch
|
||||
Patch0104: 0104-RH-Remove-the-property-blacklist-exception-builtin.patch
|
||||
Patch0105: 0105-RH-don-t-start-without-a-config-file.patch
|
||||
Patch0106: 0106-RH-Fix-nvme-function-missing-argument.patch
|
||||
Patch0107: 0107-RH-use-rpm-optflags-if-present.patch
|
||||
Patch0108: 0108-RH-add-mpathconf.patch
|
||||
Patch0109: 0109-RH-add-wwids-from-kernel-cmdline-mpath.wwids-with-A.patch
|
||||
Patch0110: 0110-RH-reset-default-find_mutipaths-value-to-off.patch
|
||||
Patch0111: 0111-RH-attempt-to-get-ANA-info-via-sysfs-first.patch
|
||||
Patch0103: 0103-libmultipath-fix-NULL-dereference-in-find_path_by_de.patch
|
||||
Patch0104: 0104-libmultipath-snprint_devices-avoid-NULL-dereference.patch
|
||||
Patch0105: 0105-libmpathpersist-fix-thread-safety-of-default-functio.patch
|
||||
Patch0106: 0106-Added-github-action-for-building.patch
|
||||
Patch0107: 0107-github-workflow-use-zram-device-as-test-block-device.patch
|
||||
Patch0108: 0108-github-workflow-use-explicit-Ubuntu-version.patch
|
||||
Patch0109: 0109-github-workflow-add-valgrind-tests.patch
|
||||
Patch0110: 0110-github-workflow-run-apt-get-update.patch
|
||||
Patch0111: 0111-github-workflow-add-tests-with-gcc-10-and-clang.patch
|
||||
Patch0112: 0112-multipathd-Fix-multipathd-stopping-on-shutdown.patch
|
||||
Patch0113: 0113-libmultipath-use-3rd-digit-as-transport_id-for-expan.patch
|
||||
Patch0114: 0114-libmultipath-sysfs_set_nexus_loss_tmo-support-SAS-ex.patch
|
||||
Patch0115: 0115-multipathd-add-code-to-initalize-unwinder.patch
|
||||
Patch0116: 0116-libmultipath-check-if-adopt_path-really-added-curren.patch
|
||||
Patch0117: 0117-multipathd-ev_add_path-fail-if-add_map_with_path-fai.patch
|
||||
Patch0118: 0118-libmultipath-check-return-value-of-udev_device_get_d.patch
|
||||
Patch0119: 0119-pathinfo-call-filter_property-after-sysfs_pathinfo.patch
|
||||
Patch0120: 0120-libmultipath-pathinfo-call-filter_property-only-with.patch
|
||||
Patch0121: 0121-multipath-w-allow-removing-blacklisted-paths.patch
|
||||
Patch0122: 0122-libmultipath-fix-use-after-free-in-uev_add_path.patch
|
||||
Patch0123: 0123-kpartx-free-loop-device-after-listing-partitions.patch
|
||||
Patch0124: 0124-RH-fixup-udev-rules-for-redhat.patch
|
||||
Patch0125: 0125-RH-Remove-the-property-blacklist-exception-builtin.patch
|
||||
Patch0126: 0126-RH-don-t-start-without-a-config-file.patch
|
||||
Patch0127: 0127-RH-Fix-nvme-function-missing-argument.patch
|
||||
Patch0128: 0128-RH-use-rpm-optflags-if-present.patch
|
||||
Patch0129: 0129-RH-add-mpathconf.patch
|
||||
Patch0130: 0130-RH-add-wwids-from-kernel-cmdline-mpath.wwids-with-A.patch
|
||||
Patch0131: 0131-RH-reset-default-find_mutipaths-value-to-off.patch
|
||||
Patch0132: 0132-RH-attempt-to-get-ANA-info-via-sysfs-first.patch
|
||||
|
||||
# runtime
|
||||
Requires: %{name}-libs = %{version}-%{release}
|
||||
@ -318,6 +339,15 @@ fi
|
||||
%{_pkgconfdir}/libdmmp.pc
|
||||
|
||||
%changelog
|
||||
* Thu Feb 11 2021 Benjamin Marzinski <bmarzins@redhat.com> - 0.8.5-4
|
||||
- Update Source to upstream version 0.8.5 plus post tag commits
|
||||
* Patches 0001-0121 are from
|
||||
https://github.com/openSUSE/multipath-tools/tree/queue and are
|
||||
already queued for upstream
|
||||
* Patches 0122&0123 have been posted for upstream inclusion
|
||||
- Rename files
|
||||
* Previous patches 0103-0111 are now patches 0124-0132
|
||||
|
||||
* Tue Jan 26 2021 Fedora Release Engineering <releng@fedoraproject.org> - 0.8.5-3
|
||||
- Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user