942c9b6ed8
Update Source to upstream version 0.8.2 * Previoud patches 0001-0017 & 0027 are included in this commit Rename files * Previous patches 0018-0026 & 0028 are not patches 0021-0030 Add 0001-libmultipath-make-vector_foreach_slot_backwards-work.patch Add 0002-libmultipath-add-marginal-paths-and-groups-infrastru.patch Add 0003-tests-add-path-grouping-policy-unit-tests.patch Add 0004-libmultipath-add-wrapper-function-around-pgpolicyfn.patch Add 0005-tests-update-pgpolicy-tests-to-work-with-group_paths.patch Add 0006-libmultipath-fix-double-free-in-pgpolicyfn-error-pat.patch Add 0007-libmultipath-consolidate-group_by_-functions.patch Add 0008-libmultipath-make-pgpolicyfn-take-a-paths-vector.patch Add 0009-libmultipath-make-group_paths-handle-marginal-paths.patch Add 0010-tests-add-tests-for-grouping-marginal-paths.patch Add 0011-libmultipath-add-marginal_pathgroups-config-option.patch Add 0012-libmutipath-deprecate-delay_-_checks.patch Add 0013-multipathd-use-marginal_pathgroups.patch Add 0014-multipath-update-man-pages.patch * The above 13 patches add the marinal_pathgroups option Add 0015-multipath.conf-add-enable_foreign-parameter.patch Add 0016-multipath.conf.5-document-foreign-library-support.patch * The above 2 patches add the enable_foreign option Add 0017-mpathpersist-remove-broken-unused-code.patch Add 0018-libmultipath-EMC-PowerMax-NVMe-device-config.patch Add 0019-mpathpersist-fix-leaks.patch Add 0020-libmultipath-fix-mpcontext-initialization.patch * The above 20 patches have been submitted upstream
233 lines
7.0 KiB
Diff
233 lines
7.0 KiB
Diff
From 33a6f6b05d7041716142f080a2708db351c92eaa Mon Sep 17 00:00:00 2001
|
|
From: Benjamin Marzinski <bmarzins@redhat.com>
|
|
Date: Tue, 10 Sep 2019 15:46:28 -0500
|
|
Subject: [PATCH] libmultipath: fix mpcontext initialization
|
|
|
|
If a path is discovered before there is a multipath device for it to
|
|
belong to, the checker will not have its mpcontext initialized, even if
|
|
that path later belongs to a multipath device. A checker's mpcontext is
|
|
only set when the checker is selected, and is set to NULL if there is no
|
|
multipath device associated with the path. This only impacts the emc
|
|
checker. However, it makes the emc checker unable to determine if a
|
|
passive path is connected to an inactive snapshot or not.
|
|
|
|
This can be solved by adding a new checker class function, mp_init().
|
|
This is called when the checker is first initialized, and whenever the
|
|
checker is called, if the checker's mpcontext hasn't been initialized.
|
|
|
|
Signed-off-by: Benjamin Marzinski <bmarzins@redhat.com>
|
|
---
|
|
libmultipath/checkers.c | 29 ++++++++++++++++++++++++++--
|
|
libmultipath/checkers.h | 1 +
|
|
libmultipath/checkers/cciss_tur.c | 5 +++++
|
|
libmultipath/checkers/directio.c | 5 +++++
|
|
libmultipath/checkers/emc_clariion.c | 7 +++++++
|
|
libmultipath/checkers/hp_sw.c | 5 +++++
|
|
libmultipath/checkers/rdac.c | 5 +++++
|
|
libmultipath/checkers/readsector0.c | 5 +++++
|
|
libmultipath/checkers/tur.c | 5 +++++
|
|
libmultipath/discovery.c | 2 ++
|
|
10 files changed, 67 insertions(+), 2 deletions(-)
|
|
|
|
diff --git a/libmultipath/checkers.c b/libmultipath/checkers.c
|
|
index f4fdcae9..240b0f29 100644
|
|
--- a/libmultipath/checkers.c
|
|
+++ b/libmultipath/checkers.c
|
|
@@ -16,6 +16,7 @@ struct checker_class {
|
|
char name[CHECKER_NAME_LEN];
|
|
int (*check)(struct checker *);
|
|
int (*init)(struct checker *); /* to allocate the context */
|
|
+ int (*mp_init)(struct checker *); /* to allocate the mpcontext */
|
|
void (*free)(struct checker *); /* to free the context */
|
|
const char **msgtable;
|
|
short msgtable_size;
|
|
@@ -140,6 +141,13 @@ static struct checker_class *add_checker_class(const char *multipath_dir,
|
|
if (!c->init)
|
|
goto out;
|
|
|
|
+ c->mp_init = (int (*)(struct checker *)) dlsym(c->handle, "libcheck_mp_init");
|
|
+ errstr = dlerror();
|
|
+ if (errstr != NULL)
|
|
+ condlog(0, "A dynamic linking error occurred: (%s)", errstr);
|
|
+ if (!c->mp_init)
|
|
+ goto out;
|
|
+
|
|
c->free = (void (*)(struct checker *)) dlsym(c->handle, "libcheck_free");
|
|
errstr = dlerror();
|
|
if (errstr != NULL)
|
|
@@ -212,8 +220,25 @@ int checker_init (struct checker * c, void ** mpctxt_addr)
|
|
if (!c || !c->cls)
|
|
return 1;
|
|
c->mpcontext = mpctxt_addr;
|
|
- if (c->cls->init)
|
|
- return c->cls->init(c);
|
|
+ if (c->cls->init && c->cls->init(c) != 0)
|
|
+ return 1;
|
|
+ if (mpctxt_addr && *mpctxt_addr == NULL && c->cls->mp_init &&
|
|
+ c->cls->mp_init(c) != 0) /* continue even if mp_init fails */
|
|
+ c->mpcontext = NULL;
|
|
+ return 0;
|
|
+}
|
|
+
|
|
+int checker_mp_init(struct checker * c, void ** mpctxt_addr)
|
|
+{
|
|
+ if (!c || !c->cls)
|
|
+ return 1;
|
|
+ if (c->cls->mp_init && !c->mpcontext && mpctxt_addr) {
|
|
+ c->mpcontext = mpctxt_addr;
|
|
+ if (c->cls->mp_init(c) != 0) {
|
|
+ c->mpcontext = NULL;
|
|
+ return 1;
|
|
+ }
|
|
+ }
|
|
return 0;
|
|
}
|
|
|
|
diff --git a/libmultipath/checkers.h b/libmultipath/checkers.h
|
|
index dab197f9..5237e7ec 100644
|
|
--- a/libmultipath/checkers.h
|
|
+++ b/libmultipath/checkers.h
|
|
@@ -138,6 +138,7 @@ const char *checker_state_name(int);
|
|
int init_checkers(const char *);
|
|
void cleanup_checkers (void);
|
|
int checker_init (struct checker *, void **);
|
|
+int checker_mp_init(struct checker *, void **);
|
|
void checker_clear (struct checker *);
|
|
void checker_put (struct checker *);
|
|
void checker_reset (struct checker *);
|
|
diff --git a/libmultipath/checkers/cciss_tur.c b/libmultipath/checkers/cciss_tur.c
|
|
index ea843742..b570ed65 100644
|
|
--- a/libmultipath/checkers/cciss_tur.c
|
|
+++ b/libmultipath/checkers/cciss_tur.c
|
|
@@ -51,6 +51,11 @@ int libcheck_init (struct checker * c)
|
|
return 0;
|
|
}
|
|
|
|
+int libcheck_mp_init (struct checker * c)
|
|
+{
|
|
+ return 0;
|
|
+}
|
|
+
|
|
void libcheck_free (struct checker * c)
|
|
{
|
|
return;
|
|
diff --git a/libmultipath/checkers/directio.c b/libmultipath/checkers/directio.c
|
|
index 1b00b775..96f223b2 100644
|
|
--- a/libmultipath/checkers/directio.c
|
|
+++ b/libmultipath/checkers/directio.c
|
|
@@ -103,6 +103,11 @@ out:
|
|
return 1;
|
|
}
|
|
|
|
+int libcheck_mp_init(struct checker * c)
|
|
+{
|
|
+ return 0;
|
|
+}
|
|
+
|
|
void libcheck_free (struct checker * c)
|
|
{
|
|
struct directio_context * ct = (struct directio_context *)c->context;
|
|
diff --git a/libmultipath/checkers/emc_clariion.c b/libmultipath/checkers/emc_clariion.c
|
|
index 6fc89113..5cd63aca 100644
|
|
--- a/libmultipath/checkers/emc_clariion.c
|
|
+++ b/libmultipath/checkers/emc_clariion.c
|
|
@@ -107,11 +107,18 @@ int libcheck_init (struct checker * c)
|
|
return 1;
|
|
((struct emc_clariion_checker_path_context *)c->context)->wwn_set = 0;
|
|
|
|
+ return 0;
|
|
+}
|
|
+
|
|
+int libcheck_mp_init (struct checker * c)
|
|
+{
|
|
/*
|
|
* Allocate and initialize the multi-path global context.
|
|
*/
|
|
if (c->mpcontext && *c->mpcontext == NULL) {
|
|
void * mpctxt = malloc(sizeof(int));
|
|
+ if (!mpctxt)
|
|
+ return 1;
|
|
*c->mpcontext = mpctxt;
|
|
CLR_INACTIVE_SNAP(c);
|
|
}
|
|
diff --git a/libmultipath/checkers/hp_sw.c b/libmultipath/checkers/hp_sw.c
|
|
index 1a820223..35aca204 100644
|
|
--- a/libmultipath/checkers/hp_sw.c
|
|
+++ b/libmultipath/checkers/hp_sw.c
|
|
@@ -37,6 +37,11 @@ int libcheck_init (struct checker * c)
|
|
return 0;
|
|
}
|
|
|
|
+int libcheck_mp_init(struct checker * c)
|
|
+{
|
|
+ return 0;
|
|
+}
|
|
+
|
|
void libcheck_free (struct checker * c)
|
|
{
|
|
return;
|
|
diff --git a/libmultipath/checkers/rdac.c b/libmultipath/checkers/rdac.c
|
|
index 8a3b73ec..805d153e 100644
|
|
--- a/libmultipath/checkers/rdac.c
|
|
+++ b/libmultipath/checkers/rdac.c
|
|
@@ -133,6 +133,11 @@ out:
|
|
return 0;
|
|
}
|
|
|
|
+int libcheck_mp_init(struct checker * c)
|
|
+{
|
|
+ return 0;
|
|
+}
|
|
+
|
|
void libcheck_free (struct checker * c)
|
|
{
|
|
return;
|
|
diff --git a/libmultipath/checkers/readsector0.c b/libmultipath/checkers/readsector0.c
|
|
index cf79e067..71db9f80 100644
|
|
--- a/libmultipath/checkers/readsector0.c
|
|
+++ b/libmultipath/checkers/readsector0.c
|
|
@@ -15,6 +15,11 @@ int libcheck_init (struct checker * c)
|
|
return 0;
|
|
}
|
|
|
|
+int libcheck_mp_init(struct checker * c)
|
|
+{
|
|
+ return 0;
|
|
+}
|
|
+
|
|
void libcheck_free (struct checker * c)
|
|
{
|
|
return;
|
|
diff --git a/libmultipath/checkers/tur.c b/libmultipath/checkers/tur.c
|
|
index 6b08dbbb..138b9e58 100644
|
|
--- a/libmultipath/checkers/tur.c
|
|
+++ b/libmultipath/checkers/tur.c
|
|
@@ -79,6 +79,11 @@ int libcheck_init (struct checker * c)
|
|
return 0;
|
|
}
|
|
|
|
+int libcheck_mp_init(struct checker * c)
|
|
+{
|
|
+ return 0;
|
|
+}
|
|
+
|
|
static void cleanup_context(struct tur_checker_context *ct)
|
|
{
|
|
pthread_mutex_destroy(&ct->lock);
|
|
diff --git a/libmultipath/discovery.c b/libmultipath/discovery.c
|
|
index acca466c..72f455e8 100644
|
|
--- a/libmultipath/discovery.c
|
|
+++ b/libmultipath/discovery.c
|
|
@@ -1608,6 +1608,8 @@ get_state (struct path * pp, struct config *conf, int daemon, int oldstate)
|
|
return PATH_UNCHECKED;
|
|
}
|
|
}
|
|
+ if (pp->mpp && !c->mpcontext)
|
|
+ checker_mp_init(c, &pp->mpp->mpcontext);
|
|
checker_clear_message(c);
|
|
if (daemon) {
|
|
if (conf->force_sync == 0)
|
|
--
|
|
2.17.2
|
|
|