libmultipath: propsel: don't print undefined values
[multipath-tools/.git] / libmultipath / propsel.c
1 /*
2  * Copyright (c) 2004, 2005 Christophe Varoqui
3  * Copyright (c) 2005 Benjamin Marzinski, Redhat
4  * Copyright (c) 2005 Kiyoshi Ueda, NEC
5  */
6 #include <stdio.h>
7
8 #include "checkers.h"
9 #include "memory.h"
10 #include "vector.h"
11 #include "structs.h"
12 #include "config.h"
13 #include "debug.h"
14 #include "pgpolicies.h"
15 #include "alias.h"
16 #include "defaults.h"
17 #include "devmapper.h"
18 #include "prio.h"
19 #include "discovery.h"
20 #include "dict.h"
21 #include "util.h"
22 #include "sysfs.h"
23 #include "prioritizers/alua_rtpg.h"
24 #include "prkey.h"
25 #include "propsel.h"
26 #include <inttypes.h>
27 #include <libudev.h>
28
29 pgpolicyfn *pgpolicies[] = {
30         NULL,
31         one_path_per_group,
32         one_group,
33         group_by_serial,
34         group_by_prio,
35         group_by_node_name
36 };
37
38 #define do_set(var, src, dest, msg)                                     \
39 do {                                                                    \
40         if (src && src->var) {                                          \
41                 dest = src->var;                                        \
42                 origin = msg;                                           \
43                 goto out;                                               \
44         }                                                               \
45 } while(0)
46
47 #define do_set_from_vec(type, var, src, dest, msg)                      \
48 do {                                                                    \
49         type *_p;                                                       \
50         int i;                                                          \
51                                                                         \
52         vector_foreach_slot(src, _p, i) {                               \
53                 if (_p->var) {                                          \
54                         dest = _p->var;                                 \
55                         origin = msg;                                   \
56                         goto out;                                       \
57                 }                                                       \
58         }                                                               \
59 } while (0)
60
61 #define do_set_from_hwe(var, src, dest, msg) \
62         do_set_from_vec(struct hwentry, var, src->hwe, dest, msg)
63
64 static const char default_origin[] = "(setting: multipath internal)";
65 static const char hwe_origin[] =
66         "(setting: storage device configuration)";
67 static const char multipaths_origin[] =
68         "(setting: multipath.conf multipaths section)";
69 static const char conf_origin[] =
70         "(setting: multipath.conf defaults/devices section)";
71 static const char overrides_origin[] =
72         "(setting: multipath.conf overrides section)";
73 static const char cmdline_origin[] =
74         "(setting: multipath command line [-p] flag)";
75 static const char autodetect_origin[] =
76         "(setting: storage device autodetected)";
77
78 #define do_default(dest, value)                                         \
79 do {                                                                    \
80         dest = value;                                                   \
81         origin = default_origin;                                        \
82 } while(0)
83
84 #define mp_set_mpe(var)                                                 \
85 do_set(var, mp->mpe, mp->var, multipaths_origin)
86 #define mp_set_hwe(var)                                                 \
87 do_set_from_hwe(var, mp, mp->var, hwe_origin)
88 #define mp_set_ovr(var)                                                 \
89 do_set(var, conf->overrides, mp->var, overrides_origin)
90 #define mp_set_conf(var)                                                \
91 do_set(var, conf, mp->var, conf_origin)
92 #define mp_set_default(var, value)                                      \
93 do_default(mp->var, value)
94
95 #define pp_set_mpe(var)                                                 \
96 do_set(var, mpe, pp->var, multipaths_origin)
97 #define pp_set_hwe(var)                                                 \
98 do_set_from_hwe(var, pp, pp->var, hwe_origin)
99 #define pp_set_conf(var)                                                \
100 do_set(var, conf, pp->var, conf_origin)
101 #define pp_set_ovr(var)                                                 \
102 do_set(var, conf->overrides, pp->var, overrides_origin)
103 #define pp_set_default(var, value)                                      \
104 do_default(pp->var, value)
105
106 #define do_attr_set(var, src, shift, msg)                               \
107 do {                                                                    \
108         if (src && (src->attribute_flags & (1 << shift))) {             \
109                 mp->attribute_flags |= (1 << shift);                    \
110                 mp->var = src->var;                                     \
111                 origin = msg;                                           \
112                 goto out;                                               \
113         }                                                               \
114 } while(0)
115
116 #define set_attr_mpe(var, shift)                                        \
117 do_attr_set(var, mp->mpe, shift, "(setting: multipath.conf multipaths section)")
118 #define set_attr_conf(var, shift)                                       \
119 do_attr_set(var, conf, shift, "(setting: multipath.conf defaults/devices section)")
120
121 #define do_prkey_set(src, msg)                                          \
122 do {                                                                    \
123         if (src && src->prkey_source != PRKEY_SOURCE_NONE) {            \
124                 mp->prkey_source = src->prkey_source;                   \
125                 mp->reservation_key = src->reservation_key;             \
126                 mp->sa_flags = src->sa_flags;                           \
127                 origin = msg;                                           \
128                 goto out;                                               \
129         }                                                               \
130 } while (0)
131
132 int select_mode(struct config *conf, struct multipath *mp)
133 {
134         const char *origin;
135
136         set_attr_mpe(mode, ATTR_MODE);
137         set_attr_conf(mode, ATTR_MODE);
138         mp->attribute_flags &= ~(1 << ATTR_MODE);
139         return 0;
140 out:
141         condlog(3, "%s: mode = 0%o %s", mp->alias, mp->mode, origin);
142         return 0;
143 }
144
145 int select_uid(struct config *conf, struct multipath *mp)
146 {
147         const char *origin;
148
149         set_attr_mpe(uid, ATTR_UID);
150         set_attr_conf(uid, ATTR_UID);
151         mp->attribute_flags &= ~(1 << ATTR_UID);
152         return 0;
153 out:
154         condlog(3, "%s: uid = 0%o %s", mp->alias, mp->uid, origin);
155         return 0;
156 }
157
158 int select_gid(struct config *conf, struct multipath *mp)
159 {
160         const char *origin;
161
162         set_attr_mpe(gid, ATTR_GID);
163         set_attr_conf(gid, ATTR_GID);
164         mp->attribute_flags &= ~(1 << ATTR_GID);
165         return 0;
166 out:
167         condlog(3, "%s: gid = 0%o %s", mp->alias, mp->gid, origin);
168         return 0;
169 }
170
171 /*
172  * selectors :
173  * traverse the configuration layers from most specific to most generic
174  * stop at first explicit setting found
175  */
176 int select_rr_weight(struct config *conf, struct multipath * mp)
177 {
178         const char *origin;
179         char buff[13];
180
181         mp_set_mpe(rr_weight);
182         mp_set_ovr(rr_weight);
183         mp_set_hwe(rr_weight);
184         mp_set_conf(rr_weight);
185         mp_set_default(rr_weight, DEFAULT_RR_WEIGHT);
186 out:
187         print_rr_weight(buff, 13, mp->rr_weight);
188         condlog(3, "%s: rr_weight = %s %s", mp->alias, buff, origin);
189         return 0;
190 }
191
192 int select_pgfailback(struct config *conf, struct multipath * mp)
193 {
194         const char *origin;
195         char buff[13];
196
197         mp_set_mpe(pgfailback);
198         mp_set_ovr(pgfailback);
199         mp_set_hwe(pgfailback);
200         mp_set_conf(pgfailback);
201         mp_set_default(pgfailback, DEFAULT_FAILBACK);
202 out:
203         print_pgfailback(buff, 13, mp->pgfailback);
204         condlog(3, "%s: failback = %s %s", mp->alias, buff, origin);
205         return 0;
206 }
207
208 int select_pgpolicy(struct config *conf, struct multipath * mp)
209 {
210         const char *origin;
211         char buff[POLICY_NAME_SIZE];
212
213         if (conf->pgpolicy_flag > 0) {
214                 mp->pgpolicy = conf->pgpolicy_flag;
215                 origin = cmdline_origin;
216                 goto out;
217         }
218         mp_set_mpe(pgpolicy);
219         mp_set_ovr(pgpolicy);
220         mp_set_hwe(pgpolicy);
221         mp_set_conf(pgpolicy);
222         mp_set_default(pgpolicy, DEFAULT_PGPOLICY);
223 out:
224         mp->pgpolicyfn = pgpolicies[mp->pgpolicy];
225         get_pgpolicy_name(buff, POLICY_NAME_SIZE, mp->pgpolicy);
226         condlog(3, "%s: path_grouping_policy = %s %s", mp->alias, buff, origin);
227         return 0;
228 }
229
230 int select_selector(struct config *conf, struct multipath * mp)
231 {
232         const char *origin;
233
234         mp_set_mpe(selector);
235         mp_set_ovr(selector);
236         mp_set_hwe(selector);
237         mp_set_conf(selector);
238         mp_set_default(selector, DEFAULT_SELECTOR);
239 out:
240         mp->selector = STRDUP(mp->selector);
241         condlog(3, "%s: path_selector = \"%s\" %s", mp->alias, mp->selector,
242                 origin);
243         return 0;
244 }
245
246 static void
247 select_alias_prefix (struct config *conf, struct multipath * mp)
248 {
249         const char *origin;
250
251         mp_set_ovr(alias_prefix);
252         mp_set_hwe(alias_prefix);
253         mp_set_conf(alias_prefix);
254         mp_set_default(alias_prefix, DEFAULT_ALIAS_PREFIX);
255 out:
256         condlog(3, "%s: alias_prefix = %s %s", mp->wwid, mp->alias_prefix,
257                 origin);
258 }
259
260 static int
261 want_user_friendly_names(struct config *conf, struct multipath * mp)
262 {
263
264         const char *origin;
265         int user_friendly_names;
266
267         do_set(user_friendly_names, mp->mpe, user_friendly_names,
268                multipaths_origin);
269         do_set(user_friendly_names, conf->overrides, user_friendly_names,
270                overrides_origin);
271         do_set_from_hwe(user_friendly_names, mp, user_friendly_names,
272                         hwe_origin);
273         do_set(user_friendly_names, conf, user_friendly_names,
274                conf_origin);
275         do_default(user_friendly_names, DEFAULT_USER_FRIENDLY_NAMES);
276 out:
277         condlog(3, "%s: user_friendly_names = %s %s", mp->wwid,
278                 (user_friendly_names == USER_FRIENDLY_NAMES_ON)? "yes" : "no",
279                 origin);
280         return (user_friendly_names == USER_FRIENDLY_NAMES_ON);
281 }
282
283 int select_alias(struct config *conf, struct multipath * mp)
284 {
285         const char *origin = NULL;
286
287         if (mp->mpe && mp->mpe->alias) {
288                 mp->alias = STRDUP(mp->mpe->alias);
289                 origin = multipaths_origin;
290                 goto out;
291         }
292
293         mp->alias = NULL;
294         if (!want_user_friendly_names(conf, mp))
295                 goto out;
296
297         select_alias_prefix(conf, mp);
298
299         if (strlen(mp->alias_old) > 0) {
300                 mp->alias = use_existing_alias(mp->wwid, conf->bindings_file,
301                                 mp->alias_old, mp->alias_prefix,
302                                 conf->bindings_read_only);
303                 memset (mp->alias_old, 0, WWID_SIZE);
304                 origin = "(setting: using existing alias)";
305         }
306
307         if (mp->alias == NULL) {
308                 mp->alias = get_user_friendly_alias(mp->wwid,
309                                 conf->bindings_file, mp->alias_prefix, conf->bindings_read_only);
310                 origin = "(setting: user_friendly_name)";
311         }
312 out:
313         if (mp->alias == NULL) {
314                 mp->alias = STRDUP(mp->wwid);
315                 origin = "(setting: default to WWID)";
316         }
317         if (mp->alias)
318                 condlog(3, "%s: alias = %s %s", mp->wwid, mp->alias, origin);
319         return mp->alias ? 0 : 1;
320 }
321
322 void reconcile_features_with_options(const char *id, char **features, int* no_path_retry,
323                   int *retain_hwhandler)
324 {
325         static const char q_i_n_p[] = "queue_if_no_path";
326         static const char r_a_h_h[] = "retain_attached_hw_handler";
327         char buff[12];
328
329         if (*features == NULL)
330                 return;
331         if (id == NULL)
332                 id = "UNKNOWN";
333
334         /*
335          * We only use no_path_retry internally. The "queue_if_no_path"
336          * device-mapper feature is derived from it when the map is loaded.
337          * For consistency, "queue_if_no_path" is removed from the
338          * internal libmultipath features string.
339          * For backward compatibility we allow 'features "1 queue_if_no_path"';
340          * it's translated into "no_path_retry queue" here.
341          */
342         if (strstr(*features, q_i_n_p)) {
343                 condlog(0, "%s: option 'features \"1 %s\"' is deprecated, "
344                         "please use 'no_path_retry queue' instead",
345                         id, q_i_n_p);
346                 if (*no_path_retry == NO_PATH_RETRY_UNDEF) {
347                         *no_path_retry = NO_PATH_RETRY_QUEUE;
348                         print_no_path_retry(buff, sizeof(buff),
349                                             *no_path_retry);
350                         condlog(3, "%s: no_path_retry = %s (inherited setting from feature '%s')",
351                                 id, buff, q_i_n_p);
352                 };
353                 /* Warn only if features string is overridden */
354                 if (*no_path_retry != NO_PATH_RETRY_QUEUE) {
355                         print_no_path_retry(buff, sizeof(buff),
356                                             *no_path_retry);
357                         condlog(2, "%s: ignoring feature '%s' because no_path_retry is set to '%s'",
358                                 id, q_i_n_p, buff);
359                 }
360                 remove_feature(features, q_i_n_p);
361         }
362         if (strstr(*features, r_a_h_h)) {
363                 condlog(0, "%s: option 'features \"1 %s\"' is deprecated",
364                         id, r_a_h_h);
365                 if (*retain_hwhandler == RETAIN_HWHANDLER_UNDEF) {
366                         condlog(3, "%s: %s = on (inherited setting from feature '%s')",
367                                 id, r_a_h_h, r_a_h_h);
368                         *retain_hwhandler = RETAIN_HWHANDLER_ON;
369                 } else if (*retain_hwhandler == RETAIN_HWHANDLER_OFF)
370                         condlog(2, "%s: ignoring feature '%s' because %s is set to 'off'",
371                                 id, r_a_h_h, r_a_h_h);
372                 remove_feature(features, r_a_h_h);
373         }
374 }
375
376 int select_features(struct config *conf, struct multipath *mp)
377 {
378         const char *origin;
379
380         mp_set_mpe(features);
381         mp_set_ovr(features);
382         mp_set_hwe(features);
383         mp_set_conf(features);
384         mp_set_default(features, DEFAULT_FEATURES);
385 out:
386         mp->features = STRDUP(mp->features);
387
388         reconcile_features_with_options(mp->alias, &mp->features,
389                                         &mp->no_path_retry,
390                                         &mp->retain_hwhandler);
391         condlog(3, "%s: features = \"%s\" %s", mp->alias, mp->features, origin);
392         return 0;
393 }
394
395 static int get_dh_state(struct path *pp, char *value, size_t value_len)
396 {
397         struct udev_device *ud;
398
399         if (pp->udev == NULL)
400                 return -1;
401
402         ud = udev_device_get_parent_with_subsystem_devtype(
403                 pp->udev, "scsi", "scsi_device");
404         if (ud == NULL)
405                 return -1;
406
407         return sysfs_attr_get_value(ud, "dh_state", value, value_len);
408 }
409
410 int select_hwhandler(struct config *conf, struct multipath *mp)
411 {
412         const char *origin;
413         struct path *pp;
414         /* dh_state is no longer than "detached" */
415         char handler[12];
416         static char alua_name[] = "1 alua";
417         static const char tpgs_origin[]= "(setting: autodetected from TPGS)";
418         char *dh_state;
419         int i;
420         bool all_tpgs = true;
421
422         dh_state = &handler[2];
423
424         vector_foreach_slot(mp->paths, pp, i)
425                 all_tpgs = all_tpgs && (pp->tpgs > 0);
426         if (mp->retain_hwhandler != RETAIN_HWHANDLER_OFF) {
427                 vector_foreach_slot(mp->paths, pp, i) {
428                         if (get_dh_state(pp, dh_state, sizeof(handler) - 2) > 0
429                             && strcmp(dh_state, "detached")) {
430                                 memcpy(handler, "1 ", 2);
431                                 mp->hwhandler = handler;
432                                 origin = "(setting: retained by kernel driver)";
433                                 goto out;
434                         }
435                 }
436         }
437
438         mp_set_hwe(hwhandler);
439         mp_set_conf(hwhandler);
440         mp_set_default(hwhandler, DEFAULT_HWHANDLER);
441 out:
442         if (all_tpgs && !strcmp(mp->hwhandler, DEFAULT_HWHANDLER) &&
443                 origin == default_origin) {
444                 mp->hwhandler = alua_name;
445                 origin = tpgs_origin;
446         } else if (!all_tpgs && !strcmp(mp->hwhandler, alua_name)) {
447                 mp->hwhandler = DEFAULT_HWHANDLER;
448                 origin = tpgs_origin;
449         }
450         mp->hwhandler = STRDUP(mp->hwhandler);
451         condlog(3, "%s: hardware_handler = \"%s\" %s", mp->alias, mp->hwhandler,
452                 origin);
453         return 0;
454 }
455
456 /*
457  * Current RDAC (NetApp E-Series) firmware relies
458  * on periodic REPORT TARGET PORT GROUPS for
459  * internal load balancing.
460  * Using the sysfs priority checker defeats this purpose.
461  *
462  * Moreover, NetApp would also prefer the RDAC checker over ALUA.
463  * (https://www.redhat.com/archives/dm-devel/2017-September/msg00326.html)
464  */
465 static int
466 check_rdac(struct path * pp)
467 {
468         int len;
469         char buff[44];
470
471         if (pp->bus != SYSFS_BUS_SCSI)
472                 return 0;
473         len = get_vpd_sgio(pp->fd, 0xC9, buff, 44);
474         if (len <= 0)
475                 return 0;
476         return !(memcmp(buff + 4, "vac1", 4));
477 }
478
479 int select_checker(struct config *conf, struct path *pp)
480 {
481         const char *origin;
482         char *ckr_name;
483         struct checker * c = &pp->checker;
484
485         if (pp->detect_checker == DETECT_CHECKER_ON) {
486                 origin = autodetect_origin;
487                 if (check_rdac(pp)) {
488                         ckr_name = RDAC;
489                         goto out;
490                 } else if (pp->tpgs > 0) {
491                         ckr_name = TUR;
492                         goto out;
493                 }
494         }
495         do_set(checker_name, conf->overrides, ckr_name, overrides_origin);
496         do_set_from_hwe(checker_name, pp, ckr_name, hwe_origin);
497         do_set(checker_name, conf, ckr_name, conf_origin);
498         do_default(ckr_name, DEFAULT_CHECKER);
499 out:
500         checker_get(conf->multipath_dir, c, ckr_name);
501         condlog(3, "%s: path_checker = %s %s", pp->dev,
502                 checker_name(c), origin);
503         if (conf->checker_timeout) {
504                 c->timeout = conf->checker_timeout;
505                 condlog(3, "%s: checker timeout = %u s %s",
506                         pp->dev, c->timeout, conf_origin);
507         }
508         else if (sysfs_get_timeout(pp, &c->timeout) > 0)
509                 condlog(3, "%s: checker timeout = %u s (setting: kernel sysfs)",
510                         pp->dev, c->timeout);
511         else {
512                 c->timeout = DEF_TIMEOUT;
513                 condlog(3, "%s: checker timeout = %u s %s",
514                         pp->dev, c->timeout, default_origin);
515         }
516         return 0;
517 }
518
519 int select_getuid(struct config *conf, struct path *pp)
520 {
521         const char *origin;
522
523         pp->uid_attribute = parse_uid_attribute_by_attrs(conf->uid_attrs, pp->dev);
524         if (pp->uid_attribute) {
525                 origin = "(setting: multipath.conf defaults section)";
526                 goto out;
527         }
528
529         pp_set_ovr(getuid);
530         pp_set_ovr(uid_attribute);
531         pp_set_hwe(getuid);
532         pp_set_hwe(uid_attribute);
533         pp_set_conf(getuid);
534         pp_set_conf(uid_attribute);
535         pp_set_default(uid_attribute, DEFAULT_UID_ATTRIBUTE);
536 out:
537         if (pp->uid_attribute)
538                 condlog(3, "%s: uid_attribute = %s %s", pp->dev,
539                         pp->uid_attribute, origin);
540         else if (pp->getuid)
541                 condlog(3, "%s: getuid = \"%s\" %s", pp->dev, pp->getuid,
542                         origin);
543         return 0;
544 }
545
546 void
547 detect_prio(struct config *conf, struct path * pp)
548 {
549         struct prio *p = &pp->prio;
550         char buff[512];
551         char *default_prio = PRIO_ALUA;
552
553         if (pp->tpgs <= 0)
554                 return;
555         if (pp->tpgs == 2 || !check_rdac(pp)) {
556                 if (sysfs_get_asymmetric_access_state(pp, buff, 512) >= 0)
557                         default_prio = PRIO_SYSFS;
558         }
559         prio_get(conf->multipath_dir, p, default_prio, DEFAULT_PRIO_ARGS);
560 }
561
562 #define set_prio(dir, src, msg)                                 \
563 do {                                                                    \
564         if (src && src->prio_name) {                                    \
565                 prio_get(dir, p, src->prio_name, src->prio_args);       \
566                 origin = msg;                                           \
567                 goto out;                                               \
568         }                                                               \
569 } while(0)
570
571 #define set_prio_from_vec(type, dir, src, msg, p)                       \
572 do {                                                                    \
573         type *_p;                                                       \
574         int i;                                                          \
575         char *prio_name = NULL, *prio_args = NULL;                      \
576                                                                         \
577         vector_foreach_slot(src, _p, i) {                               \
578                 if (prio_name == NULL && _p->prio_name)         \
579                         prio_name = _p->prio_name;                      \
580                 if (prio_args == NULL && _p->prio_args)         \
581                         prio_args = _p->prio_args;                      \
582         }                                                               \
583         if (prio_name != NULL) {                                        \
584                 prio_get(dir, p, prio_name, prio_args);                 \
585                 origin = msg;                                           \
586                 goto out;                                               \
587         }                                                               \
588 } while (0)
589
590 int select_prio(struct config *conf, struct path *pp)
591 {
592         const char *origin;
593         struct mpentry * mpe;
594         struct prio * p = &pp->prio;
595
596         if (pp->detect_prio == DETECT_PRIO_ON) {
597                 detect_prio(conf, pp);
598                 if (prio_selected(p)) {
599                         origin = autodetect_origin;
600                         goto out;
601                 }
602         }
603         mpe = find_mpe(conf->mptable, pp->wwid);
604         set_prio(conf->multipath_dir, mpe, multipaths_origin);
605         set_prio(conf->multipath_dir, conf->overrides, overrides_origin);
606         set_prio_from_vec(struct hwentry, conf->multipath_dir,
607                           pp->hwe, hwe_origin, p);
608         set_prio(conf->multipath_dir, conf, conf_origin);
609         prio_get(conf->multipath_dir, p, DEFAULT_PRIO, DEFAULT_PRIO_ARGS);
610         origin = default_origin;
611 out:
612         /*
613          * fetch tpgs mode for alua, if its not already obtained
614          */
615         if (!strncmp(prio_name(p), PRIO_ALUA, PRIO_NAME_LEN)) {
616                 int tpgs = 0;
617                 unsigned int timeout = conf->checker_timeout;
618
619                 if(!pp->tpgs &&
620                    (tpgs = get_target_port_group_support(pp->fd, timeout)) >= 0)
621                         pp->tpgs = tpgs;
622         }
623         condlog(3, "%s: prio = %s %s", pp->dev, prio_name(p), origin);
624         condlog(3, "%s: prio args = \"%s\" %s", pp->dev, prio_args(p), origin);
625         return 0;
626 }
627
628 int select_no_path_retry(struct config *conf, struct multipath *mp)
629 {
630         const char *origin = NULL;
631         char buff[12];
632
633         if (mp->disable_queueing) {
634                 condlog(0, "%s: queueing disabled", mp->alias);
635                 mp->no_path_retry = NO_PATH_RETRY_FAIL;
636                 return 0;
637         }
638         mp_set_mpe(no_path_retry);
639         mp_set_ovr(no_path_retry);
640         mp_set_hwe(no_path_retry);
641         mp_set_conf(no_path_retry);
642 out:
643         print_no_path_retry(buff, 12, mp->no_path_retry);
644         if (origin)
645                 condlog(3, "%s: no_path_retry = %s %s", mp->alias, buff,
646                         origin);
647         else
648                 condlog(3, "%s: no_path_retry = undef %s",
649                         mp->alias, default_origin);
650         return 0;
651 }
652
653 int
654 select_minio_rq (struct config *conf, struct multipath * mp)
655 {
656         const char *origin;
657
658         do_set(minio_rq, mp->mpe, mp->minio, multipaths_origin);
659         do_set(minio_rq, conf->overrides, mp->minio, overrides_origin);
660         do_set_from_hwe(minio_rq, mp, mp->minio, hwe_origin);
661         do_set(minio_rq, conf, mp->minio, conf_origin);
662         do_default(mp->minio, DEFAULT_MINIO_RQ);
663 out:
664         condlog(3, "%s: minio = %i %s", mp->alias, mp->minio, origin);
665         return 0;
666 }
667
668 int
669 select_minio_bio (struct config *conf, struct multipath * mp)
670 {
671         const char *origin;
672
673         mp_set_mpe(minio);
674         mp_set_ovr(minio);
675         mp_set_hwe(minio);
676         mp_set_conf(minio);
677         mp_set_default(minio, DEFAULT_MINIO);
678 out:
679         condlog(3, "%s: minio = %i %s", mp->alias, mp->minio, origin);
680         return 0;
681 }
682
683 int select_minio(struct config *conf, struct multipath *mp)
684 {
685         unsigned int minv_dmrq[3] = {1, 1, 0};
686
687         if (VERSION_GE(conf->version, minv_dmrq))
688                 return select_minio_rq(conf, mp);
689         else
690                 return select_minio_bio(conf, mp);
691 }
692
693 int select_fast_io_fail(struct config *conf, struct multipath *mp)
694 {
695         const char *origin;
696         char buff[12];
697
698         mp_set_ovr(fast_io_fail);
699         mp_set_hwe(fast_io_fail);
700         mp_set_conf(fast_io_fail);
701         mp_set_default(fast_io_fail, DEFAULT_FAST_IO_FAIL);
702 out:
703         print_fast_io_fail(buff, 12, mp->fast_io_fail);
704         condlog(3, "%s: fast_io_fail_tmo = %s %s", mp->alias, buff, origin);
705         return 0;
706 }
707
708 int select_dev_loss(struct config *conf, struct multipath *mp)
709 {
710         const char *origin;
711         char buff[12];
712
713         mp_set_ovr(dev_loss);
714         mp_set_hwe(dev_loss);
715         mp_set_conf(dev_loss);
716         mp->dev_loss = 0;
717         return 0;
718 out:
719         print_dev_loss(buff, 12, mp->dev_loss);
720         condlog(3, "%s: dev_loss_tmo = %s %s", mp->alias, buff, origin);
721         return 0;
722 }
723
724 int select_flush_on_last_del(struct config *conf, struct multipath *mp)
725 {
726         const char *origin;
727
728         mp_set_mpe(flush_on_last_del);
729         mp_set_ovr(flush_on_last_del);
730         mp_set_hwe(flush_on_last_del);
731         mp_set_conf(flush_on_last_del);
732         mp_set_default(flush_on_last_del, DEFAULT_FLUSH);
733 out:
734         condlog(3, "%s: flush_on_last_del = %s %s", mp->alias,
735                 (mp->flush_on_last_del == FLUSH_ENABLED)? "yes" : "no", origin);
736         return 0;
737 }
738
739 int select_reservation_key(struct config *conf, struct multipath *mp)
740 {
741         const char *origin;
742         char buff[PRKEY_SIZE];
743         char *from_file = "";
744         uint64_t prkey = 0;
745
746         do_prkey_set(mp->mpe, multipaths_origin);
747         do_prkey_set(conf, conf_origin);
748         put_be64(mp->reservation_key, 0);
749         mp->sa_flags = 0;
750         mp->prkey_source = PRKEY_SOURCE_NONE;
751         return 0;
752 out:
753         if (mp->prkey_source == PRKEY_SOURCE_FILE) {
754                 from_file = " (from prkeys file)";
755                 if (get_prkey(conf, mp, &prkey, &mp->sa_flags) != 0)
756                         put_be64(mp->reservation_key, 0);
757                 else
758                         put_be64(mp->reservation_key, prkey);
759         }
760         print_reservation_key(buff, PRKEY_SIZE, mp->reservation_key,
761                               mp->sa_flags, mp->prkey_source);
762         condlog(3, "%s: reservation_key = %s %s%s", mp->alias, buff, origin,
763                 from_file);
764         return 0;
765 }
766
767 int select_retain_hwhandler(struct config *conf, struct multipath *mp)
768 {
769         const char *origin;
770         unsigned int minv_dm_retain[3] = {1, 5, 0};
771
772         if (!VERSION_GE(conf->version, minv_dm_retain)) {
773                 mp->retain_hwhandler = RETAIN_HWHANDLER_OFF;
774                 origin = "(setting: WARNING, requires kernel dm-mpath version >= 1.5.0)";
775                 goto out;
776         }
777         if (get_linux_version_code() >= KERNEL_VERSION(4, 3, 0)) {
778                 mp->retain_hwhandler = RETAIN_HWHANDLER_ON;
779                 origin = "(setting: implied in kernel >= 4.3.0)";
780                 goto out;
781         }
782         mp_set_ovr(retain_hwhandler);
783         mp_set_hwe(retain_hwhandler);
784         mp_set_conf(retain_hwhandler);
785         mp_set_default(retain_hwhandler, DEFAULT_RETAIN_HWHANDLER);
786 out:
787         condlog(3, "%s: retain_attached_hw_handler = %s %s", mp->alias,
788                 (mp->retain_hwhandler == RETAIN_HWHANDLER_ON)? "yes" : "no",
789                 origin);
790         return 0;
791 }
792
793 int select_detect_prio(struct config *conf, struct path *pp)
794 {
795         const char *origin;
796
797         pp_set_ovr(detect_prio);
798         pp_set_hwe(detect_prio);
799         pp_set_conf(detect_prio);
800         pp_set_default(detect_prio, DEFAULT_DETECT_PRIO);
801 out:
802         condlog(3, "%s: detect_prio = %s %s", pp->dev,
803                 (pp->detect_prio == DETECT_PRIO_ON)? "yes" : "no", origin);
804         return 0;
805 }
806
807 int select_detect_checker(struct config *conf, struct path *pp)
808 {
809         const char *origin;
810
811         pp_set_ovr(detect_checker);
812         pp_set_hwe(detect_checker);
813         pp_set_conf(detect_checker);
814         pp_set_default(detect_checker, DEFAULT_DETECT_CHECKER);
815 out:
816         condlog(3, "%s: detect_checker = %s %s", pp->dev,
817                 (pp->detect_checker == DETECT_CHECKER_ON)? "yes" : "no",
818                 origin);
819         return 0;
820 }
821
822 int select_deferred_remove(struct config *conf, struct multipath *mp)
823 {
824         const char *origin;
825
826 #ifndef LIBDM_API_DEFERRED
827         mp->deferred_remove = DEFERRED_REMOVE_OFF;
828         origin = "(setting: WARNING, not compiled with support)";
829         goto out;
830 #endif
831         if (mp->deferred_remove == DEFERRED_REMOVE_IN_PROGRESS) {
832                 condlog(3, "%s: deferred remove in progress", mp->alias);
833                 return 0;
834         }
835         mp_set_mpe(deferred_remove);
836         mp_set_ovr(deferred_remove);
837         mp_set_hwe(deferred_remove);
838         mp_set_conf(deferred_remove);
839         mp_set_default(deferred_remove, DEFAULT_DEFERRED_REMOVE);
840 out:
841         condlog(3, "%s: deferred_remove = %s %s", mp->alias,
842                 (mp->deferred_remove == DEFERRED_REMOVE_ON)? "yes" : "no",
843                 origin);
844         return 0;
845 }
846
847 int select_delay_watch_checks(struct config *conf, struct multipath *mp)
848 {
849         const char *origin;
850         char buff[12];
851
852         mp_set_mpe(delay_watch_checks);
853         mp_set_ovr(delay_watch_checks);
854         mp_set_hwe(delay_watch_checks);
855         mp_set_conf(delay_watch_checks);
856         mp_set_default(delay_watch_checks, DEFAULT_DELAY_CHECKS);
857 out:
858         if (print_off_int_undef(buff, 12, mp->delay_watch_checks) != 0)
859                 condlog(3, "%s: delay_watch_checks = %s %s",
860                         mp->alias, buff, origin);
861         return 0;
862 }
863
864 int select_delay_wait_checks(struct config *conf, struct multipath *mp)
865 {
866         const char *origin;
867         char buff[12];
868
869         mp_set_mpe(delay_wait_checks);
870         mp_set_ovr(delay_wait_checks);
871         mp_set_hwe(delay_wait_checks);
872         mp_set_conf(delay_wait_checks);
873         mp_set_default(delay_wait_checks, DEFAULT_DELAY_CHECKS);
874 out:
875         if (print_off_int_undef(buff, 12, mp->delay_wait_checks) != 0)
876                 condlog(3, "%s: delay_wait_checks = %s %s",
877                         mp->alias, buff, origin);
878         return 0;
879
880 }
881
882 int select_marginal_path_err_sample_time(struct config *conf, struct multipath *mp)
883 {
884         const char *origin;
885         char buff[12];
886
887         mp_set_mpe(marginal_path_err_sample_time);
888         mp_set_ovr(marginal_path_err_sample_time);
889         mp_set_hwe(marginal_path_err_sample_time);
890         mp_set_conf(marginal_path_err_sample_time);
891         mp_set_default(marginal_path_err_sample_time, DEFAULT_ERR_CHECKS);
892 out:
893         if (print_off_int_undef(buff, 12, mp->marginal_path_err_sample_time)
894             != 0)
895                 condlog(3, "%s: marginal_path_err_sample_time = %s %s",
896                         mp->alias, buff, origin);
897         return 0;
898 }
899
900 int select_marginal_path_err_rate_threshold(struct config *conf, struct multipath *mp)
901 {
902         const char *origin;
903         char buff[12];
904
905         mp_set_mpe(marginal_path_err_rate_threshold);
906         mp_set_ovr(marginal_path_err_rate_threshold);
907         mp_set_hwe(marginal_path_err_rate_threshold);
908         mp_set_conf(marginal_path_err_rate_threshold);
909         mp_set_default(marginal_path_err_rate_threshold, DEFAULT_ERR_CHECKS);
910 out:
911         if (print_off_int_undef(buff, 12, mp->marginal_path_err_rate_threshold)
912             != 0)
913                 condlog(3, "%s: marginal_path_err_rate_threshold = %s %s",
914                         mp->alias, buff, origin);
915         return 0;
916 }
917
918 int select_marginal_path_err_recheck_gap_time(struct config *conf, struct multipath *mp)
919 {
920         const char *origin;
921         char buff[12];
922
923         mp_set_mpe(marginal_path_err_recheck_gap_time);
924         mp_set_ovr(marginal_path_err_recheck_gap_time);
925         mp_set_hwe(marginal_path_err_recheck_gap_time);
926         mp_set_conf(marginal_path_err_recheck_gap_time);
927         mp_set_default(marginal_path_err_recheck_gap_time, DEFAULT_ERR_CHECKS);
928 out:
929         if (print_off_int_undef(buff, 12,
930                                 mp->marginal_path_err_recheck_gap_time) != 0)
931                 condlog(3, "%s: marginal_path_err_recheck_gap_time = %s %s",
932                         mp->alias, buff, origin);
933         return 0;
934 }
935
936 int select_marginal_path_double_failed_time(struct config *conf, struct multipath *mp)
937 {
938         const char *origin;
939         char buff[12];
940
941         mp_set_mpe(marginal_path_double_failed_time);
942         mp_set_ovr(marginal_path_double_failed_time);
943         mp_set_hwe(marginal_path_double_failed_time);
944         mp_set_conf(marginal_path_double_failed_time);
945         mp_set_default(marginal_path_double_failed_time, DEFAULT_ERR_CHECKS);
946 out:
947         if (print_off_int_undef(buff, 12, mp->marginal_path_double_failed_time)
948             != 0)
949                 condlog(3, "%s: marginal_path_double_failed_time = %s %s",
950                         mp->alias, buff, origin);
951         return 0;
952 }
953
954 int select_skip_kpartx (struct config *conf, struct multipath * mp)
955 {
956         const char *origin;
957
958         mp_set_mpe(skip_kpartx);
959         mp_set_ovr(skip_kpartx);
960         mp_set_hwe(skip_kpartx);
961         mp_set_conf(skip_kpartx);
962         mp_set_default(skip_kpartx, DEFAULT_SKIP_KPARTX);
963 out:
964         condlog(3, "%s: skip_kpartx = %s %s", mp->alias,
965                 (mp->skip_kpartx == SKIP_KPARTX_ON)? "yes" : "no",
966                 origin);
967         return 0;
968 }
969
970 int select_max_sectors_kb(struct config *conf, struct multipath * mp)
971 {
972         const char *origin;
973
974         mp_set_mpe(max_sectors_kb);
975         mp_set_ovr(max_sectors_kb);
976         mp_set_hwe(max_sectors_kb);
977         mp_set_conf(max_sectors_kb);
978         mp_set_default(max_sectors_kb, DEFAULT_MAX_SECTORS_KB);
979         /*
980          * In the default case, we will not modify max_sectors_kb in sysfs
981          * (see sysfs_set_max_sectors_kb()).
982          * Don't print a log message here to avoid user confusion.
983          */
984         return 0;
985 out:
986         condlog(3, "%s: max_sectors_kb = %i %s", mp->alias, mp->max_sectors_kb,
987                 origin);
988         return 0;
989 }
990
991 int select_ghost_delay (struct config *conf, struct multipath * mp)
992 {
993         const char *origin;
994         char buff[12];
995
996         mp_set_mpe(ghost_delay);
997         mp_set_ovr(ghost_delay);
998         mp_set_hwe(ghost_delay);
999         mp_set_conf(ghost_delay);
1000         mp_set_default(ghost_delay, DEFAULT_GHOST_DELAY);
1001 out:
1002         if (print_off_int_undef(buff, 12, mp->ghost_delay) != 0)
1003                 condlog(3, "%s: ghost_delay = %s %s", mp->alias, buff, origin);
1004         return 0;
1005 }
1006
1007 int select_find_multipaths_timeout(struct config *conf, struct path *pp)
1008 {
1009         const char *origin;
1010
1011         pp_set_conf(find_multipaths_timeout);
1012         pp_set_default(find_multipaths_timeout,
1013                        DEFAULT_FIND_MULTIPATHS_TIMEOUT);
1014 out:
1015         /*
1016          * If configured value is negative, and this "unknown" hardware
1017          * (no hwentry), use very small timeout to avoid delays.
1018          */
1019         if (pp->find_multipaths_timeout < 0) {
1020                 pp->find_multipaths_timeout = -pp->find_multipaths_timeout;
1021                 if (!pp->hwe) {
1022                         pp->find_multipaths_timeout =
1023                                 DEFAULT_UNKNOWN_FIND_MULTIPATHS_TIMEOUT;
1024                         origin = "(default for unknown hardware)";
1025                 }
1026         }
1027         condlog(3, "%s: timeout for find_multipaths \"smart\" = %ds %s",
1028                 pp->dev, pp->find_multipaths_timeout, origin);
1029         return 0;
1030 }
1031
1032 int select_all_tg_pt (struct config *conf, struct multipath * mp)
1033 {
1034         const char *origin;
1035
1036         mp_set_ovr(all_tg_pt);
1037         mp_set_hwe(all_tg_pt);
1038         mp_set_conf(all_tg_pt);
1039         mp_set_default(all_tg_pt, DEFAULT_ALL_TG_PT);
1040 out:
1041         condlog(3, "%s: all_tg_pt = %s %s", mp->alias,
1042                 (mp->all_tg_pt == ALL_TG_PT_ON)? "yes" : "no",
1043                 origin);
1044         return 0;
1045 }