[libmultipath] fix whitespace errors
[multipath-tools/.git] / libmultipath / dict.c
1 /*
2  * Based on Alexandre Cassen template for keepalived
3  * Copyright (c) 2004, 2005, 2006  Christophe Varoqui
4  * Copyright (c) 2005 Benjamin Marzinski, Redhat
5  * Copyright (c) 2005 Kiyoshi Ueda, NEC
6  */
7 #include <sys/types.h>
8 #include <pwd.h>
9 #include <string.h>
10 #include "checkers.h"
11 #include "vector.h"
12 #include "hwtable.h"
13 #include "structs.h"
14 #include "parser.h"
15 #include "config.h"
16 #include "debug.h"
17 #include "memory.h"
18 #include "pgpolicies.h"
19 #include "blacklist.h"
20 #include "defaults.h"
21 #include "prio.h"
22 #include "errno.h"
23 #include <inttypes.h>
24
25 /*
26  * default block handlers
27  */
28 static int
29 polling_interval_handler(vector strvec)
30 {
31         char * buff;
32
33         buff = VECTOR_SLOT(strvec, 1);
34         conf->checkint = atoi(buff);
35         conf->max_checkint = MAX_CHECKINT(conf->checkint);
36
37         return 0;
38 }
39
40 static int
41 def_fast_io_fail_handler(vector strvec)
42 {
43         char * buff;
44
45         buff = set_value(strvec);
46         if (strlen(buff) == 3 && !strcmp(buff, "off"))
47                 conf->fast_io_fail = MP_FAST_IO_FAIL_OFF;
48         else if (sscanf(buff, "%d", &conf->fast_io_fail) != 1 ||
49                  conf->fast_io_fail < MP_FAST_IO_FAIL_ZERO)
50                 conf->fast_io_fail = MP_FAST_IO_FAIL_UNSET;
51         else if (conf->fast_io_fail == 0)
52                 conf->fast_io_fail = MP_FAST_IO_FAIL_ZERO;
53
54         FREE(buff);
55         return 0;
56 }
57
58 static int
59 def_dev_loss_handler(vector strvec)
60 {
61         char * buff;
62
63         buff = set_value(strvec);
64         if (!buff)
65                 return 1;
66
67         if (strlen(buff) == 8 && !strcmp(buff, "infinity"))
68                 conf->dev_loss = MAX_DEV_LOSS_TMO;
69         else if (sscanf(buff, "%u", &conf->dev_loss) != 1)
70                 conf->dev_loss = 0;
71
72         FREE(buff);
73         return 0;
74 }
75
76 static int
77 verbosity_handler(vector strvec)
78 {
79         char * buff;
80
81         buff = VECTOR_SLOT(strvec, 1);
82         conf->verbosity = atoi(buff);
83
84         return 0;
85 }
86
87 static int
88 max_polling_interval_handler(vector strvec)
89 {
90         char *buff;
91
92         buff = VECTOR_SLOT(strvec, 1);
93         conf->max_checkint = atoi(buff);
94
95         return 0;
96 }
97
98 static int
99 reassign_maps_handler(vector strvec)
100 {
101         char * buff;
102
103         buff = set_value(strvec);
104         if (!strcmp(buff, "yes"))
105                 conf->reassign_maps = 1;
106         else if (!strcmp(buff, "no"))
107                 conf->reassign_maps = 0;
108         else
109                 return 1;
110
111         return 0;
112 }
113
114 static int
115 multipath_dir_handler(vector strvec)
116 {
117         conf->multipath_dir = set_value(strvec);
118
119         if (!conf->multipath_dir)
120                 return 1;
121
122         return 0;
123 }
124
125 static int
126 def_selector_handler(vector strvec)
127 {
128         conf->selector = set_value(strvec);
129
130         if (!conf->selector)
131                 return 1;
132
133         return 0;
134 }
135
136 static int
137 def_pgpolicy_handler(vector strvec)
138 {
139         char * buff;
140
141         buff = set_value(strvec);
142
143         if (!buff)
144                 return 1;
145
146         conf->pgpolicy = get_pgpolicy_id(buff);
147         FREE(buff);
148
149         return 0;
150 }
151
152 static int
153 def_uid_attribute_handler(vector strvec)
154 {
155         conf->uid_attribute = set_value(strvec);
156
157         if (!conf->uid_attribute)
158                 return 1;
159
160         return 0;
161 }
162
163 static int
164 def_prio_handler(vector strvec)
165 {
166         conf->prio_name = set_value(strvec);
167
168         if (!conf->prio_name)
169                 return 1;
170
171         return 0;
172 }
173
174 static int
175 def_alias_prefix_handler(vector strvec)
176 {
177         conf->alias_prefix = set_value(strvec);
178
179         if (!conf->alias_prefix)
180                 return 1;
181
182         return 0;
183 }
184
185 static int
186 def_prio_args_handler(vector strvec)
187 {
188         conf->prio_args = set_value(strvec);
189
190         if (!conf->prio_args)
191                 return 1;
192
193         return 0;
194 }
195
196 static int
197 def_features_handler(vector strvec)
198 {
199         conf->features = set_value(strvec);
200
201         if (!conf->features)
202                 return 1;
203
204         return 0;
205 }
206
207 static int
208 def_path_checker_handler(vector strvec)
209 {
210         conf->checker_name = set_value(strvec);
211
212         if (!conf->checker_name)
213                 return 1;
214
215         return 0;
216 }
217
218 static int
219 def_minio_handler(vector strvec)
220 {
221         char * buff;
222
223         buff = set_value(strvec);
224
225         if (!buff)
226                 return 1;
227
228         conf->minio = atoi(buff);
229         FREE(buff);
230
231         return 0;
232 }
233
234 static int
235 def_minio_rq_handler(vector strvec)
236 {
237         char * buff;
238
239         buff = set_value(strvec);
240
241         if (!buff)
242                 return 1;
243
244         conf->minio_rq = atoi(buff);
245         FREE(buff);
246
247         return 0;
248 }
249
250 int
251 get_sys_max_fds(int *max_fds)
252 {
253         FILE *file;
254         int nr_open;
255         int ret = 1;
256
257         file = fopen("/proc/sys/fs/nr_open", "r");
258         if (!file) {
259                 fprintf(stderr, "Cannot open /proc/sys/fs/nr_open : %s\n",
260                         strerror(errno));
261                 return 1;
262         }
263         if (fscanf(file, "%d", &nr_open) != 1) {
264                 fprintf(stderr, "Cannot read max open fds from /proc/sys/fs/nr_open");
265                 if (ferror(file))
266                         fprintf(stderr, " : %s\n", strerror(errno));
267                 else
268                         fprintf(stderr, "\n");
269         } else {
270                 *max_fds = nr_open;
271                 ret = 0;
272         }
273         fclose(file);
274         return ret;
275 }
276
277
278 static int
279 max_fds_handler(vector strvec)
280 {
281         char * buff;
282         int r = 0;
283
284         buff = set_value(strvec);
285
286         if (!buff)
287                 return 1;
288
289         if (strlen(buff) == 3 &&
290             !strcmp(buff, "max"))
291                 r = get_sys_max_fds(&conf->max_fds);
292         else
293                 conf->max_fds = atoi(buff);
294         FREE(buff);
295
296         return r;
297 }
298
299 static int
300 def_mode_handler(vector strvec)
301 {
302         mode_t mode;
303         char *buff;
304
305         buff = set_value(strvec);
306
307         if (!buff)
308                 return 1;
309
310         if (sscanf(buff, "%o", &mode) == 1 && mode <= 0777) {
311                 conf->attribute_flags |= (1 << ATTR_MODE);
312                 conf->mode = mode;
313         }
314
315         FREE(buff);
316         return 0;
317 }
318
319 static int
320 def_uid_handler(vector strvec)
321 {
322         uid_t uid;
323         char *buff;
324         char passwd_buf[1024];
325         struct passwd info, *found;
326
327         buff = set_value(strvec);
328         if (!buff)
329                 return 1;
330         if (getpwnam_r(buff, &info, passwd_buf, 1024, &found) == 0 && found) {
331                 conf->attribute_flags |= (1 << ATTR_UID);
332                 conf->uid = info.pw_uid;
333         }
334         else if (sscanf(buff, "%u", &uid) == 1){
335                 conf->attribute_flags |= (1 << ATTR_UID);
336                 conf->uid = uid;
337         }
338
339         FREE(buff);
340         return 0;
341 }
342
343 static int
344 def_gid_handler(vector strvec)
345 {
346         gid_t gid;
347         char *buff;
348         char passwd_buf[1024];
349         struct passwd info, *found;
350
351         buff = set_value(strvec);
352         if (!buff)
353                 return 1;
354
355         if (getpwnam_r(buff, &info, passwd_buf, 1024, &found) == 0 && found) {
356                 conf->attribute_flags |= (1 << ATTR_GID);
357                 conf->gid = info.pw_gid;
358         }
359         else if (sscanf(buff, "%u", &gid) == 1){
360                 conf->attribute_flags |= (1 << ATTR_GID);
361                 conf->gid = gid;
362         }
363         FREE(buff);
364         return 0;
365 }
366
367 static int
368 def_weight_handler(vector strvec)
369 {
370         char * buff;
371
372         buff = set_value(strvec);
373
374         if (!buff)
375                 return 1;
376
377         if (strlen(buff) == 10 &&
378             !strcmp(buff, "priorities"))
379                 conf->rr_weight = RR_WEIGHT_PRIO;
380
381         if (strlen(buff) == strlen("uniform") &&
382             !strcmp(buff, "uniform"))
383                 conf->rr_weight = RR_WEIGHT_NONE;
384
385         FREE(buff);
386
387         return 0;
388 }
389
390 static int
391 default_failback_handler(vector strvec)
392 {
393         char * buff;
394
395         buff = set_value(strvec);
396
397         if (strlen(buff) == 6 && !strcmp(buff, "manual"))
398                 conf->pgfailback = -FAILBACK_MANUAL;
399         else if (strlen(buff) == 9 && !strcmp(buff, "immediate"))
400                 conf->pgfailback = -FAILBACK_IMMEDIATE;
401         else if (strlen(buff) == 10 && !strcmp(buff, "followover"))
402                 conf->pgfailback = -FAILBACK_FOLLOWOVER;
403         else
404                 conf->pgfailback = atoi(buff);
405
406         FREE(buff);
407
408         return 0;
409 }
410
411 static int
412 def_no_path_retry_handler(vector strvec)
413 {
414         char * buff;
415
416         buff = set_value(strvec);
417         if (!buff)
418                 return 1;
419
420         if ((strlen(buff) == 4 && !strcmp(buff, "fail")) ||
421             (strlen(buff) == 1 && !strcmp(buff, "0")))
422                 conf->no_path_retry = NO_PATH_RETRY_FAIL;
423         else if (strlen(buff) == 5 && !strcmp(buff, "queue"))
424                 conf->no_path_retry = NO_PATH_RETRY_QUEUE;
425         else if ((conf->no_path_retry = atoi(buff)) < 1)
426                 conf->no_path_retry = NO_PATH_RETRY_UNDEF;
427
428         FREE(buff);
429         return 0;
430 }
431
432 static int
433 def_queue_without_daemon(vector strvec)
434 {
435         char * buff;
436
437         buff = set_value(strvec);
438         if (!buff)
439                 return 1;
440
441         if (!strncmp(buff, "off", 3) || !strncmp(buff, "no", 2) ||
442             !strncmp(buff, "0", 1))
443                 conf->queue_without_daemon = QUE_NO_DAEMON_OFF;
444         else if (!strncmp(buff, "on", 2) || !strncmp(buff, "yes", 3) ||
445                  !strncmp(buff, "1", 1))
446                 conf->queue_without_daemon = QUE_NO_DAEMON_ON;
447         else
448                 conf->queue_without_daemon = QUE_NO_DAEMON_UNDEF;
449
450         free(buff);
451         return 0;
452 }
453
454 static int
455 def_checker_timeout_handler(vector strvec)
456 {
457         unsigned int checker_timeout;
458         char *buff;
459
460         buff = set_value(strvec);
461         if (!buff)
462                 return 1;
463
464         if (sscanf(buff, "%u", &checker_timeout) == 1)
465                 conf->checker_timeout = checker_timeout;
466         else
467                 conf->checker_timeout = 0;
468
469         free(buff);
470         return 0;
471 }
472
473 static int
474 def_pg_timeout_handler(vector strvec)
475 {
476         int pg_timeout;
477         char * buff;
478
479         buff = set_value(strvec);
480
481         if (!buff)
482                 return 1;
483
484         if (strlen(buff) == 4 && !strcmp(buff, "none"))
485                 conf->pg_timeout = -PGTIMEOUT_NONE;
486         else if (sscanf(buff, "%d", &pg_timeout) == 1 && pg_timeout >= 0) {
487                 if (pg_timeout == 0)
488                         conf->pg_timeout = -PGTIMEOUT_NONE;
489                 else
490                         conf->pg_timeout = pg_timeout;
491         }
492         else
493                 conf->pg_timeout = PGTIMEOUT_UNDEF;
494
495         FREE(buff);
496         return 0;
497 }
498
499 static int
500 def_flush_on_last_del_handler(vector strvec)
501 {
502         char * buff;
503
504         buff = set_value(strvec);
505         if (!buff)
506                 return 1;
507
508         if ((strlen(buff) == 2 && strcmp(buff, "no") == 0) ||
509             (strlen(buff) == 1 && strcmp(buff, "0") == 0))
510                 conf->flush_on_last_del = FLUSH_DISABLED;
511         else if ((strlen(buff) == 3 && strcmp(buff, "yes") == 0) ||
512             (strlen(buff) == 1 && strcmp(buff, "1") == 0))
513                 conf->flush_on_last_del = FLUSH_ENABLED;
514         else
515                 conf->flush_on_last_del = FLUSH_UNDEF;
516
517         FREE(buff);
518         return 0;
519 }
520
521 static int
522 def_log_checker_err_handler(vector strvec)
523 {
524         char * buff;
525
526         buff = set_value(strvec);
527
528         if (!buff)
529                 return 1;
530
531         if (strlen(buff) == 4 && !strcmp(buff, "once"))
532                 conf->log_checker_err = LOG_CHKR_ERR_ONCE;
533         else if (strlen(buff) == 6 && !strcmp(buff, "always"))
534                 conf->log_checker_err = LOG_CHKR_ERR_ALWAYS;
535
536         free(buff);
537         return 0;
538 }
539
540 static int
541 def_reservation_key_handler(vector strvec)
542 {
543         char *buff;
544         char *tbuff;
545         int j, k;
546         int len;
547         uint64_t prkey;
548
549         buff = set_value(strvec);
550         if (!buff)
551                 return 1;
552
553         tbuff = buff;
554
555         if (!memcmp("0x",buff, 2))
556                 buff = buff + 2;
557
558         len = strlen(buff);
559
560         k = strspn(buff, "0123456789aAbBcCdDeEfF");
561
562         if (len != k) {
563                 FREE(tbuff);
564                 return 1;
565         }
566
567         if (1 != sscanf (buff, "%" SCNx64 "", &prkey))
568         {
569                 FREE(tbuff);
570                 return 1;
571         }
572
573         if (!conf->reservation_key)
574                 conf->reservation_key = (unsigned char *) malloc(8);
575
576         memset(conf->reservation_key, 0, 8);
577
578         for (j = 7; j >= 0; --j) {
579                 conf->reservation_key[j] = (prkey & 0xff);
580                 prkey >>= 8;
581         }
582
583         FREE(tbuff);
584         return 0;
585 }
586
587 static int
588 def_names_handler(vector strvec)
589 {
590         char * buff;
591
592         buff = set_value(strvec);
593
594         if (!buff)
595                 return 1;
596
597         if ((strlen(buff) == 2 && !strcmp(buff, "no")) ||
598             (strlen(buff) == 1 && !strcmp(buff, "0")))
599                 conf->user_friendly_names = USER_FRIENDLY_NAMES_OFF;
600         else if ((strlen(buff) == 3 && !strcmp(buff, "yes")) ||
601                  (strlen(buff) == 1 && !strcmp(buff, "1")))
602                 conf->user_friendly_names = USER_FRIENDLY_NAMES_ON;
603         else
604                 conf->user_friendly_names = USER_FRIENDLY_NAMES_UNDEF;
605
606         FREE(buff);
607         return 0;
608 }
609
610 static int
611 bindings_file_handler(vector strvec)
612 {
613         conf->bindings_file = set_value(strvec);
614
615         if (!conf->bindings_file)
616                 return 1;
617
618         return 0;
619 }
620
621 static int
622 wwids_file_handler(vector strvec)
623 {
624         conf->wwids_file = set_value(strvec);
625
626         if (!conf->wwids_file)
627                 return 1;
628
629         return 0;
630 }
631
632 static int
633 def_retain_hwhandler_handler(vector strvec)
634 {
635         char * buff;
636
637         buff = set_value(strvec);
638
639         if (!buff)
640                 return 1;
641
642         if ((strlen(buff) == 2 && !strcmp(buff, "no")) ||
643             (strlen(buff) == 1 && !strcmp(buff, "0")))
644                 conf->retain_hwhandler = RETAIN_HWHANDLER_OFF;
645         else if ((strlen(buff) == 3 && !strcmp(buff, "yes")) ||
646                  (strlen(buff) == 1 && !strcmp(buff, "1")))
647                 conf->retain_hwhandler = RETAIN_HWHANDLER_ON;
648         else
649                 conf->retain_hwhandler = RETAIN_HWHANDLER_UNDEF;
650
651         FREE(buff);
652         return 0;
653 }
654
655 static int
656 def_detect_prio_handler(vector strvec)
657 {
658         char * buff;
659
660         buff = set_value(strvec);
661
662         if (!buff)
663                 return 1;
664
665         if ((strlen(buff) == 2 && !strcmp(buff, "no")) ||
666             (strlen(buff) == 1 && !strcmp(buff, "0")))
667                 conf->detect_prio = DETECT_PRIO_OFF;
668         else if ((strlen(buff) == 3 && !strcmp(buff, "yes")) ||
669                  (strlen(buff) == 1 && !strcmp(buff, "1")))
670                 conf->detect_prio = DETECT_PRIO_ON;
671         else
672                 conf->detect_prio = DETECT_PRIO_UNDEF;
673
674         FREE(buff);
675         return 0;
676 }
677
678 /*
679  * blacklist block handlers
680  */
681 static int
682 blacklist_handler(vector strvec)
683 {
684         conf->blist_devnode = vector_alloc();
685         conf->blist_wwid = vector_alloc();
686         conf->blist_device = vector_alloc();
687
688         if (!conf->blist_devnode || !conf->blist_wwid || !conf->blist_device)
689                 return 1;
690
691         return 0;
692 }
693
694 static int
695 blacklist_exceptions_handler(vector strvec)
696 {
697         conf->elist_devnode = vector_alloc();
698         conf->elist_wwid = vector_alloc();
699         conf->elist_device = vector_alloc();
700
701         if (!conf->elist_devnode || !conf->elist_wwid || !conf->elist_device)
702                 return 1;
703
704         return 0;
705 }
706
707 static int
708 ble_devnode_handler(vector strvec)
709 {
710         char * buff;
711
712         buff = set_value(strvec);
713
714         if (!buff)
715                 return 1;
716
717         return store_ble(conf->blist_devnode, buff, ORIGIN_CONFIG);
718 }
719
720 static int
721 ble_except_devnode_handler(vector strvec)
722 {
723         char * buff;
724
725         buff = set_value(strvec);
726
727         if (!buff)
728                 return 1;
729
730         return store_ble(conf->elist_devnode, buff, ORIGIN_CONFIG);
731 }
732
733 static int
734 ble_wwid_handler(vector strvec)
735 {
736         char * buff;
737
738         buff = set_value(strvec);
739
740         if (!buff)
741                 return 1;
742
743         return store_ble(conf->blist_wwid, buff, ORIGIN_CONFIG);
744 }
745
746 static int
747 ble_except_wwid_handler(vector strvec)
748 {
749         char * buff;
750
751         buff = set_value(strvec);
752
753         if (!buff)
754                 return 1;
755
756         return store_ble(conf->elist_wwid, buff, ORIGIN_CONFIG);
757 }
758
759 static int
760 ble_device_handler(vector strvec)
761 {
762         return alloc_ble_device(conf->blist_device);
763 }
764
765 static int
766 ble_except_device_handler(vector strvec)
767 {
768         return alloc_ble_device(conf->elist_device);
769 }
770
771 static int
772 ble_vendor_handler(vector strvec)
773 {
774         char * buff;
775
776         buff = set_value(strvec);
777
778         if (!buff)
779                 return 1;
780
781         return set_ble_device(conf->blist_device, buff, NULL, ORIGIN_CONFIG);
782 }
783
784 static int
785 ble_except_vendor_handler(vector strvec)
786 {
787         char * buff;
788
789         buff = set_value(strvec);
790
791         if (!buff)
792                 return 1;
793
794         return set_ble_device(conf->elist_device, buff, NULL, ORIGIN_CONFIG);
795 }
796
797 static int
798 ble_product_handler(vector strvec)
799 {
800         char * buff;
801
802         buff = set_value(strvec);
803
804         if (!buff)
805                 return 1;
806
807         return set_ble_device(conf->blist_device, NULL, buff, ORIGIN_CONFIG);
808 }
809
810 static int
811 ble_except_product_handler(vector strvec)
812 {
813         char * buff;
814
815         buff = set_value(strvec);
816
817         if (!buff)
818                 return 1;
819
820         return set_ble_device(conf->elist_device, NULL, buff, ORIGIN_CONFIG);
821 }
822
823 /*
824  * devices block handlers
825  */
826 static int
827 devices_handler(vector strvec)
828 {
829         if (!conf->hwtable)
830                 conf->hwtable = vector_alloc();
831
832         if (!conf->hwtable)
833                 return 1;
834
835         return 0;
836 }
837
838 static int
839 device_handler(vector strvec)
840 {
841         struct hwentry * hwe;
842
843         hwe = alloc_hwe();
844
845         if (!hwe)
846                 return 1;
847
848         if (!vector_alloc_slot(conf->hwtable)) {
849                 free_hwe(hwe);
850                 return 1;
851         }
852         vector_set_slot(conf->hwtable, hwe);
853
854         return 0;
855 }
856
857 static int
858 vendor_handler(vector strvec)
859 {
860         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
861
862         if (!hwe)
863                 return 1;
864
865         hwe->vendor = set_value(strvec);
866
867         if (!hwe->vendor)
868                 return 1;
869
870         return 0;
871 }
872
873 static int
874 product_handler(vector strvec)
875 {
876         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
877
878         if (!hwe)
879                 return 1;
880
881         hwe->product = set_value(strvec);
882
883         if (!hwe->product)
884                 return 1;
885
886         return 0;
887 }
888
889 static int
890 revision_handler(vector strvec)
891 {
892         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
893
894         if (!hwe)
895                 return 1;
896
897         hwe->revision = set_value(strvec);
898
899         if (!hwe->revision)
900                 return 1;
901
902         return 0;
903 }
904
905 static int
906 bl_product_handler(vector strvec)
907 {
908         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
909
910         if (!hwe)
911                 return 1;
912
913         hwe->bl_product = set_value(strvec);
914         if (!hwe->bl_product)
915                 return 1;
916
917         return 0;
918 }
919
920 static int
921 hw_fast_io_fail_handler(vector strvec)
922 {
923         char * buff;
924         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
925
926         buff = set_value(strvec);
927         if (strlen(buff) == 3 && !strcmp(buff, "off"))
928                 hwe->fast_io_fail = MP_FAST_IO_FAIL_OFF;
929         else if (sscanf(buff, "%d", &hwe->fast_io_fail) != 1 ||
930                  hwe->fast_io_fail < MP_FAST_IO_FAIL_ZERO)
931                 hwe->fast_io_fail = MP_FAST_IO_FAIL_UNSET;
932         else if (hwe->fast_io_fail == 0)
933                 hwe->fast_io_fail = MP_FAST_IO_FAIL_ZERO;
934
935         FREE(buff);
936         return 0;
937 }
938
939 static int
940 hw_dev_loss_handler(vector strvec)
941 {
942         char * buff;
943         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
944
945         buff = set_value(strvec);
946         if (!buff)
947                 return 1;
948
949         if (strlen(buff) == 8 && !strcmp(buff, "infinity"))
950                 hwe->dev_loss = MAX_DEV_LOSS_TMO;
951         else if (sscanf(buff, "%u", &hwe->dev_loss) != 1)
952                 hwe->dev_loss = 0;
953
954         FREE(buff);
955         return 0;
956 }
957
958 static int
959 hw_pgpolicy_handler(vector strvec)
960 {
961         char * buff;
962         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
963
964         buff = set_value(strvec);
965
966         if (!buff)
967                 return 1;
968
969         hwe->pgpolicy = get_pgpolicy_id(buff);
970         FREE(buff);
971
972         return 0;
973 }
974
975 static int
976 hw_uid_attribute_handler(vector strvec)
977 {
978         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
979
980         hwe->uid_attribute = set_value(strvec);
981
982         if (!hwe->uid_attribute)
983                 return 1;
984
985         return 0;
986 }
987
988 static int
989 hw_selector_handler(vector strvec)
990 {
991         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
992
993         if (!hwe)
994                 return 1;
995
996         hwe->selector = set_value(strvec);
997
998         if (!hwe->selector)
999                 return 1;
1000
1001         return 0;
1002 }
1003
1004 static int
1005 hw_path_checker_handler(vector strvec)
1006 {
1007         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1008
1009         if (!hwe)
1010                 return 1;
1011
1012         hwe->checker_name = set_value(strvec);
1013
1014         if (!hwe->checker_name)
1015                 return 1;
1016
1017         return 0;
1018 }
1019
1020 static int
1021 hw_features_handler(vector strvec)
1022 {
1023         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1024
1025         if (!hwe)
1026                 return 1;
1027
1028         hwe->features = set_value(strvec);
1029
1030         if (!hwe->features)
1031                 return 1;
1032
1033         return 0;
1034 }
1035
1036 static int
1037 hw_handler_handler(vector strvec)
1038 {
1039         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1040
1041         if (!hwe)
1042                 return 1;
1043
1044         hwe->hwhandler = set_value(strvec);
1045
1046         if (!hwe->hwhandler)
1047                 return 1;
1048
1049         return 0;
1050 }
1051
1052 static int
1053 hw_prio_handler(vector strvec)
1054 {
1055         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1056
1057         if (!hwe)
1058                 return 1;
1059
1060         hwe->prio_name = set_value(strvec);
1061
1062         if (!hwe->prio_name)
1063                 return 1;
1064
1065         return 0;
1066 }
1067
1068 static int
1069 hw_alias_prefix_handler(vector strvec)
1070 {
1071         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1072
1073         if (!hwe)
1074                 return 1;
1075
1076         hwe->alias_prefix = set_value(strvec);
1077
1078         if (!hwe->alias_prefix)
1079                 return 1;
1080
1081         return 0;
1082 }
1083
1084 static int
1085 hw_prio_args_handler(vector strvec)
1086 {
1087         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1088
1089         if (!hwe)
1090                 return 1;
1091
1092         hwe->prio_args = set_value(strvec);
1093
1094         if (!hwe->prio_args)
1095                 return 1;
1096
1097         return 0;
1098 }
1099
1100 static int
1101 hw_failback_handler(vector strvec)
1102 {
1103         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1104         char * buff;
1105
1106         if (!hwe)
1107                 return 1;
1108
1109         buff = set_value(strvec);
1110
1111         if (strlen(buff) == 6 && !strcmp(buff, "manual"))
1112                 hwe->pgfailback = -FAILBACK_MANUAL;
1113         else if (strlen(buff) == 9 && !strcmp(buff, "immediate"))
1114                 hwe->pgfailback = -FAILBACK_IMMEDIATE;
1115         else if (strlen(buff) == 10 && !strcmp(buff, "followover"))
1116                 hwe->pgfailback = -FAILBACK_FOLLOWOVER;
1117         else
1118                 hwe->pgfailback = atoi(buff);
1119
1120         FREE(buff);
1121
1122         return 0;
1123 }
1124
1125 static int
1126 hw_weight_handler(vector strvec)
1127 {
1128         struct hwentry * hwe = VECTOR_LAST_SLOT(conf->hwtable);
1129         char * buff;
1130
1131         if (!hwe)
1132                 return 1;
1133
1134         buff = set_value(strvec);
1135
1136         if (!buff)
1137                 return 1;
1138
1139         if (strlen(buff) == 10 &&
1140             !strcmp(buff, "priorities"))
1141                 hwe->rr_weight = RR_WEIGHT_PRIO;
1142
1143         if (strlen(buff) == strlen("uniform") &&
1144             !strcmp(buff, "uniform"))
1145                 hwe->rr_weight = RR_WEIGHT_NONE;
1146
1147         FREE(buff);
1148
1149         return 0;
1150 }
1151
1152 static int
1153 hw_no_path_retry_handler(vector strvec)
1154 {
1155         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1156         char *buff;
1157
1158         if (!hwe)
1159                 return 1;
1160
1161         buff = set_value(strvec);
1162         if (!buff)
1163                 return 1;
1164
1165         if ((strlen(buff) == 4 && !strcmp(buff, "fail")) ||
1166             (strlen(buff) == 1 && !strcmp(buff, "0")))
1167                 hwe->no_path_retry = NO_PATH_RETRY_FAIL;
1168         else if (strlen(buff) == 5 && !strcmp(buff, "queue"))
1169                 hwe->no_path_retry = NO_PATH_RETRY_QUEUE;
1170         else if ((hwe->no_path_retry = atoi(buff)) < 1)
1171                 hwe->no_path_retry = NO_PATH_RETRY_UNDEF;
1172
1173         FREE(buff);
1174         return 0;
1175 }
1176
1177 static int
1178 hw_minio_handler(vector strvec)
1179 {
1180         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1181         char * buff;
1182
1183         if (!hwe)
1184                 return 1;
1185
1186         buff = set_value(strvec);
1187
1188         if (!buff)
1189                 return 1;
1190
1191         hwe->minio = atoi(buff);
1192         FREE(buff);
1193
1194         return 0;
1195 }
1196
1197 static int
1198 hw_minio_rq_handler(vector strvec)
1199 {
1200         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1201         char * buff;
1202
1203         if (!hwe)
1204                 return 1;
1205
1206         buff = set_value(strvec);
1207
1208         if (!buff)
1209                 return 1;
1210
1211         hwe->minio_rq = atoi(buff);
1212         FREE(buff);
1213
1214         return 0;
1215 }
1216
1217 static int
1218 hw_pg_timeout_handler(vector strvec)
1219 {
1220         int pg_timeout;
1221         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1222         char *buff;
1223
1224         if (!hwe)
1225                 return 1;
1226
1227         buff = set_value(strvec);
1228
1229         if (!buff)
1230                 return 1;
1231
1232         if (strlen(buff) == 4 && !strcmp(buff, "none"))
1233                 hwe->pg_timeout = -PGTIMEOUT_NONE;
1234         else if (sscanf(buff, "%d", &pg_timeout) == 1 && pg_timeout >= 0) {
1235                 if (pg_timeout == 0)
1236                         hwe->pg_timeout = -PGTIMEOUT_NONE;
1237                 else
1238                         hwe->pg_timeout = pg_timeout;
1239         }
1240         else
1241                 hwe->pg_timeout = PGTIMEOUT_UNDEF;
1242
1243         FREE(buff);
1244         return 0;
1245 }
1246
1247 static int
1248 hw_flush_on_last_del_handler(vector strvec)
1249 {
1250         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1251         char * buff;
1252
1253         if (!hwe)
1254                 return 1;
1255
1256         buff = set_value(strvec);
1257         if (!buff)
1258                 return 1;
1259
1260         if ((strlen(buff) == 2 && strcmp(buff, "no") == 0) ||
1261             (strlen(buff) == 1 && strcmp(buff, "0") == 0))
1262                 hwe->flush_on_last_del = FLUSH_DISABLED;
1263         else if ((strlen(buff) == 3 && strcmp(buff, "yes") == 0) ||
1264             (strlen(buff) == 1 && strcmp(buff, "1") == 0))
1265                 hwe->flush_on_last_del = FLUSH_ENABLED;
1266         else
1267                 hwe->flush_on_last_del = FLUSH_UNDEF;
1268
1269         FREE(buff);
1270         return 0;
1271 }
1272
1273 static int
1274 hw_names_handler(vector strvec)
1275 {
1276         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1277         char * buff;
1278
1279         if (!hwe)
1280                 return 1;
1281
1282         buff = set_value(strvec);
1283         if (!buff)
1284                 return 1;
1285
1286         if ((strlen(buff) == 2 && strcmp(buff, "no") == 0) ||
1287             (strlen(buff) == 1 && strcmp(buff, "0") == 0))
1288                 hwe->user_friendly_names = USER_FRIENDLY_NAMES_OFF;
1289         else if ((strlen(buff) == 3 && strcmp(buff, "yes") == 0) ||
1290                  (strlen(buff) == 1 && strcmp(buff, "1") == 0))
1291                 hwe->user_friendly_names = USER_FRIENDLY_NAMES_ON;
1292         else
1293                 hwe->user_friendly_names = USER_FRIENDLY_NAMES_UNDEF;
1294
1295         FREE(buff);
1296         return 0;
1297 }
1298
1299 static int
1300 hw_retain_hwhandler_handler(vector strvec)
1301 {
1302         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1303         char * buff;
1304
1305         if (!hwe)
1306                 return 1;
1307
1308         buff = set_value(strvec);
1309
1310         if (!buff)
1311                 return 1;
1312
1313         if ((strlen(buff) == 2 && !strcmp(buff, "no")) ||
1314             (strlen(buff) == 1 && !strcmp(buff, "0")))
1315                 hwe->retain_hwhandler = RETAIN_HWHANDLER_OFF;
1316         else if ((strlen(buff) == 3 && !strcmp(buff, "yes")) ||
1317                  (strlen(buff) == 1 && !strcmp(buff, "1")))
1318                 hwe->retain_hwhandler = RETAIN_HWHANDLER_ON;
1319         else
1320                 hwe->user_friendly_names = RETAIN_HWHANDLER_UNDEF;
1321
1322         FREE(buff);
1323         return 0;
1324 }
1325
1326 static int
1327 hw_detect_prio_handler(vector strvec)
1328 {
1329         struct hwentry *hwe = VECTOR_LAST_SLOT(conf->hwtable);
1330         char * buff;
1331
1332         if (!hwe)
1333                 return 1;
1334
1335         buff = set_value(strvec);
1336
1337         if (!buff)
1338                 return 1;
1339
1340         if ((strlen(buff) == 2 && !strcmp(buff, "no")) ||
1341             (strlen(buff) == 1 && !strcmp(buff, "0")))
1342                 hwe->detect_prio = DETECT_PRIO_OFF;
1343         else if ((strlen(buff) == 3 && !strcmp(buff, "yes")) ||
1344                  (strlen(buff) == 1 && !strcmp(buff, "1")))
1345                 hwe->detect_prio = DETECT_PRIO_ON;
1346         else
1347                 hwe->detect_prio = DETECT_PRIO_UNDEF;
1348
1349         FREE(buff);
1350         return 0;
1351 }
1352
1353 /*
1354  * multipaths block handlers
1355  */
1356 static int
1357 multipaths_handler(vector strvec)
1358 {
1359         conf->mptable = vector_alloc();
1360
1361         if (!conf->mptable)
1362                 return 1;
1363
1364         return 0;
1365 }
1366
1367 static int
1368 multipath_handler(vector strvec)
1369 {
1370         struct mpentry * mpe;
1371
1372         mpe = alloc_mpe();
1373
1374         if (!mpe)
1375                 return 1;
1376
1377         if (!vector_alloc_slot(conf->mptable)) {
1378                 free_mpe(mpe);
1379                 return 1;
1380         }
1381         vector_set_slot(conf->mptable, mpe);
1382
1383         return 0;
1384 }
1385
1386 static int
1387 wwid_handler(vector strvec)
1388 {
1389         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1390
1391         if (!mpe)
1392                 return 1;
1393
1394         mpe->wwid = set_value(strvec);
1395
1396         if (!mpe->wwid)
1397                 return 1;
1398
1399         return 0;
1400 }
1401
1402 static int
1403 alias_handler(vector strvec)
1404 {
1405         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1406
1407         if (!mpe)
1408                 return 1;
1409
1410         mpe->alias = set_value(strvec);
1411
1412         if (!mpe->alias)
1413                 return 1;
1414
1415         return 0;
1416 }
1417
1418 static int
1419 mp_pgpolicy_handler(vector strvec)
1420 {
1421         char * buff;
1422         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1423
1424         if (!mpe)
1425                 return 1;
1426
1427         buff = set_value(strvec);
1428
1429         if (!buff)
1430                 return 1;
1431
1432         mpe->pgpolicy = get_pgpolicy_id(buff);
1433         FREE(buff);
1434
1435         return 0;
1436 }
1437
1438 static int
1439 mp_selector_handler(vector strvec)
1440 {
1441         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1442
1443         if (!mpe)
1444                 return 1;
1445
1446         mpe->selector = set_value(strvec);
1447
1448         if (!mpe->selector)
1449                 return 1;
1450
1451         return 0;
1452 }
1453
1454 static int
1455 mp_failback_handler(vector strvec)
1456 {
1457         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1458         char * buff;
1459
1460         if (!mpe)
1461                 return 1;
1462
1463         buff = set_value(strvec);
1464
1465         if (strlen(buff) == 6 && !strcmp(buff, "manual"))
1466                 mpe->pgfailback = -FAILBACK_MANUAL;
1467         else if (strlen(buff) == 9 && !strcmp(buff, "immediate"))
1468                 mpe->pgfailback = -FAILBACK_IMMEDIATE;
1469         else if (strlen(buff) == 10 && !strcmp(buff, "followover"))
1470                 mpe->pgfailback = -FAILBACK_FOLLOWOVER;
1471         else
1472                 mpe->pgfailback = atoi(buff);
1473
1474         FREE(buff);
1475
1476         return 0;
1477 }
1478
1479 static int
1480 mp_mode_handler(vector strvec)
1481 {
1482         mode_t mode;
1483         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1484         char *buff;
1485
1486         if (!mpe)
1487                 return 1;
1488
1489         buff = set_value(strvec);
1490         if (!buff)
1491                 return 1;
1492         if (sscanf(buff, "%o", &mode) == 1 && mode <= 0777) {
1493                 mpe->attribute_flags |= (1 << ATTR_MODE);
1494                 mpe->mode = mode;
1495         }
1496
1497         FREE(buff);
1498         return 0;
1499 }
1500
1501 static int
1502 mp_uid_handler(vector strvec)
1503 {
1504         uid_t uid;
1505         char *buff;
1506         char passwd_buf[1024];
1507         struct passwd info, *found;
1508
1509         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1510
1511         if (!mpe)
1512                 return 1;
1513
1514         buff = set_value(strvec);
1515         if (!buff)
1516                 return 1;
1517
1518         if (getpwnam_r(buff, &info, passwd_buf, 1024, &found) == 0 && found) {
1519                 mpe->attribute_flags |= (1 << ATTR_UID);
1520                 mpe->uid = info.pw_uid;
1521         }
1522         else if (sscanf(buff, "%u", &uid) == 1){
1523                 mpe->attribute_flags |= (1 << ATTR_UID);
1524                 mpe->uid = uid;
1525         }
1526         FREE(buff);
1527         return 0;
1528 }
1529
1530 static int
1531 mp_gid_handler(vector strvec)
1532 {
1533         gid_t gid;
1534         char *buff;
1535         char passwd_buf[1024];
1536         struct passwd info, *found;
1537
1538         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1539
1540         if (!mpe)
1541                 return 1;
1542
1543         buff = set_value(strvec);
1544         if (!buff)
1545                 return 1;
1546
1547         if (getpwnam_r(buff, &info, passwd_buf, 1024, &found) == 0 && found) {
1548                 mpe->attribute_flags |= (1 << ATTR_GID);
1549                 mpe->gid = info.pw_gid;
1550         }
1551         else if (sscanf(buff, "%u", &gid) == 1) {
1552                 mpe->attribute_flags |= (1 << ATTR_GID);
1553                 mpe->gid = gid;
1554         }
1555         FREE(buff);
1556         return 0;
1557 }
1558
1559 static int
1560 mp_weight_handler(vector strvec)
1561 {
1562         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1563         char * buff;
1564
1565         if (!mpe)
1566                 return 1;
1567
1568         buff = set_value(strvec);
1569
1570         if (!buff)
1571                 return 1;
1572
1573         if (strlen(buff) == 10 &&
1574             !strcmp(buff, "priorities"))
1575                 mpe->rr_weight = RR_WEIGHT_PRIO;
1576
1577         if (strlen(buff) == strlen("uniform") &&
1578             !strcmp(buff, "uniform"))
1579                 mpe->rr_weight = RR_WEIGHT_NONE;
1580
1581         FREE(buff);
1582
1583         return 0;
1584 }
1585
1586 static int
1587 mp_no_path_retry_handler(vector strvec)
1588 {
1589         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1590         char *buff;
1591
1592         if (!mpe)
1593                 return 1;
1594
1595         buff = set_value(strvec);
1596         if (!buff)
1597                 return 1;
1598
1599         if ((strlen(buff) == 4 && !strcmp(buff, "fail")) ||
1600             (strlen(buff) == 1 && !strcmp(buff, "0")))
1601                 mpe->no_path_retry = NO_PATH_RETRY_FAIL;
1602         else if (strlen(buff) == 5 && !strcmp(buff, "queue"))
1603                 mpe->no_path_retry = NO_PATH_RETRY_QUEUE;
1604         else if ((mpe->no_path_retry = atoi(buff)) < 1)
1605                 mpe->no_path_retry = NO_PATH_RETRY_UNDEF;
1606
1607         FREE(buff);
1608         return 0;
1609 }
1610
1611 static int
1612 mp_minio_handler(vector strvec)
1613 {
1614         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1615         char * buff;
1616
1617         if (!mpe)
1618                 return 1;
1619
1620         buff = set_value(strvec);
1621
1622         if (!buff)
1623                 return 1;
1624
1625         mpe->minio = atoi(buff);
1626         FREE(buff);
1627
1628         return 0;
1629 }
1630
1631 static int
1632 mp_minio_rq_handler(vector strvec)
1633 {
1634         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1635         char * buff;
1636
1637         if (!mpe)
1638                 return 1;
1639
1640         buff = set_value(strvec);
1641
1642         if (!buff)
1643                 return 1;
1644
1645         mpe->minio_rq = atoi(buff);
1646         FREE(buff);
1647
1648         return 0;
1649 }
1650
1651 static int
1652 mp_pg_timeout_handler(vector strvec)
1653 {
1654         int pg_timeout;
1655         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1656         char *buff;
1657
1658         if (!mpe)
1659                 return 1;
1660
1661         buff = set_value(strvec);
1662
1663         if (!buff)
1664                 return 1;
1665         if (strlen(buff) == 4 && !strcmp(buff, "none"))
1666                 mpe->pg_timeout = -PGTIMEOUT_NONE;
1667         else if (sscanf(buff, "%d", &pg_timeout) == 1 && pg_timeout >= 0) {
1668                 if (pg_timeout == 0)
1669                         mpe->pg_timeout = -PGTIMEOUT_NONE;
1670                 else
1671                         mpe->pg_timeout = pg_timeout;
1672         }
1673         else
1674                 mpe->pg_timeout = PGTIMEOUT_UNDEF;
1675
1676         FREE(buff);
1677         return 0;
1678 }
1679
1680 static int
1681 mp_features_handler(vector strvec)
1682 {
1683         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1684
1685         if (!mpe)
1686                 return 1;
1687
1688         mpe->features = set_value(strvec);
1689
1690         if (!mpe->features)
1691                 return 1;
1692
1693         return 0;
1694 }
1695
1696 static int
1697 mp_flush_on_last_del_handler(vector strvec)
1698 {
1699         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1700         char * buff;
1701
1702         if (!mpe)
1703                 return 1;
1704
1705         buff = set_value(strvec);
1706         if (!buff)
1707                 return 1;
1708
1709         if ((strlen(buff) == 2 && strcmp(buff, "no") == 0) ||
1710             (strlen(buff) == 1 && strcmp(buff, "0") == 0))
1711                 mpe->flush_on_last_del = FLUSH_DISABLED;
1712         else if ((strlen(buff) == 3 && strcmp(buff, "yes") == 0) ||
1713             (strlen(buff) == 1 && strcmp(buff, "1") == 0))
1714                 mpe->flush_on_last_del = FLUSH_ENABLED;
1715         else
1716                 mpe->flush_on_last_del = FLUSH_UNDEF;
1717
1718         FREE(buff);
1719         return 0;
1720 }
1721
1722 static int
1723 mp_prio_handler(vector strvec)
1724 {
1725         struct mpentry * mpe = VECTOR_LAST_SLOT(conf->mptable);
1726
1727         if (!mpe)
1728                 return 1;
1729
1730         mpe->prio_name = set_value(strvec);
1731
1732         if (!mpe->prio_name)
1733                 return 1;
1734
1735         return 0;
1736 }
1737
1738 static int
1739 mp_prio_args_handler (vector strvec)
1740 {
1741         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1742
1743         if (!mpe)
1744                 return 1;
1745
1746         mpe->prio_args = set_value(strvec);
1747         if (!mpe->prio_args)
1748                 return 1;
1749
1750         return 0;
1751 }
1752
1753 static int
1754 mp_reservation_key_handler (vector strvec)
1755 {
1756         char *buff;
1757         char *tbuff;
1758         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1759
1760         int j, k, len;
1761         uint64_t prkey;
1762
1763         if (!mpe)
1764                 return 1;
1765
1766         buff = set_value(strvec);
1767         if (!buff)
1768                 return 1;
1769
1770         tbuff = buff;
1771         if (!memcmp(buff, "0x", 2))
1772                 buff = buff + 2;
1773
1774         len = strlen(buff);
1775
1776         k = strspn(buff, "0123456789aAbBcCdDeEfF");
1777         if (len != k) {
1778                 FREE(tbuff);
1779                 return 1;
1780         }
1781
1782         if (1 != sscanf (buff, "%" SCNx64 "", &prkey))
1783         {
1784                 FREE(tbuff);
1785                 return 1;
1786         }
1787
1788         if (!mpe->reservation_key)
1789                 mpe->reservation_key = (unsigned char *) malloc(8);
1790
1791         memset(mpe->reservation_key, 0, 8);
1792
1793         for (j = 7; j >= 0; --j) {
1794                 mpe->reservation_key[j] = (prkey & 0xff);
1795                 prkey >>= 8;
1796         }
1797
1798         FREE(tbuff);
1799         return 0;
1800 }
1801
1802 static int
1803 mp_names_handler(vector strvec)
1804 {
1805         struct mpentry *mpe = VECTOR_LAST_SLOT(conf->mptable);
1806         char * buff;
1807
1808         if (!mpe)
1809                 return 1;
1810
1811         buff = set_value(strvec);
1812         if (!buff)
1813                 return 1;
1814
1815         if ((strlen(buff) == 2 && strcmp(buff, "no") == 0) ||
1816             (strlen(buff) == 1 && strcmp(buff, "0") == 0))
1817                 mpe->user_friendly_names = USER_FRIENDLY_NAMES_OFF;
1818         else if ((strlen(buff) == 3 && strcmp(buff, "yes") == 0) ||
1819                  (strlen(buff) == 1 && strcmp(buff, "1") == 0))
1820                 mpe->user_friendly_names = USER_FRIENDLY_NAMES_ON;
1821         else
1822                 mpe->user_friendly_names = USER_FRIENDLY_NAMES_UNDEF;
1823
1824         FREE(buff);
1825         return 0;
1826 }
1827
1828 /*
1829  * config file keywords printing
1830  */
1831 static int
1832 snprint_mp_wwid (char * buff, int len, void * data)
1833 {
1834         struct mpentry * mpe = (struct mpentry *)data;
1835
1836         return snprintf(buff, len, "%s", mpe->wwid);
1837 }
1838
1839 static int
1840 snprint_mp_alias (char * buff, int len, void * data)
1841 {
1842         struct mpentry * mpe = (struct mpentry *)data;
1843
1844         if (!mpe->alias)
1845                 return 0;
1846
1847         return snprintf(buff, len, "%s", mpe->alias);
1848 }
1849
1850 static int
1851 snprint_mp_path_grouping_policy (char * buff, int len, void * data)
1852 {
1853         struct mpentry * mpe = (struct mpentry *)data;
1854         char str[POLICY_NAME_SIZE];
1855
1856         if (!mpe->pgpolicy)
1857                 return 0;
1858         get_pgpolicy_name(str, POLICY_NAME_SIZE, mpe->pgpolicy);
1859
1860         return snprintf(buff, len, "\"%s\"", str);
1861 }
1862
1863 static int
1864 snprint_mp_selector (char * buff, int len, void * data)
1865 {
1866         struct mpentry * mpe = (struct mpentry *)data;
1867
1868         if (!mpe->selector)
1869                 return 0;
1870
1871         return snprintf(buff, len, "\"%s\"", mpe->selector);
1872 }
1873
1874 static int
1875 snprint_mp_failback (char * buff, int len, void * data)
1876 {
1877         struct mpentry * mpe = (struct mpentry *)data;
1878
1879         if (!mpe->pgfailback)
1880                 return 0;
1881
1882         switch(mpe->pgfailback) {
1883         case  FAILBACK_UNDEF:
1884                 break;
1885         case -FAILBACK_MANUAL:
1886                 return snprintf(buff, len, "\"manual\"");
1887         case -FAILBACK_IMMEDIATE:
1888                 return snprintf(buff, len, "\"immediate\"");
1889         case -FAILBACK_FOLLOWOVER:
1890                 return snprintf(buff, len, "\"followover\"");
1891         default:
1892                 return snprintf(buff, len, "%i", mpe->pgfailback);
1893         }
1894         return 0;
1895 }
1896
1897 static int
1898 snprint_mp_mode(char * buff, int len, void * data)
1899 {
1900         struct mpentry * mpe = (struct mpentry *)data;
1901
1902         if ((mpe->attribute_flags & (1 << ATTR_MODE)) == 0)
1903                 return 0;
1904         return snprintf(buff, len, "0%o", mpe->mode);
1905 }
1906
1907 static int
1908 snprint_mp_uid(char * buff, int len, void * data)
1909 {
1910         struct mpentry * mpe = (struct mpentry *)data;
1911
1912         if ((mpe->attribute_flags & (1 << ATTR_UID)) == 0)
1913                 return 0;
1914         return snprintf(buff, len, "0%o", mpe->uid);
1915 }
1916
1917 static int
1918 snprint_mp_gid(char * buff, int len, void * data)
1919 {
1920         struct mpentry * mpe = (struct mpentry *)data;
1921
1922         if ((mpe->attribute_flags & (1 << ATTR_GID)) == 0)
1923                 return 0;
1924         return snprintf(buff, len, "0%o", mpe->gid);
1925 }
1926
1927 static int
1928 snprint_mp_rr_weight (char * buff, int len, void * data)
1929 {
1930         struct mpentry * mpe = (struct mpentry *)data;
1931
1932         if (!mpe->rr_weight)
1933                 return 0;
1934         if (mpe->rr_weight == RR_WEIGHT_PRIO)
1935                 return snprintf(buff, len, "\"priorities\"");
1936         if (mpe->rr_weight == RR_WEIGHT_NONE)
1937                 return snprintf(buff, len, "\"uniform\"");
1938
1939         return 0;
1940 }
1941
1942 static int
1943 snprint_mp_no_path_retry (char * buff, int len, void * data)
1944 {
1945         struct mpentry * mpe = (struct mpentry *)data;
1946
1947         if (!mpe->no_path_retry)
1948                 return 0;
1949
1950         switch(mpe->no_path_retry) {
1951         case NO_PATH_RETRY_UNDEF:
1952                 break;
1953         case NO_PATH_RETRY_FAIL:
1954                 return snprintf(buff, len, "\"fail\"");
1955         case NO_PATH_RETRY_QUEUE:
1956                 return snprintf(buff, len, "\"queue\"");
1957         default:
1958                 return snprintf(buff, len, "%i",
1959                                 mpe->no_path_retry);
1960         }
1961         return 0;
1962 }
1963
1964 static int
1965 snprint_mp_rr_min_io (char * buff, int len, void * data)
1966 {
1967         struct mpentry * mpe = (struct mpentry *)data;
1968
1969         if (!mpe->minio)
1970                 return 0;
1971
1972         return snprintf(buff, len, "%u", mpe->minio);
1973 }
1974
1975 static int
1976 snprint_mp_rr_min_io_rq (char * buff, int len, void * data)
1977 {
1978         struct mpentry * mpe = (struct mpentry *)data;
1979
1980         if (!mpe->minio_rq)
1981                 return 0;
1982
1983         return snprintf(buff, len, "%u", mpe->minio_rq);
1984 }
1985
1986 static int
1987 snprint_mp_pg_timeout (char * buff, int len, void * data)
1988 {
1989         struct mpentry * mpe = (struct mpentry *)data;
1990
1991         switch (mpe->pg_timeout) {
1992         case PGTIMEOUT_UNDEF:
1993                 break;
1994         case -PGTIMEOUT_NONE:
1995                 return snprintf(buff, len, "\"none\"");
1996         default:
1997                 return snprintf(buff, len, "%i", mpe->pg_timeout);
1998         }
1999         return 0;
2000 }
2001
2002 static int
2003 snprint_mp_features (char * buff, int len, void * data)
2004 {
2005         struct mpentry * mpe = (struct mpentry *)data;
2006
2007         if (!mpe->features)
2008                 return 0;
2009         if (strlen(mpe->features) == strlen(conf->features) &&
2010             !strcmp(mpe->features, conf->features))
2011                 return 0;
2012
2013         return snprintf(buff, len, "\"%s\"", mpe->features);
2014 }
2015
2016 static int
2017 snprint_mp_flush_on_last_del (char * buff, int len, void * data)
2018 {
2019         struct mpentry * mpe = (struct mpentry *)data;
2020
2021         switch (mpe->flush_on_last_del) {
2022         case FLUSH_DISABLED:
2023                 return snprintf(buff, len, "\"no\"");
2024         case FLUSH_ENABLED:
2025                 return snprintf(buff, len, "\"yes\"");
2026         }
2027         return 0;
2028 }
2029
2030 static int
2031 snprint_mp_prio(char * buff, int len, void * data)
2032 {
2033         struct mpentry * mpe = (struct mpentry *)data;
2034
2035         if (!mpe->prio_name)
2036                 return 0;
2037
2038         return snprintf(buff, len, "\"%s\"", mpe->prio_name);
2039 }
2040
2041 static int
2042 snprint_mp_prio_args(char * buff, int len, void * data)
2043 {
2044         struct mpentry * mpe = (struct mpentry *)data;
2045
2046         if (!mpe->prio_args)
2047                 return 0;
2048
2049         return snprintf(buff, len, "\"%s\"", mpe->prio_args);
2050 }
2051
2052 static int
2053 snprint_mp_reservation_key (char * buff, int len, void * data)
2054 {
2055         int i;
2056         unsigned char *keyp;
2057         uint64_t prkey = 0;
2058         struct mpentry * mpe = (struct mpentry *)data;
2059
2060         if (!mpe->reservation_key)
2061                 return 0;
2062         keyp = (unsigned char *)mpe->reservation_key;
2063         for (i = 0; i < 8; i++) {
2064                 if (i > 0)
2065                         prkey <<= 8;
2066                 prkey |= *keyp;
2067                 keyp++;
2068         }
2069
2070         return snprintf(buff, len, "0x%" PRIx64, prkey);
2071 }
2072
2073         static int
2074 snprint_mp_user_friendly_names (char * buff, int len, void * data)
2075 {
2076         struct mpentry * mpe = (struct mpentry *)data;
2077
2078         if (mpe->user_friendly_names == USER_FRIENDLY_NAMES_UNDEF)
2079                 return 0;
2080         else if (mpe->user_friendly_names == USER_FRIENDLY_NAMES_OFF)
2081                 return snprintf(buff, len, "\"no\"");
2082         else
2083                 return snprintf(buff, len, "\"yes\"");
2084 }
2085
2086 static int
2087 snprint_hw_fast_io_fail(char * buff, int len, void * data)
2088 {
2089         struct hwentry * hwe = (struct hwentry *)data;
2090         if (hwe->fast_io_fail == MP_FAST_IO_FAIL_UNSET)
2091                 return 0;
2092         if (hwe->fast_io_fail == conf->fast_io_fail)
2093                 return 0;
2094         if (hwe->fast_io_fail == MP_FAST_IO_FAIL_OFF)
2095                 return snprintf(buff, len, "\"off\"");
2096         if (hwe->fast_io_fail == MP_FAST_IO_FAIL_ZERO)
2097                 return snprintf(buff, len, "0");
2098         return snprintf(buff, len, "%d", hwe->fast_io_fail);
2099 }
2100
2101 static int
2102 snprint_hw_dev_loss(char * buff, int len, void * data)
2103 {
2104         struct hwentry * hwe = (struct hwentry *)data;
2105         if (!hwe->dev_loss)
2106                 return 0;
2107         if (hwe->dev_loss == conf->dev_loss)
2108                 return 0;
2109         if (hwe->dev_loss >= MAX_DEV_LOSS_TMO)
2110                 return snprintf(buff, len, "\"infinity\"");
2111
2112         return snprintf(buff, len, "%u", hwe->dev_loss);
2113 }
2114
2115 static int
2116 snprint_hw_vendor (char * buff, int len, void * data)
2117 {
2118         struct hwentry * hwe = (struct hwentry *)data;
2119
2120         if (!hwe->vendor)
2121                 return 0;
2122
2123         return snprintf(buff, len, "\"%s\"", hwe->vendor);
2124 }
2125
2126 static int
2127 snprint_hw_product (char * buff, int len, void * data)
2128 {
2129         struct hwentry * hwe = (struct hwentry *)data;
2130
2131         if (!hwe->product)
2132                 return 0;
2133
2134         return snprintf(buff, len, "\"%s\"", hwe->product);
2135 }
2136
2137 static int
2138 snprint_hw_revision (char * buff, int len, void * data)
2139 {
2140         struct hwentry * hwe = (struct hwentry *)data;
2141
2142         if (!hwe->revision)
2143                 return 0;
2144
2145         return snprintf(buff, len, "\"%s\"", hwe->revision);
2146 }
2147
2148 static int
2149 snprint_hw_bl_product (char * buff, int len, void * data)
2150 {
2151         struct hwentry * hwe = (struct hwentry *)data;
2152
2153         if (!hwe->bl_product)
2154                 return 0;
2155
2156         return snprintf(buff, len, "\"%s\"", hwe->bl_product);
2157 }
2158
2159 static int
2160 snprint_hw_uid_attribute (char * buff, int len, void * data)
2161 {
2162         struct hwentry * hwe = (struct hwentry *)data;
2163
2164         if (!hwe->uid_attribute)
2165                 return 0;
2166
2167         return snprintf(buff, len, "\"%s\"", hwe->uid_attribute);
2168 }
2169
2170 static int
2171 snprint_hw_prio (char * buff, int len, void * data)
2172 {
2173         struct hwentry * hwe = (struct hwentry *)data;
2174
2175         if (!hwe->prio_name)
2176                 return 0;
2177
2178         return snprintf(buff, len, "\"%s\"", hwe->prio_name);
2179 }
2180
2181 static int
2182 snprint_hw_alias_prefix (char * buff, int len, void * data)
2183 {
2184         struct hwentry * hwe = (struct hwentry *)data;
2185
2186         if (!hwe->alias_prefix)
2187                 return 0;
2188
2189         return snprintf(buff, len, "\"%s\"", hwe->alias_prefix);
2190 }
2191
2192 static int
2193 snprint_hw_prio_args (char * buff, int len, void * data)
2194 {
2195         struct hwentry * hwe = (struct hwentry *)data;
2196
2197         if (!hwe->prio_args)
2198                 return 0;
2199
2200         return snprintf(buff, len, "\"%s\"", hwe->prio_args);
2201 }
2202
2203 static int
2204 snprint_hw_features (char * buff, int len, void * data)
2205 {
2206         struct hwentry * hwe = (struct hwentry *)data;
2207
2208         if (!hwe->features)
2209                 return 0;
2210
2211         return snprintf(buff, len, "\"%s\"", hwe->features);
2212 }
2213
2214 static int
2215 snprint_hw_hardware_handler (char * buff, int len, void * data)
2216 {
2217         struct hwentry * hwe = (struct hwentry *)data;
2218
2219         if (!hwe->hwhandler)
2220                 return 0;
2221
2222         return snprintf(buff, len, "\"%s\"", hwe->hwhandler);
2223 }
2224
2225 static int
2226 snprint_hw_selector (char * buff, int len, void * data)
2227 {
2228         struct hwentry * hwe = (struct hwentry *)data;
2229
2230         if (!hwe->selector)
2231                 return 0;
2232
2233         return snprintf(buff, len, "\"%s\"", hwe->selector);
2234 }
2235
2236 static int
2237 snprint_hw_path_grouping_policy (char * buff, int len, void * data)
2238 {
2239         struct hwentry * hwe = (struct hwentry *)data;
2240
2241         char str[POLICY_NAME_SIZE];
2242
2243         if (!hwe->pgpolicy)
2244                 return 0;
2245
2246         get_pgpolicy_name(str, POLICY_NAME_SIZE, hwe->pgpolicy);
2247
2248         return snprintf(buff, len, "\"%s\"", str);
2249 }
2250
2251 static int
2252 snprint_hw_failback (char * buff, int len, void * data)
2253 {
2254         struct hwentry * hwe = (struct hwentry *)data;
2255
2256         if (!hwe->pgfailback)
2257                 return 0;
2258
2259         switch(hwe->pgfailback) {
2260         case  FAILBACK_UNDEF:
2261                 break;
2262         case -FAILBACK_MANUAL:
2263                 return snprintf(buff, len, "\"manual\"");
2264         case -FAILBACK_IMMEDIATE:
2265                 return snprintf(buff, len, "\"immediate\"");
2266         case -FAILBACK_FOLLOWOVER:
2267                 return snprintf(buff, len, "\"followover\"");
2268         default:
2269                 return snprintf(buff, len, "%i", hwe->pgfailback);
2270         }
2271         return 0;
2272 }
2273
2274 static int
2275 snprint_hw_rr_weight (char * buff, int len, void * data)
2276 {
2277         struct hwentry * hwe = (struct hwentry *)data;
2278
2279         if (!hwe->rr_weight)
2280                 return 0;
2281         if (hwe->rr_weight == RR_WEIGHT_PRIO)
2282                 return snprintf(buff, len, "\"priorities\"");
2283         if (hwe->rr_weight == RR_WEIGHT_NONE)
2284                 return snprintf(buff, len, "\"uniform\"");
2285
2286         return 0;
2287 }
2288
2289 static int
2290 snprint_hw_no_path_retry (char * buff, int len, void * data)
2291 {
2292         struct hwentry * hwe = (struct hwentry *)data;
2293
2294         if (!hwe->no_path_retry)
2295                 return 0;
2296
2297         switch(hwe->no_path_retry) {
2298         case NO_PATH_RETRY_UNDEF:
2299                 break;
2300         case NO_PATH_RETRY_FAIL:
2301                 return snprintf(buff, len, "\"fail\"");
2302         case NO_PATH_RETRY_QUEUE:
2303                 return snprintf(buff, len, "\"queue\"");
2304         default:
2305                 return snprintf(buff, len, "%i",
2306                                 hwe->no_path_retry);
2307         }
2308         return 0;
2309 }
2310
2311 static int
2312 snprint_hw_rr_min_io (char * buff, int len, void * data)
2313 {
2314         struct hwentry * hwe = (struct hwentry *)data;
2315
2316         if (!hwe->minio)
2317                 return 0;
2318
2319         return snprintf(buff, len, "%u", hwe->minio);
2320 }
2321
2322 static int
2323 snprint_hw_rr_min_io_rq (char * buff, int len, void * data)
2324 {
2325         struct hwentry * hwe = (struct hwentry *)data;
2326
2327         if (!hwe->minio_rq)
2328                 return 0;
2329
2330         return snprintf(buff, len, "%u", hwe->minio_rq);
2331 }
2332
2333 static int
2334 snprint_hw_pg_timeout (char * buff, int len, void * data)
2335 {
2336         struct hwentry * hwe = (struct hwentry *)data;
2337
2338         if (!hwe->pg_timeout)
2339                 return 0;
2340
2341         switch (hwe->pg_timeout) {
2342         case PGTIMEOUT_UNDEF:
2343                 break;
2344         case -PGTIMEOUT_NONE:
2345                 return snprintf(buff, len, "\"none\"");
2346         default:
2347                 return snprintf(buff, len, "%i", hwe->pg_timeout);
2348         }
2349         return 0;
2350 }
2351
2352 static int
2353 snprint_hw_flush_on_last_del (char * buff, int len, void * data)
2354 {
2355         struct hwentry * hwe = (struct hwentry *)data;
2356
2357         switch (hwe->flush_on_last_del) {
2358         case FLUSH_DISABLED:
2359                 return snprintf(buff, len, "\"no\"");
2360         case FLUSH_ENABLED:
2361                 return snprintf(buff, len, "\"yes\"");
2362         }
2363         return 0;
2364 }
2365
2366 static int
2367 snprint_hw_path_checker (char * buff, int len, void * data)
2368 {
2369         struct hwentry * hwe = (struct hwentry *)data;
2370
2371         if (!hwe->checker_name)
2372                 return 0;
2373
2374         return snprintf(buff, len, "\"%s\"", hwe->checker_name);
2375 }
2376
2377         static int
2378 snprint_hw_user_friendly_names (char * buff, int len, void * data)
2379 {
2380         struct hwentry * hwe = (struct hwentry *)data;
2381
2382         if (hwe->user_friendly_names == USER_FRIENDLY_NAMES_UNDEF)
2383                 return 0;
2384         else if (hwe->user_friendly_names == USER_FRIENDLY_NAMES_OFF)
2385                 return snprintf(buff, len, "\"no\"");
2386         else
2387                 return snprintf(buff, len, "\"yes\"");
2388 }
2389
2390 static int
2391 snprint_hw_retain_hwhandler_handler(char * buff, int len, void * data)
2392 {
2393         struct hwentry * hwe = (struct hwentry *)data;
2394
2395         if (hwe->retain_hwhandler == RETAIN_HWHANDLER_ON)
2396                 return snprintf(buff, len, "\"yes\"");
2397         else if (hwe->retain_hwhandler == RETAIN_HWHANDLER_OFF)
2398                 return snprintf(buff, len, "\"no\"");
2399         else
2400                 return 0;
2401 }
2402
2403 static int
2404 snprint_detect_prio(char * buff, int len, void * data)
2405 {
2406         struct hwentry * hwe = (struct hwentry *)data;
2407
2408         if (hwe->detect_prio == DETECT_PRIO_ON)
2409                 return snprintf(buff, len, "\"yes\"");
2410         else if (hwe->detect_prio == DETECT_PRIO_OFF)
2411                 return snprintf(buff, len, "\"no\"");
2412         else
2413                 return 0;
2414 }
2415
2416 static int
2417 snprint_def_polling_interval (char * buff, int len, void * data)
2418 {
2419         return snprintf(buff, len, "%i", conf->checkint);
2420 }
2421
2422 static int
2423 snprint_def_fast_io_fail(char * buff, int len, void * data)
2424 {
2425         if (conf->fast_io_fail == MP_FAST_IO_FAIL_UNSET)
2426                 return 0;
2427         if (conf->fast_io_fail == MP_FAST_IO_FAIL_OFF)
2428                 return snprintf(buff, len, "\"off\"");
2429         if (conf->fast_io_fail == MP_FAST_IO_FAIL_ZERO)
2430                 return snprintf(buff, len, "0");
2431         return snprintf(buff, len, "%d", conf->fast_io_fail);
2432 }
2433
2434 static int
2435 snprint_def_dev_loss(char * buff, int len, void * data)
2436 {
2437         if (!conf->dev_loss)
2438                 return 0;
2439         if (conf->dev_loss >= MAX_DEV_LOSS_TMO)
2440                 return snprintf(buff, len, "\"infinity\"");
2441         return snprintf(buff, len, "%u", conf->dev_loss);
2442 }
2443
2444 static int
2445 snprint_def_verbosity (char * buff, int len, void * data)
2446 {
2447         return snprintf(buff, len, "%i", conf->verbosity);
2448 }
2449
2450 static int
2451 snprint_def_max_polling_interval (char * buff, int len, void * data)
2452 {
2453         if (conf->max_checkint == MAX_CHECKINT(conf->checkint))
2454                 return 0;
2455         return snprintf(buff, len, "%i", conf->max_checkint);
2456 }
2457
2458 static int
2459 snprint_reassign_maps (char * buff, int len, void * data)
2460 {
2461         if (conf->reassign_maps == DEFAULT_REASSIGN_MAPS)
2462                 return 0;
2463         return snprintf(buff, len, "\"%s\"",
2464                         conf->reassign_maps?"yes":"no");
2465 }
2466
2467 static int
2468 snprint_def_multipath_dir (char * buff, int len, void * data)
2469 {
2470         if (!conf->multipath_dir)
2471                 return 0;
2472
2473         return snprintf(buff, len, "\"%s\"", conf->multipath_dir);
2474 }
2475
2476 static int
2477 snprint_def_selector (char * buff, int len, void * data)
2478 {
2479         if (!conf->selector)
2480                 return snprintf(buff, len, "\"%s\"", DEFAULT_SELECTOR);
2481
2482         return snprintf(buff, len, "\"%s\"", conf->selector);
2483 }
2484
2485 static int
2486 snprint_def_path_grouping_policy (char * buff, int len, void * data)
2487 {
2488         char str[POLICY_NAME_SIZE];
2489         int pgpolicy = conf->pgpolicy;
2490
2491         if (!pgpolicy)
2492                 pgpolicy = DEFAULT_PGPOLICY;
2493
2494         get_pgpolicy_name(str, POLICY_NAME_SIZE, pgpolicy);
2495
2496         return snprintf(buff, len, "\"%s\"", str);
2497 }
2498
2499 static int
2500 snprint_def_uid_attribute (char * buff, int len, void * data)
2501 {
2502         if (!conf->uid_attribute)
2503                 return snprintf(buff, len, "\"%s\"", DEFAULT_UID_ATTRIBUTE);
2504
2505         return snprintf(buff, len, "\"%s\"", conf->uid_attribute);
2506 }
2507
2508 static int
2509 snprint_def_prio (char * buff, int len, void * data)
2510 {
2511         if (!conf->prio_name)
2512                 return snprintf(buff, len, "\"%s\"", DEFAULT_PRIO);
2513
2514         return snprintf(buff, len, "\"%s\"", conf->prio_name);
2515 }
2516
2517 static int
2518 snprint_def_prio_args (char * buff, int len, void * data)
2519 {
2520         if (!conf->prio_args)
2521                 return snprintf(buff, len, "\"%s\"", DEFAULT_PRIO_ARGS);
2522
2523         return snprintf(buff, len, "\"%s\"", conf->prio_args);
2524 }
2525
2526 static int
2527 snprint_def_features (char * buff, int len, void * data)
2528 {
2529         if (!conf->features)
2530                 return snprintf(buff, len, "\"%s\"", DEFAULT_FEATURES);
2531
2532         return snprintf(buff, len, "\"%s\"", conf->features);
2533 }
2534
2535 static int
2536 snprint_def_path_checker (char * buff, int len, void * data)
2537 {
2538         if (!conf->checker_name)
2539                 return snprintf(buff, len, "\"%s\"", DEFAULT_CHECKER);
2540
2541         return snprintf(buff, len, "\"%s\"", conf->checker_name);
2542 }
2543
2544 static int
2545 snprint_def_failback (char * buff, int len, void * data)
2546 {
2547         int pgfailback = conf->pgfailback;
2548         if (!pgfailback)
2549                 pgfailback = DEFAULT_FAILBACK;
2550
2551         switch(conf->pgfailback) {
2552         case  FAILBACK_UNDEF:
2553                 break;
2554         case -FAILBACK_MANUAL:
2555                 return snprintf(buff, len, "\"manual\"");
2556         case -FAILBACK_IMMEDIATE:
2557                 return snprintf(buff, len, "\"immediate\"");
2558         case -FAILBACK_FOLLOWOVER:
2559                 return snprintf(buff, len, "\"followover\"");
2560         default:
2561                 return snprintf(buff, len, "%i", conf->pgfailback);
2562         }
2563         return 0;
2564 }
2565
2566 static int
2567 snprint_def_rr_min_io (char * buff, int len, void * data)
2568 {
2569         if (!conf->minio)
2570                 return 0;
2571
2572         return snprintf(buff, len, "%u", conf->minio);
2573 }
2574
2575 static int
2576 snprint_def_rr_min_io_rq (char * buff, int len, void * data)
2577 {
2578         if (!conf->minio_rq)
2579                 return 0;
2580
2581         return snprintf(buff, len, "%u", conf->minio_rq);
2582 }
2583
2584 static int
2585 snprint_max_fds (char * buff, int len, void * data)
2586 {
2587         if (!conf->max_fds)
2588                 return 0;
2589
2590         return snprintf(buff, len, "%d", conf->max_fds);
2591 }
2592
2593 static int
2594 snprint_def_mode(char * buff, int len, void * data)
2595 {
2596         if ((conf->attribute_flags & (1 << ATTR_MODE)) == 0)
2597                 return 0;
2598         return snprintf(buff, len, "0%o", conf->mode);
2599 }
2600
2601 static int
2602 snprint_def_uid(char * buff, int len, void * data)
2603 {
2604         if ((conf->attribute_flags & (1 << ATTR_UID)) == 0)
2605                 return 0;
2606         return snprintf(buff, len, "0%o", conf->uid);
2607 }
2608
2609 static int
2610 snprint_def_gid(char * buff, int len, void * data)
2611 {
2612         if ((conf->attribute_flags & (1 << ATTR_GID)) == 0)
2613                 return 0;
2614         return snprintf(buff, len, "0%o", conf->gid);
2615 }
2616
2617 static int
2618 snprint_def_rr_weight (char * buff, int len, void * data)
2619 {
2620         if (!conf->rr_weight || conf->rr_weight == RR_WEIGHT_NONE)
2621                 return snprintf(buff, len, "\"uniform\"");
2622         if (conf->rr_weight == RR_WEIGHT_PRIO)
2623                 return snprintf(buff, len, "\"priorities\"");
2624
2625         return 0;
2626 }
2627
2628 static int
2629 snprint_def_no_path_retry (char * buff, int len, void * data)
2630 {
2631         switch(conf->no_path_retry) {
2632         case NO_PATH_RETRY_UNDEF:
2633                 break;
2634         case NO_PATH_RETRY_FAIL:
2635                 return snprintf(buff, len, "\"fail\"");
2636         case NO_PATH_RETRY_QUEUE:
2637                 return snprintf(buff, len, "\"queue\"");
2638         default:
2639                 return snprintf(buff, len, "%i",
2640                                 conf->no_path_retry);
2641         }
2642         return 0;
2643 }
2644
2645 static int
2646 snprint_def_queue_without_daemon (char * buff, int len, void * data)
2647 {
2648         switch (conf->queue_without_daemon) {
2649         case QUE_NO_DAEMON_OFF:
2650                 return snprintf(buff, len, "\"no\"");
2651         case QUE_NO_DAEMON_ON:
2652         case QUE_NO_DAEMON_UNDEF:
2653                 return snprintf(buff, len, "\"yes\"");
2654         }
2655         return 0;
2656 }
2657
2658 static int
2659 snprint_def_checker_timeout (char *buff, int len, void *data)
2660 {
2661         if (!conf->checker_timeout)
2662                 return 0;
2663
2664         return snprintf(buff, len, "%u", conf->checker_timeout);
2665 }
2666
2667 static int
2668 snprint_def_pg_timeout (char * buff, int len, void * data)
2669 {
2670         switch (conf->pg_timeout) {
2671         case PGTIMEOUT_UNDEF:
2672         case -PGTIMEOUT_NONE:
2673                 return snprintf(buff, len, "\"none\"");
2674         default:
2675                 return snprintf(buff, len, "%i", conf->pg_timeout);
2676         }
2677         return 0;
2678 }
2679
2680 static int
2681 snprint_def_flush_on_last_del (char * buff, int len, void * data)
2682 {
2683         switch (conf->flush_on_last_del) {
2684         case FLUSH_UNDEF:
2685         case FLUSH_DISABLED:
2686                 return snprintf(buff, len, "\"no\"");
2687         case FLUSH_ENABLED:
2688         case FLUSH_IN_PROGRESS:
2689                 return snprintf(buff, len, "\"yes\"");
2690         }
2691         return 0;
2692 }
2693
2694 static int
2695 snprint_def_log_checker_err (char * buff, int len, void * data)
2696 {
2697         if (conf->log_checker_err == LOG_CHKR_ERR_ONCE)
2698                 return snprintf(buff, len, "once");
2699         return snprintf(buff, len, "always");
2700 }
2701
2702 static int
2703 snprint_def_user_friendly_names (char * buff, int len, void * data)
2704 {
2705         if (conf->user_friendly_names  == USER_FRIENDLY_NAMES_ON)
2706                 return snprintf(buff, len, "\"yes\"");
2707         else
2708                 return snprintf(buff, len, "\"no\"");
2709 }
2710
2711 static int
2712 snprint_def_alias_prefix (char * buff, int len, void * data)
2713 {
2714         if (!conf->alias_prefix)
2715                 return snprintf(buff, len, "\"%s\"", DEFAULT_ALIAS_PREFIX);
2716         return snprintf(buff, len, "\"%s\"", conf->alias_prefix);
2717 }
2718
2719 static int
2720 snprint_def_bindings_file (char * buff, int len, void * data)
2721 {
2722         if (conf->bindings_file == NULL)
2723                 return 0;
2724         return snprintf(buff, len, "\"%s\"", conf->bindings_file);
2725 }
2726
2727 static int
2728 snprint_def_wwids_file (char * buff, int len, void * data)
2729 {
2730         if (conf->wwids_file == NULL)
2731                 return 0;
2732         return snprintf(buff, len, "%s", conf->wwids_file);
2733 }
2734
2735 static int
2736 snprint_def_reservation_key(char * buff, int len, void * data)
2737 {
2738         int i;
2739         unsigned char *keyp;
2740         uint64_t prkey = 0;
2741
2742         if (!conf->reservation_key)
2743                 return 0;
2744         keyp = (unsigned char *)conf->reservation_key;
2745         for (i = 0; i < 8; i++) {
2746                 if (i > 0)
2747                         prkey <<= 8;
2748                 prkey |= *keyp;
2749                 keyp++;
2750         }
2751         return snprintf(buff, len, "0x%" PRIx64, prkey);
2752 }
2753
2754 static int
2755 snprint_def_retain_hwhandler_handler(char * buff, int len, void * data)
2756 {
2757         if (conf->retain_hwhandler == RETAIN_HWHANDLER_ON)
2758                 return snprintf(buff, len, "yes");
2759         else
2760                 return snprintf(buff, len, "no");
2761 }
2762
2763 static int
2764 snprint_def_detect_prio(char * buff, int len, void * data)
2765 {
2766         if (conf->detect_prio == DETECT_PRIO_ON)
2767                 return snprintf(buff, len, "yes");
2768         else
2769                 return snprintf(buff, len, "no");
2770 }
2771
2772 static int
2773 snprint_ble_simple (char * buff, int len, void * data)
2774 {
2775         struct blentry * ble = (struct blentry *)data;
2776
2777         return snprintf(buff, len, "\"%s\"", ble->str);
2778 }
2779
2780 static int
2781 snprint_bled_vendor (char * buff, int len, void * data)
2782 {
2783         struct blentry_device * bled = (struct blentry_device *)data;
2784
2785         return snprintf(buff, len, "\"%s\"", bled->vendor);
2786 }
2787
2788 static int
2789 snprint_bled_product (char * buff, int len, void * data)
2790 {
2791         struct blentry_device * bled = (struct blentry_device *)data;
2792
2793         return snprintf(buff, len, "\"%s\"", bled->product);
2794 }
2795
2796 #define __deprecated
2797
2798 void
2799 init_keywords(void)
2800 {
2801         install_keyword_root("defaults", NULL);
2802         install_keyword("verbosity", &verbosity_handler, &snprint_def_verbosity);
2803         install_keyword("polling_interval", &polling_interval_handler, &snprint_def_polling_interval);
2804         install_keyword("max_polling_interval", &max_polling_interval_handler, &snprint_def_max_polling_interval);
2805         install_keyword("reassign_maps", &reassign_maps_handler, &snprint_reassign_maps);
2806         install_keyword("multipath_dir", &multipath_dir_handler, &snprint_def_multipath_dir);
2807         install_keyword("path_selector", &def_selector_handler, &snprint_def_selector);
2808         install_keyword("path_grouping_policy", &def_pgpolicy_handler, &snprint_def_path_grouping_policy);
2809         install_keyword("uid_attribute", &def_uid_attribute_handler, &snprint_def_uid_attribute);
2810         install_keyword("prio", &def_prio_handler, &snprint_def_prio);
2811         install_keyword("prio_args", &def_prio_args_handler, &snprint_def_prio_args);
2812         install_keyword("features", &def_features_handler, &snprint_def_features);
2813         install_keyword("path_checker", &def_path_checker_handler, &snprint_def_path_checker);
2814         install_keyword("checker", &def_path_checker_handler, NULL);
2815         install_keyword("alias_prefix", &def_alias_prefix_handler, &snprint_def_alias_prefix);
2816         install_keyword("failback", &default_failback_handler, &snprint_def_failback);
2817         install_keyword("rr_min_io", &def_minio_handler, &snprint_def_rr_min_io);
2818         install_keyword("rr_min_io_rq", &def_minio_rq_handler, &snprint_def_rr_min_io_rq);
2819         install_keyword("max_fds", &max_fds_handler, &snprint_max_fds);
2820         install_keyword("rr_weight", &def_weight_handler, &snprint_def_rr_weight);
2821         install_keyword("no_path_retry", &def_no_path_retry_handler, &snprint_def_no_path_retry);
2822         install_keyword("queue_without_daemon", &def_queue_without_daemon, &snprint_def_queue_without_daemon);
2823         install_keyword("checker_timeout", &def_checker_timeout_handler, &snprint_def_checker_timeout);
2824         install_keyword("pg_timeout", &def_pg_timeout_handler, &snprint_def_pg_timeout);
2825         install_keyword("flush_on_last_del", &def_flush_on_last_del_handler, &snprint_def_flush_on_last_del);
2826         install_keyword("user_friendly_names", &def_names_handler, &snprint_def_user_friendly_names);
2827         install_keyword("mode", &def_mode_handler, &snprint_def_mode);
2828         install_keyword("uid", &def_uid_handler, &snprint_def_uid);
2829         install_keyword("gid", &def_gid_handler, &snprint_def_gid);
2830         install_keyword("fast_io_fail_tmo", &def_fast_io_fail_handler, &snprint_def_fast_io_fail);
2831         install_keyword("dev_loss_tmo", &def_dev_loss_handler, &snprint_def_dev_loss);
2832         install_keyword("bindings_file", &bindings_file_handler, &snprint_def_bindings_file);
2833         install_keyword("wwids_file", &wwids_file_handler, &snprint_def_wwids_file);
2834         install_keyword("log_checker_err", &def_log_checker_err_handler, &snprint_def_log_checker_err);
2835         install_keyword("reservation_key", &def_reservation_key_handler, &snprint_def_reservation_key);
2836         install_keyword("retain_attached_hw_handler", &def_retain_hwhandler_handler, &snprint_def_retain_hwhandler_handler);
2837         install_keyword("detect_prio", &def_detect_prio_handler, &snprint_def_detect_prio);
2838         __deprecated install_keyword("default_selector", &def_selector_handler, NULL);
2839         __deprecated install_keyword("default_path_grouping_policy", &def_pgpolicy_handler, NULL);
2840         __deprecated install_keyword("default_uid_attribute", &def_uid_attribute_handler, NULL);
2841         __deprecated install_keyword("default_features", &def_features_handler, NULL);
2842         __deprecated install_keyword("default_path_checker", &def_path_checker_handler, NULL);
2843
2844         install_keyword_root("blacklist", &blacklist_handler);
2845         install_keyword_multi("devnode", &ble_devnode_handler, &snprint_ble_simple);
2846         install_keyword_multi("wwid", &ble_wwid_handler, &snprint_ble_simple);
2847         install_keyword_multi("device", &ble_device_handler, NULL);
2848         install_sublevel();
2849         install_keyword("vendor", &ble_vendor_handler, &snprint_bled_vendor);
2850         install_keyword("product", &ble_product_handler, &snprint_bled_product);
2851         install_sublevel_end();
2852         install_keyword_root("blacklist_exceptions", &blacklist_exceptions_handler);
2853         install_keyword_multi("devnode", &ble_except_devnode_handler, &snprint_ble_simple);
2854         install_keyword_multi("wwid", &ble_except_wwid_handler, &snprint_ble_simple);
2855         install_keyword_multi("device", &ble_except_device_handler, NULL);
2856         install_sublevel();
2857         install_keyword("vendor", &ble_except_vendor_handler, &snprint_bled_vendor);
2858         install_keyword("product", &ble_except_product_handler, &snprint_bled_product);
2859         install_sublevel_end();
2860
2861 #if 0
2862         __deprecated install_keyword_root("devnode_blacklist", &blacklist_handler);
2863         __deprecated install_keyword("devnode", &ble_devnode_handler, &snprint_ble_simple);
2864         __deprecated install_keyword("wwid", &ble_wwid_handler, &snprint_ble_simple);
2865         __deprecated install_keyword("device", &ble_device_handler, NULL);
2866         __deprecated install_sublevel();
2867         __deprecated install_keyword("vendor", &ble_vendor_handler, &snprint_bled_vendor);
2868         __deprecated install_keyword("product", &ble_product_handler, &snprint_bled_product);
2869         __deprecated install_sublevel_end();
2870 #endif
2871
2872         install_keyword_root("devices", &devices_handler);
2873         install_keyword_multi("device", &device_handler, NULL);
2874         install_sublevel();
2875         install_keyword("vendor", &vendor_handler, &snprint_hw_vendor);
2876         install_keyword("product", &product_handler, &snprint_hw_product);
2877         install_keyword("revision", &revision_handler, &snprint_hw_revision);
2878         install_keyword("product_blacklist", &bl_product_handler, &snprint_hw_bl_product);
2879         install_keyword("path_grouping_policy", &hw_pgpolicy_handler, &snprint_hw_path_grouping_policy);
2880         install_keyword("uid_attribute", &hw_uid_attribute_handler, &snprint_hw_uid_attribute);
2881         install_keyword("path_selector", &hw_selector_handler, &snprint_hw_selector);
2882         install_keyword("path_checker", &hw_path_checker_handler, &snprint_hw_path_checker);
2883         install_keyword("checker", &hw_path_checker_handler, NULL);
2884         install_keyword("alias_prefix", &hw_alias_prefix_handler, &snprint_hw_alias_prefix);
2885         install_keyword("features", &hw_features_handler, &snprint_hw_features);
2886         install_keyword("hardware_handler", &hw_handler_handler, &snprint_hw_hardware_handler);
2887         install_keyword("prio", &hw_prio_handler, &snprint_hw_prio);
2888         install_keyword("prio_args", &hw_prio_args_handler, &snprint_hw_prio_args);
2889         install_keyword("failback", &hw_failback_handler, &snprint_hw_failback);
2890         install_keyword("rr_weight", &hw_weight_handler, &snprint_hw_rr_weight);
2891         install_keyword("no_path_retry", &hw_no_path_retry_handler, &snprint_hw_no_path_retry);
2892         install_keyword("rr_min_io", &hw_minio_handler, &snprint_hw_rr_min_io);
2893         install_keyword("rr_min_io_rq", &hw_minio_rq_handler, &snprint_hw_rr_min_io_rq);
2894         install_keyword("pg_timeout", &hw_pg_timeout_handler, &snprint_hw_pg_timeout);
2895         install_keyword("flush_on_last_del", &hw_flush_on_last_del_handler, &snprint_hw_flush_on_last_del);
2896         install_keyword("fast_io_fail_tmo", &hw_fast_io_fail_handler, &snprint_hw_fast_io_fail);
2897         install_keyword("dev_loss_tmo", &hw_dev_loss_handler, &snprint_hw_dev_loss);
2898         install_keyword("user_friendly_names", &hw_names_handler, &snprint_hw_user_friendly_names);
2899         install_keyword("retain_attached_hw_handler", &hw_retain_hwhandler_handler, &snprint_hw_retain_hwhandler_handler);
2900         install_keyword("detect_prio", &hw_detect_prio_handler, &snprint_detect_prio);
2901         install_sublevel_end();
2902
2903         install_keyword_root("multipaths", &multipaths_handler);
2904         install_keyword_multi("multipath", &multipath_handler, NULL);
2905         install_sublevel();
2906         install_keyword("wwid", &wwid_handler, &snprint_mp_wwid);
2907         install_keyword("alias", &alias_handler, &snprint_mp_alias);
2908         install_keyword("path_grouping_policy", &mp_pgpolicy_handler, &snprint_mp_path_grouping_policy);
2909         install_keyword("path_selector", &mp_selector_handler, &snprint_mp_selector);
2910         install_keyword("prio", &mp_prio_handler, &snprint_mp_prio);
2911         install_keyword("prio_args", &mp_prio_args_handler, &snprint_mp_prio_args);
2912         install_keyword("failback", &mp_failback_handler, &snprint_mp_failback);
2913         install_keyword("rr_weight", &mp_weight_handler, &snprint_mp_rr_weight);
2914         install_keyword("no_path_retry", &mp_no_path_retry_handler, &snprint_mp_no_path_retry);
2915         install_keyword("rr_min_io", &mp_minio_handler, &snprint_mp_rr_min_io);
2916         install_keyword("rr_min_io_rq", &mp_minio_rq_handler, &snprint_mp_rr_min_io_rq);
2917         install_keyword("pg_timeout", &mp_pg_timeout_handler, &snprint_mp_pg_timeout);
2918         install_keyword("flush_on_last_del", &mp_flush_on_last_del_handler, &snprint_mp_flush_on_last_del);
2919         install_keyword("features", &mp_features_handler, &snprint_mp_features);
2920         install_keyword("mode", &mp_mode_handler, &snprint_mp_mode);
2921         install_keyword("uid", &mp_uid_handler, &snprint_mp_uid);
2922         install_keyword("gid", &mp_gid_handler, &snprint_mp_gid);
2923         install_keyword("reservation_key", &mp_reservation_key_handler, &snprint_mp_reservation_key);
2924         install_keyword("user_friendly_names", &mp_names_handler, &snprint_mp_user_friendly_names);
2925         install_sublevel_end();
2926 }