summaryrefslogtreecommitdiffstats
path: root/0052-RHBZ-601247-fix-path-adoption.patch
blob: 12fe73d1617c0b75cac75e236b04bb925aeeb1e5 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
---
 libmultipath/structs_vec.c |   42 ++++++++++++++++++++++++++----------------
 libmultipath/structs_vec.h |    2 +-
 multipathd/main.c          |    2 +-
 3 files changed, 28 insertions(+), 18 deletions(-)

Index: multipath-tools/libmultipath/structs_vec.c
===================================================================
--- multipath-tools.orig/libmultipath/structs_vec.c
+++ multipath-tools/libmultipath/structs_vec.c
@@ -45,8 +45,15 @@ update_mpp_paths(struct multipath * mpp,
 	return 0;
 }
 
+/* Getting the pathinfo for paths we already have seems like a hack.
+ * It's necessary since sometimes a multipath device we get from the
+ * kernel conatains paths that aren't in our pathvector.  In this case
+ * we need to add the paths just like any other, making sure
+ * that we only accept paths that are allowed by our configuration.
+ */
+
 extern int
-adopt_paths (vector pathvec, struct multipath * mpp)
+adopt_paths (vector pathvec, struct multipath * mpp, int verify_all)
 {
 	int i;
 	struct path * pp;
@@ -58,19 +65,22 @@ adopt_paths (vector pathvec, struct mult
 		return 1;
 
 	vector_foreach_slot (pathvec, pp, i) {
-		if (!strncmp(mpp->wwid, pp->wwid, WWID_SIZE)) {
-			condlog(3, "%s: ownership set to %s",
-				pp->dev, mpp->alias);
-			pp->mpp = mpp;
-
-			if (!mpp->paths && !(mpp->paths = vector_alloc()))
-				return 1;
-
-			if (!find_path_by_dev(mpp->paths, pp->dev) &&
-			    store_path(mpp->paths, pp))
-					return 1;
-			pathinfo(pp, conf->hwtable, DI_PRIO | DI_CHECKER);
+		if (strncmp(mpp->wwid, pp->wwid, WWID_SIZE))
+			continue;
+		condlog(3, "%s: ownership set to %s", pp->dev, mpp->alias);
+		pp->mpp = mpp;
+
+		if (!mpp->paths && !(mpp->paths = vector_alloc()))
+			return 1;
+
+		if (find_path_by_dev(mpp->paths, pp->dev)) {
+			if (!verify_all)
+				continue;
 		}
+		else if (store_path(mpp->paths, pp))
+			return 1;
+
+		pathinfo(pp, conf->hwtable, DI_PRIO | DI_CHECKER);
 	}
 	return 0;
 }
@@ -389,7 +399,7 @@ add_map_without_path (struct vectors * v
 		return NULL; /* mpp freed in setup_multipath */
 	}
 
-	if (adopt_paths(vecs->pathvec, mpp))
+	if (adopt_paths(vecs->pathvec, mpp, 1))
 		goto out;
 
 	if (!vector_alloc_slot(vecs->mpvec))
@@ -422,7 +432,7 @@ add_map_with_path (struct vectors * vecs
 	select_alias(mpp);
 	mpp->size = pp->size;
 
-	if (adopt_paths(vecs->pathvec, mpp))
+	if (adopt_paths(vecs->pathvec, mpp, 1))
 		goto out;
 
 	if (add_vec) {
@@ -497,7 +507,7 @@ int update_multipath (struct vectors *ve
 	if (setup_multipath(vecs, mpp))
 		return 1; /* mpp freed in setup_multipath */
 
-	adopt_paths(vecs->pathvec, mpp);
+	adopt_paths(vecs->pathvec, mpp, 0);
 	/*
 	 * compare checkers states with DM states
 	 */
Index: multipath-tools/multipathd/main.c
===================================================================
--- multipath-tools.orig/multipathd/main.c
+++ multipath-tools/multipathd/main.c
@@ -413,7 +413,7 @@ rescan:
 	if (mpp) {
 		condlog(4,"%s: adopting all paths for path %s",
 			mpp->alias, pp->dev);
-		if (adopt_paths(vecs->pathvec, mpp))
+		if (adopt_paths(vecs->pathvec, mpp, 1))
 			goto fail; /* leave path added to pathvec */
 
 		verify_paths(mpp, vecs, NULL);
Index: multipath-tools/libmultipath/structs_vec.h
===================================================================
--- multipath-tools.orig/libmultipath/structs_vec.h
+++ multipath-tools/libmultipath/structs_vec.h
@@ -15,7 +15,7 @@ struct vectors {
 
 void set_no_path_retry(struct multipath *mpp);
 
-int adopt_paths (vector pathvec, struct multipath * mpp);
+int adopt_paths (vector pathvec, struct multipath * mpp, int verify_all);
 void orphan_paths (vector pathvec, struct multipath * mpp);
 void orphan_path (struct path * pp);