libmultipath: add vend_id to get_vpd_sgio
[multipath-tools/.git] / libmultipath / discovery.c
1 /*
2  * Copyright (c) 2004, 2005, 2006 Christophe Varoqui
3  * Copyright (c) 2005 Stefan Bader, IBM
4  * Copyright (c) 2005 Mike Anderson
5  */
6 #include <stdio.h>
7 #include <ctype.h>
8 #include <unistd.h>
9 #include <limits.h>
10 #include <fcntl.h>
11 #include <sys/ioctl.h>
12 #include <sys/stat.h>
13 #include <dirent.h>
14 #include <errno.h>
15 #include <libgen.h>
16 #include <libudev.h>
17
18 #include "checkers.h"
19 #include "vector.h"
20 #include "memory.h"
21 #include "util.h"
22 #include "structs.h"
23 #include "config.h"
24 #include "blacklist.h"
25 #include "callout.h"
26 #include "debug.h"
27 #include "propsel.h"
28 #include "sg_include.h"
29 #include "sysfs.h"
30 #include "discovery.h"
31 #include "prio.h"
32 #include "defaults.h"
33 #include "unaligned.h"
34 #include "prioritizers/alua_rtpg.h"
35 #include "foreign.h"
36
37 int
38 alloc_path_with_pathinfo (struct config *conf, struct udev_device *udevice,
39                           const char *wwid, int flag, struct path **pp_ptr)
40 {
41         int err = PATHINFO_FAILED;
42         struct path * pp;
43         const char * devname;
44
45         if (pp_ptr)
46                 *pp_ptr = NULL;
47
48         devname = udev_device_get_sysname(udevice);
49         if (!devname)
50                 return PATHINFO_FAILED;
51
52         pp = alloc_path();
53
54         if (!pp)
55                 return PATHINFO_FAILED;
56
57         if (wwid)
58                 strlcpy(pp->wwid, wwid, sizeof(pp->wwid));
59
60         if (safe_sprintf(pp->dev, "%s", devname)) {
61                 condlog(0, "pp->dev too small");
62         } else {
63                 pp->udev = udev_device_ref(udevice);
64                 err = pathinfo(pp, conf, flag | DI_BLACKLIST);
65         }
66
67         if (err || !pp_ptr)
68                 free_path(pp);
69         else if (pp_ptr)
70                 *pp_ptr = pp;
71         return err;
72 }
73
74 int
75 store_pathinfo (vector pathvec, struct config *conf,
76                 struct udev_device *udevice, int flag, struct path **pp_ptr)
77 {
78         int err = PATHINFO_FAILED;
79         struct path * pp;
80         const char * devname;
81
82         if (pp_ptr)
83                 *pp_ptr = NULL;
84
85         devname = udev_device_get_sysname(udevice);
86         if (!devname)
87                 return PATHINFO_FAILED;
88
89         pp = alloc_path();
90
91         if (!pp)
92                 return PATHINFO_FAILED;
93
94         if(safe_sprintf(pp->dev, "%s", devname)) {
95                 condlog(0, "pp->dev too small");
96                 goto out;
97         }
98         pp->udev = udev_device_ref(udevice);
99         err = pathinfo(pp, conf, flag);
100         if (err)
101                 goto out;
102
103         err = store_path(pathvec, pp);
104         if (err)
105                 goto out;
106         pp->checkint = conf->checkint;
107
108 out:
109         if (err)
110                 free_path(pp);
111         else if (pp_ptr)
112                 *pp_ptr = pp;
113         return err;
114 }
115
116 static int
117 path_discover (vector pathvec, struct config * conf,
118                struct udev_device *udevice, int flag)
119 {
120         struct path * pp;
121         const char * devname;
122
123         devname = udev_device_get_sysname(udevice);
124         if (!devname)
125                 return PATHINFO_FAILED;
126
127         pp = find_path_by_dev(pathvec, devname);
128         if (!pp) {
129                 char devt[BLK_DEV_SIZE];
130                 dev_t devnum = udev_device_get_devnum(udevice);
131
132                 snprintf(devt, BLK_DEV_SIZE, "%d:%d",
133                          major(devnum), minor(devnum));
134                 pp = find_path_by_devt(pathvec, devt);
135                 if (!pp)
136                         return store_pathinfo(pathvec, conf,
137                                               udevice, flag | DI_BLACKLIST,
138                                               NULL);
139         }
140         return pathinfo(pp, conf, flag);
141 }
142
143 static void cleanup_udev_enumerate_ptr(void *arg)
144 {
145         struct udev_enumerate *ue;
146
147         if (!arg)
148                 return;
149         ue = *((struct udev_enumerate**) arg);
150         if (ue)
151                 (void)udev_enumerate_unref(ue);
152 }
153
154 static void cleanup_udev_device_ptr(void *arg)
155 {
156         struct udev_device *ud;
157
158         if (!arg)
159                 return;
160         ud = *((struct udev_device**) arg);
161         if (ud)
162                 (void)udev_device_unref(ud);
163 }
164
165 int
166 path_discovery (vector pathvec, int flag)
167 {
168         struct udev_enumerate *udev_iter = NULL;
169         struct udev_list_entry *entry;
170         struct udev_device *udevice = NULL;
171         struct config *conf;
172         int num_paths = 0, total_paths = 0, ret;
173
174         pthread_cleanup_push(cleanup_udev_enumerate_ptr, &udev_iter);
175         pthread_cleanup_push(cleanup_udev_device_ptr, &udevice);
176         conf = get_multipath_config();
177         pthread_cleanup_push(put_multipath_config, conf);
178
179         udev_iter = udev_enumerate_new(udev);
180         if (!udev_iter) {
181                 ret = -ENOMEM;
182                 goto out;
183         }
184
185         if (udev_enumerate_add_match_subsystem(udev_iter, "block") < 0 ||
186             udev_enumerate_add_match_is_initialized(udev_iter) < 0 ||
187             udev_enumerate_scan_devices(udev_iter) < 0) {
188                 condlog(1, "%s: error setting up udev_enumerate: %m", __func__);
189                 ret = -1;
190                 goto out;
191         }
192
193         udev_list_entry_foreach(entry,
194                                 udev_enumerate_get_list_entry(udev_iter)) {
195                 const char *devtype;
196                 const char *devpath;
197
198                 devpath = udev_list_entry_get_name(entry);
199                 condlog(4, "Discover device %s", devpath);
200                 udevice = udev_device_new_from_syspath(udev, devpath);
201                 if (!udevice) {
202                         condlog(4, "%s: no udev information", devpath);
203                         continue;
204                 }
205                 devtype = udev_device_get_devtype(udevice);
206                 if(devtype && !strncmp(devtype, "disk", 4)) {
207                         total_paths++;
208                         if (path_discover(pathvec, conf,
209                                           udevice, flag) == PATHINFO_OK)
210                                 num_paths++;
211                 }
212                 udevice = udev_device_unref(udevice);
213         }
214         ret = total_paths - num_paths;
215         condlog(4, "Discovered %d/%d paths", num_paths, total_paths);
216 out:
217         pthread_cleanup_pop(1);
218         pthread_cleanup_pop(1);
219         pthread_cleanup_pop(1);
220         return ret;
221 }
222
223 #define declare_sysfs_get_str(fname)                                    \
224 ssize_t                                                                 \
225 sysfs_get_##fname (struct udev_device * udev, char * buff, size_t len)  \
226 {                                                                       \
227         size_t l;                                                       \
228         const char * attr;                                              \
229         const char * devname;                                           \
230                                                                         \
231         if (!udev)                                                      \
232                 return -ENOSYS;                                         \
233                                                                         \
234         devname = udev_device_get_sysname(udev);                        \
235                                                                         \
236         attr = udev_device_get_sysattr_value(udev, #fname);             \
237         if (!attr) {                                                    \
238                 condlog(3, "%s: attribute %s not found in sysfs",       \
239                         devname, #fname);                               \
240                 return -ENXIO;                                          \
241         }                                                               \
242         for (l = strlen(attr); l >= 1 && isspace(attr[l-1]); l--);      \
243         if (l > len) {                                                  \
244                 condlog(3, "%s: overflow in attribute %s",              \
245                         devname, #fname);                               \
246                 return -EINVAL;                                         \
247         }                                                               \
248         strlcpy(buff, attr, len);                                       \
249         return strchop(buff);                                           \
250 }
251
252 declare_sysfs_get_str(devtype);
253 declare_sysfs_get_str(vendor);
254 declare_sysfs_get_str(model);
255 declare_sysfs_get_str(rev);
256
257 static ssize_t
258 sysfs_get_binary (struct udev_device * udev, const char *attrname,
259                   unsigned char *buff, size_t len)
260 {
261         ssize_t attr_len;
262         const char * devname;
263
264         if (!udev) {
265                 condlog(3, "No udev device given\n");
266                 return -ENOSYS;
267         }
268
269         devname = udev_device_get_sysname(udev);
270         attr_len = sysfs_bin_attr_get_value(udev, attrname, buff, len);
271         if (attr_len < 0) {
272                 condlog(3, "%s: attribute %s not found in sysfs",
273                         devname, attrname);
274                 return attr_len;
275         }
276         return attr_len;
277 }
278
279 ssize_t sysfs_get_vpd(struct udev_device * udev, unsigned char pg,
280                       unsigned char *buff, size_t len)
281 {
282         char attrname[9];
283
284         snprintf(attrname, sizeof(attrname), "vpd_pg%02x", pg);
285         return sysfs_get_binary(udev, attrname, buff, len);
286 }
287
288 ssize_t sysfs_get_inquiry(struct udev_device * udev,
289                           unsigned char *buff, size_t len)
290 {
291         return sysfs_get_binary(udev, "inquiry", buff, len);
292 }
293
294 int
295 sysfs_get_timeout(const struct path *pp, unsigned int *timeout)
296 {
297         const char *attr = NULL;
298         const char *subsys;
299         struct udev_device *parent;
300         char *eptr;
301         unsigned long t;
302
303         if (!pp->udev || pp->bus != SYSFS_BUS_SCSI)
304                 return -ENOSYS;
305
306         parent = pp->udev;
307         while (parent) {
308                 subsys = udev_device_get_subsystem(parent);
309                 attr = udev_device_get_sysattr_value(parent, "timeout");
310                 if (subsys && attr)
311                         break;
312                 parent = udev_device_get_parent(parent);
313         }
314         if (!attr) {
315                 condlog(3, "%s: No timeout value in sysfs", pp->dev);
316                 return -ENXIO;
317         }
318
319         t = strtoul(attr, &eptr, 0);
320         if (attr == eptr || t == ULONG_MAX) {
321                 condlog(3, "%s: Cannot parse timeout attribute '%s'",
322                         pp->dev, attr);
323                 return -EINVAL;
324         }
325         if (t > UINT_MAX) {
326                 condlog(3, "%s: Overflow in timeout value '%s'",
327                         pp->dev, attr);
328                 return -ERANGE;
329         }
330         *timeout = t;
331
332         return 1;
333 }
334
335 static int
336 sysfs_get_tgt_nodename(struct path *pp, char *node)
337 {
338         const char *tgtname, *value;
339         struct udev_device *parent, *tgtdev;
340         int host, channel, tgtid = -1;
341
342         parent = udev_device_get_parent_with_subsystem_devtype(pp->udev, "scsi", "scsi_device");
343         if (!parent)
344                 return 1;
345         /* Check for SAS */
346         value = udev_device_get_sysattr_value(parent, "sas_address");
347         if (value) {
348                 tgtdev = udev_device_get_parent(parent);
349                 while (tgtdev) {
350                         tgtname = udev_device_get_sysname(tgtdev);
351                         if (sscanf(tgtname, "end_device-%d:%d",
352                                    &host, &tgtid) == 2)
353                                 break;
354                         tgtdev = udev_device_get_parent(tgtdev);
355                         tgtid = -1;
356                 }
357                 if (tgtid >= 0) {
358                         pp->sg_id.proto_id = SCSI_PROTOCOL_SAS;
359                         pp->sg_id.transport_id = tgtid;
360                         strlcpy(node, value, NODE_NAME_SIZE);
361                         return 0;
362                 }
363         }
364
365         /* Check for USB */
366         tgtdev = udev_device_get_parent(parent);
367         while (tgtdev) {
368                 value = udev_device_get_subsystem(tgtdev);
369                 if (value && !strcmp(value, "usb")) {
370                         pp->sg_id.proto_id = SCSI_PROTOCOL_UNSPEC;
371                         tgtname = udev_device_get_sysname(tgtdev);
372                         strlcpy(node, tgtname, NODE_NAME_SIZE);
373                         condlog(3, "%s: skip USB device %s", pp->dev, node);
374                         return 1;
375                 }
376                 tgtdev = udev_device_get_parent(tgtdev);
377         }
378         parent = udev_device_get_parent_with_subsystem_devtype(pp->udev, "scsi", "scsi_target");
379         if (!parent)
380                 return 1;
381         /* Check for FibreChannel */
382         tgtdev = udev_device_get_parent(parent);
383         value = udev_device_get_sysname(tgtdev);
384         if (sscanf(value, "rport-%d:%d-%d",
385                    &host, &channel, &tgtid) == 3) {
386                 tgtdev = udev_device_new_from_subsystem_sysname(udev,
387                                 "fc_remote_ports", value);
388                 if (tgtdev) {
389                         condlog(3, "SCSI target %d:%d:%d -> "
390                                 "FC rport %d:%d-%d",
391                                 pp->sg_id.host_no, pp->sg_id.channel,
392                                 pp->sg_id.scsi_id, host, channel,
393                                 tgtid);
394                         value = udev_device_get_sysattr_value(tgtdev,
395                                                               "node_name");
396                         if (value) {
397                                 pp->sg_id.proto_id = SCSI_PROTOCOL_FCP;
398                                 pp->sg_id.transport_id = tgtid;
399                                 strlcpy(node, value, NODE_NAME_SIZE);
400                                 udev_device_unref(tgtdev);
401                                 return 0;
402                         } else
403                                 udev_device_unref(tgtdev);
404                 }
405         }
406
407         /* Check for iSCSI */
408         parent = pp->udev;
409         tgtname = NULL;
410         while (parent) {
411                 tgtname = udev_device_get_sysname(parent);
412                 if (tgtname && sscanf(tgtname , "session%d", &tgtid) == 1)
413                         break;
414                 parent = udev_device_get_parent(parent);
415                 tgtname = NULL;
416                 tgtid = -1;
417         }
418         if (parent && tgtname) {
419                 tgtdev = udev_device_new_from_subsystem_sysname(udev,
420                                 "iscsi_session", tgtname);
421                 if (tgtdev) {
422                         const char *value;
423
424                         value = udev_device_get_sysattr_value(tgtdev, "targetname");
425                         if (value) {
426                                 pp->sg_id.proto_id = SCSI_PROTOCOL_ISCSI;
427                                 pp->sg_id.transport_id = tgtid;
428                                 strlcpy(node, value, NODE_NAME_SIZE);
429                                 udev_device_unref(tgtdev);
430                                 return 0;
431                         }
432                         else
433                                 udev_device_unref(tgtdev);
434                 }
435         }
436         /* Check for libata */
437         parent = pp->udev;
438         tgtname = NULL;
439         while (parent) {
440                 tgtname = udev_device_get_sysname(parent);
441                 if (tgtname && sscanf(tgtname, "ata%d", &tgtid) == 1)
442                         break;
443                 parent = udev_device_get_parent(parent);
444                 tgtname = NULL;
445         }
446         if (tgtname) {
447                 pp->sg_id.proto_id = SCSI_PROTOCOL_ATA;
448                 pp->sg_id.transport_id = tgtid;
449                 snprintf(node, NODE_NAME_SIZE, "ata-%d.00", tgtid);
450                 return 0;
451         }
452         /* Unknown SCSI transport. Keep fingers crossed */
453         pp->sg_id.proto_id = SCSI_PROTOCOL_UNSPEC;
454         return 0;
455 }
456
457 int sysfs_get_host_adapter_name(const struct path *pp, char *adapter_name)
458 {
459         int proto_id;
460
461         if (!pp || !adapter_name)
462                 return 1;
463
464         proto_id = pp->sg_id.proto_id;
465
466         if (proto_id != SCSI_PROTOCOL_FCP &&
467             proto_id != SCSI_PROTOCOL_SAS &&
468             proto_id != SCSI_PROTOCOL_ISCSI &&
469             proto_id != SCSI_PROTOCOL_SRP) {
470                 return 1;
471         }
472         /* iscsi doesn't have adapter info in sysfs
473          * get ip_address for grouping paths
474          */
475         if (pp->sg_id.proto_id == SCSI_PROTOCOL_ISCSI)
476                 return sysfs_get_iscsi_ip_address(pp, adapter_name);
477
478         /* fetch adapter pci name for other protocols
479          */
480         return sysfs_get_host_pci_name(pp, adapter_name);
481 }
482
483 int sysfs_get_host_pci_name(const struct path *pp, char *pci_name)
484 {
485         struct udev_device *hostdev, *parent;
486         char host_name[HOST_NAME_LEN];
487         const char *driver_name, *value;
488
489         if (!pp || !pci_name)
490                 return 1;
491
492         sprintf(host_name, "host%d", pp->sg_id.host_no);
493         hostdev = udev_device_new_from_subsystem_sysname(udev,
494                         "scsi_host", host_name);
495         if (!hostdev)
496                 return 1;
497
498         parent = udev_device_get_parent(hostdev);
499         while (parent) {
500                 driver_name = udev_device_get_driver(parent);
501                 if (!driver_name) {
502                         parent = udev_device_get_parent(parent);
503                         continue;
504                 }
505                 if (!strcmp(driver_name, "pcieport"))
506                         break;
507                 parent = udev_device_get_parent(parent);
508         }
509         if (parent) {
510                 /* pci_device found
511                  */
512                 value = udev_device_get_sysname(parent);
513
514                 strncpy(pci_name, value, SLOT_NAME_SIZE);
515                 udev_device_unref(hostdev);
516                 return 0;
517         }
518         udev_device_unref(hostdev);
519         return 1;
520 }
521
522 int sysfs_get_iscsi_ip_address(const struct path *pp, char *ip_address)
523 {
524         struct udev_device *hostdev;
525         char host_name[HOST_NAME_LEN];
526         const char *value;
527
528         sprintf(host_name, "host%d", pp->sg_id.host_no);
529         hostdev = udev_device_new_from_subsystem_sysname(udev,
530                         "iscsi_host", host_name);
531         if (hostdev) {
532                 value = udev_device_get_sysattr_value(hostdev,
533                                 "ipaddress");
534                 if (value) {
535                         strncpy(ip_address, value, SLOT_NAME_SIZE);
536                         udev_device_unref(hostdev);
537                         return 0;
538                 } else
539                         udev_device_unref(hostdev);
540         }
541         return 1;
542 }
543
544 int
545 sysfs_get_asymmetric_access_state(struct path *pp, char *buff, int buflen)
546 {
547         struct udev_device *parent = pp->udev;
548         char value[16], *eptr;
549         unsigned long preferred;
550
551         while (parent) {
552                 const char *subsys = udev_device_get_subsystem(parent);
553                 if (subsys && !strncmp(subsys, "scsi", 4))
554                         break;
555                 parent = udev_device_get_parent(parent);
556         }
557
558         if (!parent)
559                 return -1;
560
561         if (sysfs_attr_get_value(parent, "access_state", buff, buflen) <= 0)
562                 return -1;
563
564         if (sysfs_attr_get_value(parent, "preferred_path", value, 16) <= 0)
565                 return 0;
566
567         preferred = strtoul(value, &eptr, 0);
568         if (value == eptr || preferred == ULONG_MAX) {
569                 /* Parse error, ignore */
570                 return 0;
571         }
572         return !!preferred;
573 }
574
575 static void
576 sysfs_set_rport_tmo(struct multipath *mpp, struct path *pp)
577 {
578         struct udev_device *rport_dev = NULL;
579         char value[16], *eptr;
580         char rport_id[32];
581         unsigned long long tmo = 0;
582         int ret;
583
584         sprintf(rport_id, "rport-%d:%d-%d",
585                 pp->sg_id.host_no, pp->sg_id.channel, pp->sg_id.transport_id);
586         rport_dev = udev_device_new_from_subsystem_sysname(udev,
587                                 "fc_remote_ports", rport_id);
588         if (!rport_dev) {
589                 condlog(1, "%s: No fc_remote_port device for '%s'", pp->dev,
590                         rport_id);
591                 return;
592         }
593         condlog(4, "target%d:%d:%d -> %s", pp->sg_id.host_no,
594                 pp->sg_id.channel, pp->sg_id.scsi_id, rport_id);
595
596         /*
597          * read the current dev_loss_tmo value from sysfs
598          */
599         ret = sysfs_attr_get_value(rport_dev, "dev_loss_tmo", value, 16);
600         if (ret <= 0) {
601                 condlog(0, "%s: failed to read dev_loss_tmo value, "
602                         "error %d", rport_id, -ret);
603                 goto out;
604         }
605         tmo = strtoull(value, &eptr, 0);
606         if (value == eptr || tmo == ULLONG_MAX) {
607                 condlog(0, "%s: Cannot parse dev_loss_tmo "
608                         "attribute '%s'", rport_id, value);
609                 goto out;
610         }
611
612         /*
613          * This is tricky.
614          * dev_loss_tmo will be limited to 600 if fast_io_fail
615          * is _not_ set.
616          * fast_io_fail will be limited by the current dev_loss_tmo
617          * setting.
618          * So to get everything right we first need to increase
619          * dev_loss_tmo to the fast_io_fail setting (if present),
620          * then set fast_io_fail, and _then_ set dev_loss_tmo
621          * to the correct value.
622          */
623         if (mpp->fast_io_fail != MP_FAST_IO_FAIL_UNSET &&
624             mpp->fast_io_fail != MP_FAST_IO_FAIL_ZERO &&
625             mpp->fast_io_fail != MP_FAST_IO_FAIL_OFF) {
626                 /* Check if we need to temporarily increase dev_loss_tmo */
627                 if ((unsigned int)mpp->fast_io_fail >= tmo) {
628                         /* Increase dev_loss_tmo temporarily */
629                         snprintf(value, sizeof(value), "%u",
630                                  (unsigned int)mpp->fast_io_fail + 1);
631                         ret = sysfs_attr_set_value(rport_dev, "dev_loss_tmo",
632                                                    value, strlen(value));
633                         if (ret <= 0) {
634                                 if (ret == -EBUSY)
635                                         condlog(3, "%s: rport blocked",
636                                                 rport_id);
637                                 else
638                                         condlog(0, "%s: failed to set "
639                                                 "dev_loss_tmo to %s, error %d",
640                                                 rport_id, value, -ret);
641                                 goto out;
642                         }
643                 }
644         } else if (mpp->dev_loss > DEFAULT_DEV_LOSS_TMO &&
645                 mpp->no_path_retry != NO_PATH_RETRY_QUEUE) {
646                 condlog(3, "%s: limiting dev_loss_tmo to %d, since "
647                         "fast_io_fail is not set",
648                         rport_id, DEFAULT_DEV_LOSS_TMO);
649                 mpp->dev_loss = DEFAULT_DEV_LOSS_TMO;
650         }
651         if (mpp->fast_io_fail != MP_FAST_IO_FAIL_UNSET) {
652                 if (mpp->fast_io_fail == MP_FAST_IO_FAIL_OFF)
653                         sprintf(value, "off");
654                 else if (mpp->fast_io_fail == MP_FAST_IO_FAIL_ZERO)
655                         sprintf(value, "0");
656                 else
657                         snprintf(value, 16, "%u", mpp->fast_io_fail);
658                 ret = sysfs_attr_set_value(rport_dev, "fast_io_fail_tmo",
659                                            value, strlen(value));
660                 if (ret <= 0) {
661                         if (ret == -EBUSY)
662                                 condlog(3, "%s: rport blocked", rport_id);
663                         else
664                                 condlog(0, "%s: failed to set fast_io_fail_tmo to %s, error %d",
665                                         rport_id, value, -ret);
666                 }
667         }
668         if (mpp->dev_loss > 0) {
669                 snprintf(value, 16, "%u", mpp->dev_loss);
670                 ret = sysfs_attr_set_value(rport_dev, "dev_loss_tmo",
671                                            value, strlen(value));
672                 if (ret <= 0) {
673                         if (ret == -EBUSY)
674                                 condlog(3, "%s: rport blocked", rport_id);
675                         else
676                                 condlog(0, "%s: failed to set dev_loss_tmo to %s, error %d",
677                                         rport_id, value, -ret);
678                 }
679         }
680 out:
681         udev_device_unref(rport_dev);
682 }
683
684 static void
685 sysfs_set_session_tmo(struct multipath *mpp, struct path *pp)
686 {
687         struct udev_device *session_dev = NULL;
688         char session_id[64];
689         char value[11];
690
691         sprintf(session_id, "session%d", pp->sg_id.transport_id);
692         session_dev = udev_device_new_from_subsystem_sysname(udev,
693                                 "iscsi_session", session_id);
694         if (!session_dev) {
695                 condlog(1, "%s: No iscsi session for '%s'", pp->dev,
696                         session_id);
697                 return;
698         }
699         condlog(4, "target%d:%d:%d -> %s", pp->sg_id.host_no,
700                 pp->sg_id.channel, pp->sg_id.scsi_id, session_id);
701
702         if (mpp->dev_loss) {
703                 condlog(3, "%s: ignoring dev_loss_tmo on iSCSI", pp->dev);
704         }
705         if (mpp->fast_io_fail != MP_FAST_IO_FAIL_UNSET) {
706                 if (mpp->fast_io_fail == MP_FAST_IO_FAIL_OFF) {
707                         condlog(3, "%s: can't switch off fast_io_fail_tmo "
708                                 "on iSCSI", pp->dev);
709                 } else if (mpp->fast_io_fail == MP_FAST_IO_FAIL_ZERO) {
710                         condlog(3, "%s: can't set fast_io_fail_tmo to '0'"
711                                 "on iSCSI", pp->dev);
712                 } else {
713                         snprintf(value, 11, "%u", mpp->fast_io_fail);
714                         if (sysfs_attr_set_value(session_dev, "recovery_tmo",
715                                                  value, strlen(value)) <= 0) {
716                                 condlog(3, "%s: Failed to set recovery_tmo, "
717                                         " error %d", pp->dev, errno);
718                         }
719                 }
720         }
721         udev_device_unref(session_dev);
722         return;
723 }
724
725 static void
726 sysfs_set_nexus_loss_tmo(struct multipath *mpp, struct path *pp)
727 {
728         struct udev_device *sas_dev = NULL;
729         char end_dev_id[64];
730         char value[11];
731
732         sprintf(end_dev_id, "end_device-%d:%d",
733                 pp->sg_id.host_no, pp->sg_id.transport_id);
734         sas_dev = udev_device_new_from_subsystem_sysname(udev,
735                                 "sas_end_device", end_dev_id);
736         if (!sas_dev) {
737                 condlog(1, "%s: No SAS end device for '%s'", pp->dev,
738                         end_dev_id);
739                 return;
740         }
741         condlog(4, "target%d:%d:%d -> %s", pp->sg_id.host_no,
742                 pp->sg_id.channel, pp->sg_id.scsi_id, end_dev_id);
743
744         if (mpp->dev_loss) {
745                 snprintf(value, 11, "%u", mpp->dev_loss);
746                 if (sysfs_attr_set_value(sas_dev, "I_T_nexus_loss_timeout",
747                                          value, strlen(value)) <= 0)
748                         condlog(3, "%s: failed to update "
749                                 "I_T Nexus loss timeout, error %d",
750                                 pp->dev, errno);
751         }
752         udev_device_unref(sas_dev);
753         return;
754 }
755
756 int
757 sysfs_set_scsi_tmo (struct multipath *mpp, unsigned int checkint)
758 {
759         struct path *pp;
760         int i;
761         unsigned int dev_loss_tmo = mpp->dev_loss;
762
763         if (mpp->no_path_retry > 0) {
764                 uint64_t no_path_retry_tmo =
765                         (uint64_t)mpp->no_path_retry * checkint;
766
767                 if (no_path_retry_tmo > MAX_DEV_LOSS_TMO)
768                         no_path_retry_tmo = MAX_DEV_LOSS_TMO;
769                 if (no_path_retry_tmo > dev_loss_tmo)
770                         dev_loss_tmo = no_path_retry_tmo;
771                 condlog(3, "%s: update dev_loss_tmo to %u",
772                         mpp->alias, dev_loss_tmo);
773         } else if (mpp->no_path_retry == NO_PATH_RETRY_QUEUE) {
774                 dev_loss_tmo = MAX_DEV_LOSS_TMO;
775                 condlog(3, "%s: update dev_loss_tmo to %u",
776                         mpp->alias, dev_loss_tmo);
777         }
778         mpp->dev_loss = dev_loss_tmo;
779         if (mpp->dev_loss && mpp->fast_io_fail > 0 &&
780             (unsigned int)mpp->fast_io_fail >= mpp->dev_loss) {
781                 condlog(3, "%s: turning off fast_io_fail (%d is not smaller than dev_loss_tmo)",
782                         mpp->alias, mpp->fast_io_fail);
783                 mpp->fast_io_fail = MP_FAST_IO_FAIL_OFF;
784         }
785         if (!mpp->dev_loss && mpp->fast_io_fail == MP_FAST_IO_FAIL_UNSET)
786                 return 0;
787
788         vector_foreach_slot(mpp->paths, pp, i) {
789                 if (pp->sg_id.proto_id == SCSI_PROTOCOL_FCP)
790                         sysfs_set_rport_tmo(mpp, pp);
791                 if (pp->sg_id.proto_id == SCSI_PROTOCOL_ISCSI)
792                         sysfs_set_session_tmo(mpp, pp);
793                 if (pp->sg_id.proto_id == SCSI_PROTOCOL_SAS)
794                         sysfs_set_nexus_loss_tmo(mpp, pp);
795         }
796         return 0;
797 }
798
799 int
800 do_inq(int sg_fd, int cmddt, int evpd, unsigned int pg_op,
801        void *resp, int mx_resp_len)
802 {
803         unsigned char inqCmdBlk[INQUIRY_CMDLEN] =
804                 { INQUIRY_CMD, 0, 0, 0, 0, 0 };
805         unsigned char sense_b[SENSE_BUFF_LEN];
806         struct sg_io_hdr io_hdr;
807
808         if (cmddt)
809                 inqCmdBlk[1] |= 2;
810         if (evpd)
811                 inqCmdBlk[1] |= 1;
812         inqCmdBlk[2] = (unsigned char) pg_op;
813         inqCmdBlk[3] = (unsigned char)((mx_resp_len >> 8) & 0xff);
814         inqCmdBlk[4] = (unsigned char) (mx_resp_len & 0xff);
815         memset(&io_hdr, 0, sizeof (struct sg_io_hdr));
816         memset(sense_b, 0, SENSE_BUFF_LEN);
817         io_hdr.interface_id = 'S';
818         io_hdr.cmd_len = sizeof (inqCmdBlk);
819         io_hdr.mx_sb_len = sizeof (sense_b);
820         io_hdr.dxfer_direction = SG_DXFER_FROM_DEV;
821         io_hdr.dxfer_len = mx_resp_len;
822         io_hdr.dxferp = resp;
823         io_hdr.cmdp = inqCmdBlk;
824         io_hdr.sbp = sense_b;
825         io_hdr.timeout = DEF_TIMEOUT * 1000;
826
827         if (ioctl(sg_fd, SG_IO, &io_hdr) < 0)
828                 return -1;
829
830         /* treat SG_ERR here to get rid of sg_err.[ch] */
831         io_hdr.status &= 0x7e;
832         if ((0 == io_hdr.status) && (0 == io_hdr.host_status) &&
833             (0 == io_hdr.driver_status))
834                 return 0;
835         if ((SCSI_CHECK_CONDITION == io_hdr.status) ||
836             (SCSI_COMMAND_TERMINATED == io_hdr.status) ||
837             (SG_ERR_DRIVER_SENSE == (0xf & io_hdr.driver_status))) {
838                 if (io_hdr.sbp && (io_hdr.sb_len_wr > 2)) {
839                         int sense_key;
840                         unsigned char * sense_buffer = io_hdr.sbp;
841                         if (sense_buffer[0] & 0x2)
842                                 sense_key = sense_buffer[1] & 0xf;
843                         else
844                                 sense_key = sense_buffer[2] & 0xf;
845                         if(RECOVERED_ERROR == sense_key)
846                                 return 0;
847                 }
848         }
849         return -1;
850 }
851
852 static int
853 get_serial (char * str, int maxlen, int fd)
854 {
855         int len = 0;
856         char buff[MX_ALLOC_LEN + 1] = {0};
857
858         if (fd < 0)
859                 return 1;
860
861         if (0 == do_inq(fd, 0, 1, 0x80, buff, MX_ALLOC_LEN)) {
862                 len = buff[3];
863                 if (len >= maxlen)
864                         return 1;
865                 if (len > 0) {
866                         memcpy(str, buff + 4, len);
867                         str[len] = '\0';
868                 }
869                 return 0;
870         }
871         return 1;
872 }
873
874 static void
875 detect_alua(struct path * pp)
876 {
877         int ret;
878         int tpgs;
879         unsigned int timeout;
880
881         if (sysfs_get_timeout(pp, &timeout) <= 0)
882                 timeout = DEF_TIMEOUT;
883
884         if ((tpgs = get_target_port_group_support(pp, timeout)) <= 0) {
885                 pp->tpgs = TPGS_NONE;
886                 return;
887         }
888         ret = get_target_port_group(pp, timeout);
889         if (ret < 0 || get_asymmetric_access_state(pp, ret, timeout) < 0) {
890                 pp->tpgs = TPGS_NONE;
891                 return;
892         }
893         pp->tpgs = tpgs;
894 }
895
896 int path_get_tpgs(struct path *pp)
897 {
898         if (pp->tpgs == TPGS_UNDEF)
899                 detect_alua(pp);
900         return pp->tpgs;
901 }
902
903 #define DEFAULT_SGIO_LEN 254
904
905 /* Query VPD page @pg. Returns number of INQUIRY bytes
906    upon success and -1 upon failure. */
907 static int
908 sgio_get_vpd (unsigned char * buff, int maxlen, int fd, int pg)
909 {
910         int len = DEFAULT_SGIO_LEN;
911         int rlen;
912
913         if (fd < 0) {
914                 errno = EBADF;
915                 return -1;
916         }
917 retry:
918         if (0 == do_inq(fd, 0, 1, pg, buff, len)) {
919                 rlen = get_unaligned_be16(&buff[2]) + 4;
920                 if (rlen <= len || len >= maxlen)
921                         return rlen;
922                 len = (rlen < maxlen)? rlen : maxlen;
923                 goto retry;
924         }
925         return -1;
926 }
927
928 static int
929 get_geometry(struct path *pp)
930 {
931         if (pp->fd < 0)
932                 return 1;
933
934         if (ioctl(pp->fd, HDIO_GETGEO, &pp->geom)) {
935                 condlog(2, "%s: HDIO_GETGEO failed with %d", pp->dev, errno);
936                 memset(&pp->geom, 0, sizeof(pp->geom));
937                 return 1;
938         }
939         condlog(3, "%s: %u cyl, %u heads, %u sectors/track, start at %lu",
940                 pp->dev, pp->geom.cylinders, pp->geom.heads,
941                 pp->geom.sectors, pp->geom.start);
942         return 0;
943 }
944
945 static int
946 parse_vpd_pg80(const unsigned char *in, char *out, size_t out_len)
947 {
948         size_t len = get_unaligned_be16(&in[2]);
949
950         if (out_len == 0)
951                 return 0;
952
953         /*
954          * Strip leading and trailing whitespace
955          */
956         while (len > 0 && in[len + 3] == ' ')
957                 --len;
958         while (len > 0 && in[4] == ' ') {
959                 ++in;
960                 --len;
961         }
962
963         if (len >= out_len) {
964                 condlog(2, "vpd pg80 overflow, %lu/%lu bytes required",
965                         len + 1, out_len);
966                 len = out_len - 1;
967         }
968         if (len > 0) {
969                 memcpy(out, in + 4, len);
970                 out[len] = '\0';
971         }
972         return len;
973 }
974
975 static int
976 parse_vpd_pg83(const unsigned char *in, size_t in_len,
977                char *out, size_t out_len)
978 {
979         const unsigned char *d;
980         const unsigned char *vpd = NULL;
981         size_t len, vpd_len, i;
982         int vpd_type, prio = -1, naa_prio;
983
984         d = in + 4;
985         while (d < in + in_len) {
986                 /* Select 'association: LUN' */
987                 if ((d[1] & 0x30) != 0) {
988                         d += d[3] + 4;
989                         continue;
990                 }
991                 switch (d[1] & 0xf) {
992                 case 0x3:
993                         /* NAA: Prio 5 */
994                         switch (d[4] >> 4) {
995                         case 6:
996                                 /* IEEE Registered Extended: Prio 8 */
997                                 naa_prio = 8;
998                                 break;
999                         case 5:
1000                                 /* IEEE Registered: Prio 7 */
1001                                 naa_prio = 7;
1002                                 break;
1003                         case 2:
1004                                 /* IEEE Extended: Prio 6 */
1005                                 naa_prio = 6;
1006                                 break;
1007                         case 3:
1008                                 /* IEEE Locally assigned: Prio 1 */
1009                                 naa_prio = 1;
1010                                 break;
1011                         default:
1012                                 /* Default: no priority */
1013                                 naa_prio = -1;
1014                                 break;
1015                         }
1016                         if (prio < naa_prio) {
1017                                 prio = naa_prio;
1018                                 vpd = d;
1019                         }
1020                         break;
1021                 case 0x8:
1022                         /* SCSI Name: Prio 4 */
1023                         if (memcmp(d + 4, "eui.", 4) &&
1024                             memcmp(d + 4, "naa.", 4) &&
1025                             memcmp(d + 4, "iqn.", 4))
1026                                 continue;
1027                         if (prio < 4) {
1028                                 prio = 4;
1029                                 vpd = d;
1030                         }
1031                         break;
1032                 case 0x2:
1033                         /* EUI-64: Prio 3 */
1034                         if (prio < 3) {
1035                                 prio = 3;
1036                                 vpd = d;
1037                         }
1038                         break;
1039                 case 0x1:
1040                         /* T-10 Vendor ID: Prio 2 */
1041                         if (prio < 2) {
1042                                 prio = 2;
1043                                 vpd = d;
1044                         }
1045                         break;
1046                 }
1047                 d += d[3] + 4;
1048         }
1049
1050         if (prio <= 0)
1051                 return -ENODATA;
1052         /* Need space at least for one digit */
1053         else if (out_len <= 1)
1054                 return 0;
1055
1056         len = 0;
1057         vpd_type = vpd[1] & 0xf;
1058         vpd_len = vpd[3];
1059         vpd += 4;
1060         if (vpd_type == 0x2 || vpd_type == 0x3) {
1061                 size_t i;
1062
1063                 len = sprintf(out, "%d", vpd_type);
1064                 if (2 * vpd_len >= out_len - len) {
1065                         condlog(1, "%s: WWID overflow, type %d, %lu/%lu bytes required",
1066                                 __func__, vpd_type,
1067                                 2 * vpd_len + len + 1, out_len);
1068                         vpd_len = (out_len - len - 1) / 2;
1069                 }
1070                 for (i = 0; i < vpd_len; i++)
1071                         len += sprintf(out + len,
1072                                        "%02x", vpd[i]);
1073         } else if (vpd_type == 0x8 && vpd_len < 4) {
1074                 condlog(1, "%s: VPD length %lu too small for designator type 8",
1075                         __func__, vpd_len);
1076                 return -EINVAL;
1077         } else if (vpd_type == 0x8) {
1078                 if (!memcmp("eui.", vpd, 4))
1079                         out[0] =  '2';
1080                 else if (!memcmp("naa.", vpd, 4))
1081                         out[0] = '3';
1082                 else
1083                         out[0] = '8';
1084
1085                 vpd += 4;
1086                 len = vpd_len - 4;
1087                 while (len > 2 && vpd[len - 2] == '\0')
1088                         --len;
1089                 if (len > out_len - 1) {
1090                         condlog(1, "%s: WWID overflow, type 8/%c, %lu/%lu bytes required",
1091                                 __func__, out[0], len + 1, out_len);
1092                         len = out_len - 1;
1093                 }
1094
1095                 if (out[0] == '8')
1096                         for (i = 0; i < len; ++i)
1097                                 out[1 + i] = vpd[i];
1098                 else
1099                         for (i = 0; i < len; ++i)
1100                                 out[1 + i] = tolower(vpd[i]);
1101
1102                 /* designator should be 0-terminated, but let's make sure */
1103                 out[len] = '\0';
1104
1105         } else if (vpd_type == 0x1) {
1106                 const unsigned char *p;
1107                 size_t p_len;
1108
1109                 out[0] = '1';
1110                 len = 1;
1111                 while ((p = memchr(vpd, ' ', vpd_len))) {
1112                         p_len = p - vpd;
1113                         if (len + p_len > out_len - 1) {
1114                                 condlog(1, "%s: WWID overflow, type 1, %lu/%lu bytes required",
1115                                         __func__, len + p_len, out_len);
1116                                 p_len = out_len - len - 1;
1117                         }
1118                         memcpy(out + len, vpd, p_len);
1119                         len += p_len;
1120                         if (len >= out_len - 1) {
1121                                 out[len] = '\0';
1122                                 break;
1123                         }
1124                         out[len] = '_';
1125                         len ++;
1126                         if (len >= out_len - 1) {
1127                                 out[len] = '\0';
1128                                 break;
1129                         }
1130                         vpd = p;
1131                         vpd_len -= p_len;
1132                         while (vpd && *vpd == ' ') {
1133                                 vpd++;
1134                                 vpd_len --;
1135                         }
1136                 }
1137                 p_len = vpd_len;
1138                 if (p_len > 0 && len < out_len - 1) {
1139                         if (len + p_len > out_len - 1) {
1140                                 condlog(1, "%s: WWID overflow, type 1, %lu/%lu bytes required",
1141                                         __func__, len + p_len + 1, out_len);
1142                                 p_len = out_len - len - 1;
1143                         }
1144                         memcpy(out + len, vpd, p_len);
1145                         len += p_len;
1146                         out[len] = '\0';
1147                 }
1148                 if (len > 1 && out[len - 1] == '_') {
1149                         out[len - 1] = '\0';
1150                         len--;
1151                 }
1152         }
1153         return len;
1154 }
1155
1156 static int
1157 get_vpd_sysfs (struct udev_device *parent, int pg, char * str, int maxlen)
1158 {
1159         int len, buff_len;
1160         unsigned char buff[4096];
1161
1162         memset(buff, 0x0, 4096);
1163         if (!parent || sysfs_get_vpd(parent, pg, buff, 4096) <= 0) {
1164                 condlog(3, "failed to read sysfs vpd pg%02x", pg);
1165                 return -EINVAL;
1166         }
1167
1168         if (buff[1] != pg) {
1169                 condlog(3, "vpd pg%02x error, invalid vpd page %02x",
1170                         pg, buff[1]);
1171                 return -ENODATA;
1172         }
1173         buff_len = get_unaligned_be16(&buff[2]) + 4;
1174         if (buff_len > 4096)
1175                 condlog(3, "vpd pg%02x page truncated", pg);
1176
1177         if (pg == 0x80)
1178                 len = parse_vpd_pg80(buff, str, maxlen);
1179         else if (pg == 0x83)
1180                 len = parse_vpd_pg83(buff, buff_len, str, maxlen);
1181         else
1182                 len = -ENOSYS;
1183
1184         return len;
1185 }
1186
1187 int
1188 get_vpd_sgio (int fd, int pg, int vend_id, char * str, int maxlen)
1189 {
1190         int len, buff_len;
1191         unsigned char buff[4096];
1192
1193         memset(buff, 0x0, 4096);
1194         if (sgio_get_vpd(buff, 4096, fd, pg) < 0) {
1195                 int lvl = pg == 0x80 || pg == 0x83 ? 3 : 4;
1196
1197                 condlog(lvl, "failed to issue vpd inquiry for pg%02x",
1198                         pg);
1199                 return -errno;
1200         }
1201
1202         if (buff[1] != pg) {
1203                 condlog(3, "vpd pg%02x error, invalid vpd page %02x",
1204                         pg, buff[1]);
1205                 return -ENODATA;
1206         }
1207         buff_len = get_unaligned_be16(&buff[2]) + 4;
1208         if (buff_len > 4096) {
1209                 condlog(3, "vpd pg%02x page truncated", pg);
1210                 buff_len = 4096;
1211         }
1212         if (pg == 0x80)
1213                 len = parse_vpd_pg80(buff, str, maxlen);
1214         else if (pg == 0x83)
1215                 len = parse_vpd_pg83(buff, buff_len, str, maxlen);
1216         else if (pg == 0xc9 && maxlen >= 8) {
1217                 if (buff_len < 8)
1218                         len = -ENODATA;
1219                 else {
1220                         len = (buff_len <= maxlen)? buff_len : maxlen;
1221                         memcpy (str, buff, len);
1222                 }
1223         } else
1224                 len = -ENOSYS;
1225
1226         return len;
1227 }
1228
1229 static int
1230 scsi_sysfs_pathinfo (struct path * pp, vector hwtable)
1231 {
1232         struct udev_device *parent;
1233         const char *attr_path = NULL;
1234
1235         parent = pp->udev;
1236         while (parent) {
1237                 const char *subsys = udev_device_get_subsystem(parent);
1238                 if (subsys && !strncmp(subsys, "scsi", 4)) {
1239                         attr_path = udev_device_get_sysname(parent);
1240                         if (!attr_path)
1241                                 break;
1242                         if (sscanf(attr_path, "%i:%i:%i:%i",
1243                                    &pp->sg_id.host_no,
1244                                    &pp->sg_id.channel,
1245                                    &pp->sg_id.scsi_id,
1246                                    &pp->sg_id.lun) == 4)
1247                                 break;
1248                 }
1249                 parent = udev_device_get_parent(parent);
1250         }
1251         if (!attr_path || pp->sg_id.host_no == -1)
1252                 return PATHINFO_FAILED;
1253
1254         if (sysfs_get_vendor(parent, pp->vendor_id, SCSI_VENDOR_SIZE) <= 0)
1255                 return PATHINFO_FAILED;;
1256
1257         condlog(3, "%s: vendor = %s", pp->dev, pp->vendor_id);
1258
1259         if (sysfs_get_model(parent, pp->product_id, PATH_PRODUCT_SIZE) <= 0)
1260                 return PATHINFO_FAILED;;
1261
1262         condlog(3, "%s: product = %s", pp->dev, pp->product_id);
1263
1264         if (sysfs_get_rev(parent, pp->rev, PATH_REV_SIZE) < 0)
1265                 return PATHINFO_FAILED;;
1266
1267         condlog(3, "%s: rev = %s", pp->dev, pp->rev);
1268
1269         /*
1270          * set the hwe configlet pointer
1271          */
1272         find_hwe(hwtable, pp->vendor_id, pp->product_id, pp->rev, pp->hwe);
1273
1274         /*
1275          * host / bus / target / lun
1276          */
1277         condlog(3, "%s: h:b:t:l = %i:%i:%i:%i",
1278                         pp->dev,
1279                         pp->sg_id.host_no,
1280                         pp->sg_id.channel,
1281                         pp->sg_id.scsi_id,
1282                         pp->sg_id.lun);
1283
1284         /*
1285          * target node name
1286          */
1287         if(sysfs_get_tgt_nodename(pp, pp->tgt_node_name))
1288                 return PATHINFO_FAILED;
1289
1290         condlog(3, "%s: tgt_node_name = %s",
1291                 pp->dev, pp->tgt_node_name);
1292
1293         return PATHINFO_OK;
1294 }
1295
1296 static int
1297 nvme_sysfs_pathinfo (struct path * pp, vector hwtable)
1298 {
1299         struct udev_device *parent;
1300         const char *attr_path = NULL;
1301         const char *attr;
1302
1303         attr_path = udev_device_get_sysname(pp->udev);
1304         if (!attr_path)
1305                 return PATHINFO_FAILED;
1306
1307         if (sscanf(attr_path, "nvme%dn%d",
1308                    &pp->sg_id.host_no,
1309                    &pp->sg_id.scsi_id) != 2)
1310                 return PATHINFO_FAILED;
1311
1312         parent = udev_device_get_parent_with_subsystem_devtype(pp->udev,
1313                                                                "nvme", NULL);
1314         if (!parent)
1315                 return PATHINFO_SKIPPED;
1316
1317         attr = udev_device_get_sysattr_value(pp->udev, "nsid");
1318         pp->sg_id.lun = attr ? atoi(attr) : 0;
1319
1320         attr = udev_device_get_sysattr_value(parent, "cntlid");
1321         pp->sg_id.channel = attr ? atoi(attr) : 0;
1322
1323         snprintf(pp->vendor_id, SCSI_VENDOR_SIZE, "NVME");
1324         snprintf(pp->product_id, PATH_PRODUCT_SIZE, "%s",
1325                  udev_device_get_sysattr_value(parent, "model"));
1326         snprintf(pp->serial, SERIAL_SIZE, "%s",
1327                  udev_device_get_sysattr_value(parent, "serial"));
1328         snprintf(pp->rev, PATH_REV_SIZE, "%s",
1329                  udev_device_get_sysattr_value(parent, "firmware_rev"));
1330
1331         condlog(3, "%s: vendor = %s", pp->dev, pp->vendor_id);
1332         condlog(3, "%s: product = %s", pp->dev, pp->product_id);
1333         condlog(3, "%s: serial = %s", pp->dev, pp->serial);
1334         condlog(3, "%s: rev = %s", pp->dev, pp->rev);
1335
1336         find_hwe(hwtable, pp->vendor_id, pp->product_id, NULL, pp->hwe);
1337
1338         return PATHINFO_OK;
1339 }
1340
1341 static int
1342 ccw_sysfs_pathinfo (struct path * pp, vector hwtable)
1343 {
1344         struct udev_device *parent;
1345         char attr_buff[NAME_SIZE];
1346         const char *attr_path;
1347
1348         parent = pp->udev;
1349         while (parent) {
1350                 const char *subsys = udev_device_get_subsystem(parent);
1351                 if (subsys && !strncmp(subsys, "ccw", 3))
1352                         break;
1353                 parent = udev_device_get_parent(parent);
1354         }
1355         if (!parent)
1356                 return PATHINFO_FAILED;
1357
1358         sprintf(pp->vendor_id, "IBM");
1359
1360         condlog(3, "%s: vendor = %s", pp->dev, pp->vendor_id);
1361
1362         if (sysfs_get_devtype(parent, attr_buff, FILE_NAME_SIZE) <= 0)
1363                 return PATHINFO_FAILED;
1364
1365         if (!strncmp(attr_buff, "3370", 4)) {
1366                 sprintf(pp->product_id,"S/390 DASD FBA");
1367         } else if (!strncmp(attr_buff, "9336", 4)) {
1368                 sprintf(pp->product_id,"S/390 DASD FBA");
1369         } else {
1370                 sprintf(pp->product_id,"S/390 DASD ECKD");
1371         }
1372
1373         condlog(3, "%s: product = %s", pp->dev, pp->product_id);
1374
1375         /*
1376          * set the hwe configlet pointer
1377          */
1378         find_hwe(hwtable, pp->vendor_id, pp->product_id, NULL, pp->hwe);
1379
1380         /*
1381          * host / bus / target / lun
1382          */
1383         attr_path = udev_device_get_sysname(parent);
1384         pp->sg_id.lun = 0;
1385         if (sscanf(attr_path, "%i.%i.%x",
1386                    &pp->sg_id.host_no,
1387                    &pp->sg_id.channel,
1388                    &pp->sg_id.scsi_id) == 3) {
1389                 condlog(3, "%s: h:b:t:l = %i:%i:%i:%i",
1390                         pp->dev,
1391                         pp->sg_id.host_no,
1392                         pp->sg_id.channel,
1393                         pp->sg_id.scsi_id,
1394                         pp->sg_id.lun);
1395         }
1396
1397         return PATHINFO_OK;
1398 }
1399
1400 static int
1401 cciss_sysfs_pathinfo (struct path * pp, vector hwtable)
1402 {
1403         const char * attr_path = NULL;
1404         struct udev_device *parent;
1405
1406         parent = pp->udev;
1407         while (parent) {
1408                 const char *subsys = udev_device_get_subsystem(parent);
1409                 if (subsys && !strncmp(subsys, "cciss", 5)) {
1410                         attr_path = udev_device_get_sysname(parent);
1411                         if (!attr_path)
1412                                 break;
1413                         if (sscanf(attr_path, "c%id%i",
1414                                    &pp->sg_id.host_no,
1415                                    &pp->sg_id.scsi_id) == 2)
1416                                 break;
1417                 }
1418                 parent = udev_device_get_parent(parent);
1419         }
1420         if (!attr_path || pp->sg_id.host_no == -1)
1421                 return PATHINFO_FAILED;
1422
1423         if (sysfs_get_vendor(parent, pp->vendor_id, SCSI_VENDOR_SIZE) <= 0)
1424                 return PATHINFO_FAILED;
1425
1426         condlog(3, "%s: vendor = %s", pp->dev, pp->vendor_id);
1427
1428         if (sysfs_get_model(parent, pp->product_id, PATH_PRODUCT_SIZE) <= 0)
1429                 return PATHINFO_FAILED;
1430
1431         condlog(3, "%s: product = %s", pp->dev, pp->product_id);
1432
1433         if (sysfs_get_rev(parent, pp->rev, PATH_REV_SIZE) <= 0)
1434                 return PATHINFO_FAILED;
1435
1436         condlog(3, "%s: rev = %s", pp->dev, pp->rev);
1437
1438         /*
1439          * set the hwe configlet pointer
1440          */
1441         find_hwe(hwtable, pp->vendor_id, pp->product_id, pp->rev, pp->hwe);
1442
1443         /*
1444          * host / bus / target / lun
1445          */
1446         pp->sg_id.lun = 0;
1447         pp->sg_id.channel = 0;
1448         condlog(3, "%s: h:b:t:l = %i:%i:%i:%i",
1449                 pp->dev,
1450                 pp->sg_id.host_no,
1451                 pp->sg_id.channel,
1452                 pp->sg_id.scsi_id,
1453                 pp->sg_id.lun);
1454
1455         return PATHINFO_OK;
1456 }
1457
1458 static int
1459 common_sysfs_pathinfo (struct path * pp)
1460 {
1461         dev_t devt;
1462
1463         if (!pp)
1464                 return PATHINFO_FAILED;
1465
1466         if (!pp->udev) {
1467                 condlog(4, "%s: udev not initialised", pp->dev);
1468                 return PATHINFO_FAILED;
1469         }
1470         devt = udev_device_get_devnum(pp->udev);
1471         snprintf(pp->dev_t, BLK_DEV_SIZE, "%d:%d", major(devt), minor(devt));
1472
1473         condlog(4, "%s: dev_t = %s", pp->dev, pp->dev_t);
1474
1475         if (sysfs_get_size(pp, &pp->size))
1476                 return PATHINFO_FAILED;
1477
1478         condlog(3, "%s: size = %llu", pp->dev, pp->size);
1479
1480         return PATHINFO_OK;
1481 }
1482
1483 int
1484 path_offline (struct path * pp)
1485 {
1486         struct udev_device * parent;
1487         char buff[SCSI_STATE_SIZE];
1488         int err;
1489         const char *subsys_type;
1490
1491         if (pp->bus == SYSFS_BUS_SCSI) {
1492                 subsys_type = "scsi";
1493         }
1494         else if (pp->bus == SYSFS_BUS_NVME) {
1495                 subsys_type = "nvme";
1496         }
1497         else {
1498                 return PATH_UP;
1499         }
1500
1501         parent = pp->udev;
1502         while (parent) {
1503                 const char *subsys = udev_device_get_subsystem(parent);
1504                 if (subsys && !strncmp(subsys, subsys_type, 4))
1505                         break;
1506                 parent = udev_device_get_parent(parent);
1507         }
1508
1509         if (!parent) {
1510                 condlog(1, "%s: failed to get sysfs information", pp->dev);
1511                 return PATH_REMOVED;
1512         }
1513
1514         memset(buff, 0x0, SCSI_STATE_SIZE);
1515         err = sysfs_attr_get_value(parent, "state", buff, SCSI_STATE_SIZE);
1516         if (err <= 0) {
1517                 if (err == -ENXIO)
1518                         return PATH_REMOVED;
1519                 else
1520                         return PATH_DOWN;
1521         }
1522
1523
1524         condlog(4, "%s: path state = %s", pp->dev, buff);
1525
1526         if (pp->bus == SYSFS_BUS_SCSI) {
1527                 if (!strncmp(buff, "offline", 7)) {
1528                         pp->offline = 1;
1529                         return PATH_DOWN;
1530                 }
1531                 pp->offline = 0;
1532                 if (!strncmp(buff, "blocked", 7) ||
1533                     !strncmp(buff, "quiesce", 7))
1534                         return PATH_PENDING;
1535                 else if (!strncmp(buff, "running", 7))
1536                         return PATH_UP;
1537
1538         }
1539         else if (pp->bus == SYSFS_BUS_NVME) {
1540                 if (!strncmp(buff, "dead", 4)) {
1541                         pp->offline = 1;
1542                         return PATH_DOWN;
1543                 }
1544                 pp->offline = 0;
1545                 if (!strncmp(buff, "new", 3) ||
1546                     !strncmp(buff, "deleting", 8))
1547                         return PATH_PENDING;
1548                 else if (!strncmp(buff, "live", 4))
1549                         return PATH_UP;
1550         }
1551
1552         return PATH_DOWN;
1553 }
1554
1555 int
1556 sysfs_pathinfo(struct path * pp, vector hwtable)
1557 {
1558         int r = common_sysfs_pathinfo(pp);
1559
1560         if (r != PATHINFO_OK)
1561                 return r;
1562
1563         pp->bus = SYSFS_BUS_UNDEF;
1564         if (!strncmp(pp->dev,"cciss",5))
1565                 pp->bus = SYSFS_BUS_CCISS;
1566         if (!strncmp(pp->dev,"dasd", 4))
1567                 pp->bus = SYSFS_BUS_CCW;
1568         if (!strncmp(pp->dev,"sd", 2))
1569                 pp->bus = SYSFS_BUS_SCSI;
1570         if (!strncmp(pp->dev,"nvme", 4))
1571                 pp->bus = SYSFS_BUS_NVME;
1572
1573         switch (pp->bus) {
1574         case SYSFS_BUS_SCSI:
1575                 return scsi_sysfs_pathinfo(pp, hwtable);
1576         case SYSFS_BUS_CCW:
1577                 return ccw_sysfs_pathinfo(pp, hwtable);
1578         case SYSFS_BUS_CCISS:
1579                 return cciss_sysfs_pathinfo(pp, hwtable);
1580         case SYSFS_BUS_NVME:
1581                 return nvme_sysfs_pathinfo(pp, hwtable);
1582         case SYSFS_BUS_UNDEF:
1583         default:
1584                 return PATHINFO_OK;
1585         }
1586 }
1587
1588 static void
1589 scsi_ioctl_pathinfo (struct path * pp, int mask)
1590 {
1591         struct udev_device *parent;
1592         const char *attr_path = NULL;
1593
1594         if (!(mask & DI_SERIAL))
1595                 return;
1596
1597         parent = pp->udev;
1598         while (parent) {
1599                 const char *subsys = udev_device_get_subsystem(parent);
1600                 if (subsys && !strncmp(subsys, "scsi", 4)) {
1601                         attr_path = udev_device_get_sysname(parent);
1602                         if (!attr_path)
1603                                 break;
1604                         if (sscanf(attr_path, "%i:%i:%i:%i",
1605                                    &pp->sg_id.host_no,
1606                                    &pp->sg_id.channel,
1607                                    &pp->sg_id.scsi_id,
1608                                    &pp->sg_id.lun) == 4)
1609                                 break;
1610                 }
1611                 parent = udev_device_get_parent(parent);
1612         }
1613         if (!attr_path || pp->sg_id.host_no == -1)
1614                 return;
1615
1616         if (get_vpd_sysfs(parent, 0x80, pp->serial, SERIAL_SIZE) <= 0) {
1617                 if (get_serial(pp->serial, SERIAL_SIZE, pp->fd)) {
1618                         condlog(3, "%s: fail to get serial", pp->dev);
1619                         return;
1620                 }
1621         }
1622
1623         condlog(3, "%s: serial = %s", pp->dev, pp->serial);
1624         return;
1625 }
1626
1627 static void
1628 cciss_ioctl_pathinfo(struct path *pp)
1629 {
1630         get_serial(pp->serial, SERIAL_SIZE, pp->fd);
1631         condlog(3, "%s: serial = %s", pp->dev, pp->serial);
1632 }
1633
1634 int
1635 get_state (struct path * pp, struct config *conf, int daemon, int oldstate)
1636 {
1637         struct checker * c = &pp->checker;
1638         int state;
1639
1640         if (!checker_selected(c)) {
1641                 if (daemon) {
1642                         if (pathinfo(pp, conf, DI_SYSFS) != PATHINFO_OK) {
1643                                 condlog(3, "%s: couldn't get sysfs pathinfo",
1644                                         pp->dev);
1645                                 return PATH_UNCHECKED;
1646                         }
1647                 }
1648                 select_detect_checker(conf, pp);
1649                 select_checker(conf, pp);
1650                 if (!checker_selected(c)) {
1651                         condlog(3, "%s: No checker selected", pp->dev);
1652                         return PATH_UNCHECKED;
1653                 }
1654                 checker_set_fd(c, pp->fd);
1655                 if (checker_init(c, pp->mpp?&pp->mpp->mpcontext:NULL)) {
1656                         checker_clear(c);
1657                         condlog(3, "%s: checker init failed", pp->dev);
1658                         return PATH_UNCHECKED;
1659                 }
1660         }
1661         if (pp->mpp && !c->mpcontext)
1662                 checker_mp_init(c, &pp->mpp->mpcontext);
1663         checker_clear_message(c);
1664         if (daemon) {
1665                 if (conf->force_sync == 0)
1666                         checker_set_async(c);
1667                 else
1668                         checker_set_sync(c);
1669         }
1670         if (!conf->checker_timeout &&
1671             sysfs_get_timeout(pp, &(c->timeout)) <= 0)
1672                 c->timeout = DEF_TIMEOUT;
1673         state = checker_check(c, oldstate);
1674         condlog(3, "%s: %s state = %s", pp->dev,
1675                 checker_name(c), checker_state_name(state));
1676         if (state != PATH_UP && state != PATH_GHOST &&
1677             strlen(checker_message(c)))
1678                 condlog(3, "%s: %s checker%s",
1679                         pp->dev, checker_name(c), checker_message(c));
1680         return state;
1681 }
1682
1683 static int
1684 get_prio (struct path * pp)
1685 {
1686         struct prio * p;
1687         struct config *conf;
1688         int checker_timeout;
1689         int old_prio;
1690
1691         if (!pp)
1692                 return 0;
1693
1694         p = &pp->prio;
1695         if (!prio_selected(p)) {
1696                 conf = get_multipath_config();
1697                 pthread_cleanup_push(put_multipath_config, conf);
1698                 select_detect_prio(conf, pp);
1699                 select_prio(conf, pp);
1700                 pthread_cleanup_pop(1);
1701                 if (!prio_selected(p)) {
1702                         condlog(3, "%s: no prio selected", pp->dev);
1703                         pp->priority = PRIO_UNDEF;
1704                         return 1;
1705                 }
1706         }
1707         conf = get_multipath_config();
1708         checker_timeout = conf->checker_timeout;
1709         put_multipath_config(conf);
1710         old_prio = pp->priority;
1711         pp->priority = prio_getprio(p, pp, checker_timeout);
1712         if (pp->priority < 0) {
1713                 /* this changes pp->offline, but why not */
1714                 int state = path_offline(pp);
1715
1716                 if (state == PATH_DOWN || state == PATH_PENDING) {
1717                         pp->priority = old_prio;
1718                         condlog(3, "%s: %s prio error in state %d, keeping prio = %d",
1719                                 pp->dev, prio_name(p), state, pp->priority);
1720                 } else {
1721                         condlog(3, "%s: %s prio error in state %d",
1722                                 pp->dev, prio_name(p), state);
1723                         pp->priority = PRIO_UNDEF;
1724                 }
1725                 return 1;
1726         }
1727         condlog((old_prio == pp->priority ? 4 : 3), "%s: %s prio = %u",
1728                 pp->dev, prio_name(p), pp->priority);
1729         return 0;
1730 }
1731
1732 /*
1733  * Mangle string of length *len starting at start
1734  * by removing character sequence "00" (hex for a 0 byte),
1735  * starting at end, backwards.
1736  * Changes the value of *len if characters were removed.
1737  * Returns a pointer to the position where "end" was moved to.
1738  */
1739 static char
1740 *skip_zeroes_backward(char* start, size_t *len, char *end)
1741 {
1742         char *p = end;
1743
1744         while (p >= start + 2 && *(p - 1) == '0' && *(p - 2) == '0')
1745                 p -= 2;
1746
1747         if (p == end)
1748                 return p;
1749
1750         memmove(p, end, start + *len + 1 - end);
1751         *len -= end - p;
1752
1753         return p;
1754 }
1755
1756 /*
1757  * Fix for NVME wwids looking like this:
1758  * nvme.0000-3163653363666438366239656630386200-4c696e75780000000000000000000000000000000000000000000000000000000000000000000000-00000002
1759  * which are encountered in some combinations of Linux NVME host and target.
1760  * The '00' are hex-encoded 0-bytes which are forbidden in the serial (SN)
1761  * and model (MN) fields. Discard them.
1762  * If a WWID of the above type is found, sets pp->wwid and returns a value > 0.
1763  * Otherwise, returns 0.
1764  */
1765 static int
1766 fix_broken_nvme_wwid(struct path *pp, const char *value, size_t size)
1767 {
1768         static const char _nvme[] = "nvme.";
1769         size_t len, i;
1770         char mangled[256];
1771         char *p;
1772
1773         len = strlen(value);
1774         if (len >= sizeof(mangled))
1775                 return 0;
1776
1777         /* Check that value starts with "nvme.%04x-" */
1778         if (memcmp(value, _nvme, sizeof(_nvme) - 1) || value[9] != '-')
1779                 return 0;
1780         for (i = 5; i < 9; i++)
1781                 if (!isxdigit(value[i]))
1782                         return 0;
1783
1784         memcpy(mangled, value, len + 1);
1785
1786         /* search end of "model" part and strip trailing '00' */
1787         p = memrchr(mangled, '-', len);
1788         if (p == NULL)
1789                 return 0;
1790
1791         p = skip_zeroes_backward(mangled, &len, p);
1792
1793         /* search end of "serial" part */
1794         p = memrchr(mangled, '-', p - mangled);
1795         if (p == NULL || memrchr(mangled, '-', p - mangled) != mangled + 9)
1796             /* We expect exactly 3 '-' in the value */
1797                 return 0;
1798
1799         p = skip_zeroes_backward(mangled, &len, p);
1800         if (len >= size)
1801                 return 0;
1802
1803         memcpy(pp->wwid, mangled, len + 1);
1804         condlog(2, "%s: over-long WWID shortened to %s", pp->dev, pp->wwid);
1805         return len;
1806 }
1807
1808 static int
1809 get_udev_uid(struct path * pp, char *uid_attribute, struct udev_device *udev)
1810 {
1811         ssize_t len;
1812         const char *value;
1813
1814         value = udev_device_get_property_value(udev, uid_attribute);
1815         if (!value || strlen(value) == 0)
1816                 value = getenv(uid_attribute);
1817         if (value && strlen(value)) {
1818                 len = strlcpy(pp->wwid, value, WWID_SIZE);
1819                 if (len >= WWID_SIZE) {
1820                         len = fix_broken_nvme_wwid(pp, value, WWID_SIZE);
1821                         if (len > 0)
1822                                 return len;
1823                         condlog(0, "%s: wwid overflow", pp->dev);
1824                         len = WWID_SIZE;
1825                 }
1826         } else {
1827                 condlog(3, "%s: no %s attribute", pp->dev,
1828                         uid_attribute);
1829                 len = -EINVAL;
1830         }
1831         return len;
1832 }
1833
1834 static int
1835 get_vpd_uid(struct path * pp)
1836 {
1837         struct udev_device *parent = pp->udev;
1838
1839         while (parent) {
1840                 const char *subsys = udev_device_get_subsystem(parent);
1841                 if (subsys && !strncmp(subsys, "scsi", 4))
1842                         break;
1843                 parent = udev_device_get_parent(parent);
1844         }
1845
1846         if (!parent)
1847                 return -EINVAL;
1848
1849         return get_vpd_sysfs(parent, 0x83, pp->wwid, WWID_SIZE);
1850 }
1851
1852 static ssize_t uid_fallback(struct path *pp, int path_state,
1853                             const char **origin)
1854 {
1855         ssize_t len = -1;
1856
1857         if (pp->bus == SYSFS_BUS_SCSI) {
1858                 len = get_vpd_uid(pp);
1859                 *origin = "sysfs";
1860                 if (len < 0 && path_state == PATH_UP) {
1861                         condlog(1, "%s: failed to get sysfs uid: %s",
1862                                 pp->dev, strerror(-len));
1863                         len = get_vpd_sgio(pp->fd, 0x83, 0, pp->wwid,
1864                                            WWID_SIZE);
1865                         *origin = "sgio";
1866                 }
1867         } else if (pp->bus == SYSFS_BUS_NVME) {
1868                 char value[256];
1869                 len = sysfs_attr_get_value(pp->udev, "wwid", value,
1870                                            sizeof(value));
1871                 if (len <= 0)
1872                         return -1;
1873                 len = strlcpy(pp->wwid, value, WWID_SIZE);
1874                 if (len >= WWID_SIZE) {
1875                         len = fix_broken_nvme_wwid(pp, value,
1876                                                    WWID_SIZE);
1877                         if (len > 0)
1878                                 return len;
1879                         condlog(0, "%s: wwid overflow", pp->dev);
1880                         len = WWID_SIZE;
1881                 }
1882                 *origin = "sysfs";
1883         }
1884         return len;
1885 }
1886
1887 static bool has_uid_fallback(struct path *pp)
1888 {
1889         /*
1890          * Falling back to direct WWID determination is dangerous
1891          * if uid_attribute is set to something non-standard.
1892          * Allow it only if it's either the default, or if udev
1893          * has been disabled by setting 'uid_attribute ""'.
1894          */
1895         if (!pp->uid_attribute)
1896                 return false;
1897         return ((pp->bus == SYSFS_BUS_SCSI &&
1898                  (!strcmp(pp->uid_attribute, DEFAULT_UID_ATTRIBUTE) ||
1899                   !strcmp(pp->uid_attribute, ""))) ||
1900                 (pp->bus == SYSFS_BUS_NVME &&
1901                  (!strcmp(pp->uid_attribute, DEFAULT_NVME_UID_ATTRIBUTE) ||
1902                   !strcmp(pp->uid_attribute, ""))));
1903 }
1904
1905 int
1906 get_uid (struct path * pp, int path_state, struct udev_device *udev,
1907          int allow_fallback)
1908 {
1909         char *c;
1910         const char *origin = "unknown";
1911         ssize_t len = 0;
1912         struct config *conf;
1913         int used_fallback = 0;
1914
1915         if (!pp->uid_attribute && !pp->getuid) {
1916                 conf = get_multipath_config();
1917                 pthread_cleanup_push(put_multipath_config, conf);
1918                 select_getuid(conf, pp);
1919                 pthread_cleanup_pop(1);
1920         }
1921
1922         memset(pp->wwid, 0, WWID_SIZE);
1923         if (pp->getuid) {
1924                 char buff[CALLOUT_MAX_SIZE];
1925
1926                 /* Use 'getuid' callout, deprecated */
1927                 condlog(1, "%s: using deprecated getuid callout", pp->dev);
1928                 if (path_state != PATH_UP) {
1929                         condlog(3, "%s: path inaccessible", pp->dev);
1930                         len = -EWOULDBLOCK;
1931                 } else if (apply_format(pp->getuid, &buff[0], pp)) {
1932                         condlog(0, "error formatting uid callout command");
1933                         len = -EINVAL;
1934                 } else if (execute_program(buff, pp->wwid, WWID_SIZE)) {
1935                         condlog(3, "error calling out %s", buff);
1936                         len = -EIO;
1937                 } else
1938                         len = strlen(pp->wwid);
1939                 origin = "callout";
1940         } else {
1941                 bool udev_available = udev && pp->uid_attribute
1942                         && *pp->uid_attribute;
1943
1944                 if (udev_available) {
1945                         len = get_udev_uid(pp, pp->uid_attribute, udev);
1946                         if (len <= 0)
1947                                 condlog(1,
1948                                         "%s: failed to get udev uid: %s",
1949                                         pp->dev, strerror(-len));
1950                         else
1951                                 origin = "udev";
1952                 }
1953                 if ((!udev_available || (len <= 0 && allow_fallback))
1954                     && has_uid_fallback(pp)) {
1955                         used_fallback = 1;
1956                         len = uid_fallback(pp, path_state, &origin);
1957                 }
1958         }
1959         if ( len < 0 ) {
1960                 condlog(1, "%s: failed to get %s uid: %s",
1961                         pp->dev, origin, strerror(-len));
1962                 memset(pp->wwid, 0x0, WWID_SIZE);
1963                 return 1;
1964         } else {
1965                 /* Strip any trailing blanks */
1966                 c = strchr(pp->wwid, '\0');
1967                 c--;
1968                 while (c && c >= pp->wwid && *c == ' ') {
1969                         *c = '\0';
1970                         c--;
1971                 }
1972         }
1973         condlog((used_fallback)? 1 : 3, "%s: uid = %s (%s)", pp->dev,
1974                 *pp->wwid == '\0' ? "<empty>" : pp->wwid, origin);
1975         return 0;
1976 }
1977
1978 int pathinfo(struct path *pp, struct config *conf, int mask)
1979 {
1980         int path_state;
1981
1982         if (!pp || !conf)
1983                 return PATHINFO_FAILED;
1984
1985         /*
1986          * For behavior backward-compatibility with multipathd,
1987          * the blacklisting by filter_property|devnode() is not
1988          * limited by DI_BLACKLIST and occurs before this debug
1989          * message with the mask value.
1990          */
1991         if (pp->udev) {
1992                 const char *hidden =
1993                         udev_device_get_sysattr_value(pp->udev, "hidden");
1994
1995                 if (hidden && !strcmp(hidden, "1")) {
1996                         condlog(4, "%s: hidden", pp->dev);
1997                         return PATHINFO_SKIPPED;
1998                 }
1999                 if (is_claimed_by_foreign(pp->udev) ||
2000                     filter_property(conf, pp->udev, 4, pp->uid_attribute) > 0)
2001                         return PATHINFO_SKIPPED;
2002         }
2003
2004         if (filter_devnode(conf->blist_devnode,
2005                            conf->elist_devnode,
2006                            pp->dev) > 0)
2007                 return PATHINFO_SKIPPED;
2008
2009         condlog(4, "%s: mask = 0x%x", pp->dev, mask);
2010
2011         /*
2012          * Sanity check: we need the device number to
2013          * avoid inconsistent information in
2014          * find_path_by_dev()/find_path_by_devt()
2015          */
2016         if (!strlen(pp->dev_t) && !(mask & DI_SYSFS)) {
2017                 condlog(1, "%s: empty device number", pp->dev);
2018                 mask |= DI_SYSFS;
2019         }
2020
2021         /*
2022          * fetch info available in sysfs
2023          */
2024         if (mask & DI_SYSFS) {
2025                 int rc = sysfs_pathinfo(pp, conf->hwtable);
2026
2027                 if (rc != PATHINFO_OK)
2028                         return rc;
2029         }
2030
2031         if (mask & DI_BLACKLIST && mask & DI_SYSFS) {
2032                 if (filter_device(conf->blist_device, conf->elist_device,
2033                                   pp->vendor_id, pp->product_id, pp->dev) > 0 ||
2034                     filter_protocol(conf->blist_protocol, conf->elist_protocol,
2035                                     pp) > 0)
2036                         return PATHINFO_SKIPPED;
2037         }
2038
2039         path_state = path_offline(pp);
2040         if (path_state == PATH_REMOVED)
2041                 goto blank;
2042         else if (mask & DI_NOIO) {
2043                 if (mask & DI_CHECKER)
2044                         /*
2045                          * Avoid any IO on the device itself.
2046                          * simply use the path_offline() return as its state
2047                          */
2048                         pp->chkrstate = pp->state = path_state;
2049                 return PATHINFO_OK;
2050         }
2051
2052         /*
2053          * fetch info not available through sysfs
2054          */
2055         if (pp->fd < 0)
2056                 pp->fd = open(udev_device_get_devnode(pp->udev), O_RDONLY);
2057
2058         if (pp->fd < 0) {
2059                 condlog(4, "Couldn't open node for %s: %s",
2060                         pp->dev, strerror(errno));
2061                 goto blank;
2062         }
2063
2064         if (mask & DI_SERIAL)
2065                 get_geometry(pp);
2066
2067         if (path_state == PATH_UP && pp->bus == SYSFS_BUS_SCSI)
2068                 scsi_ioctl_pathinfo(pp, mask);
2069
2070         if (pp->bus == SYSFS_BUS_CCISS && mask & DI_SERIAL)
2071                 cciss_ioctl_pathinfo(pp);
2072
2073         if (mask & DI_CHECKER) {
2074                 if (path_state == PATH_UP) {
2075                         int newstate = get_state(pp, conf, 0, path_state);
2076                         if (newstate != PATH_PENDING ||
2077                             pp->state == PATH_UNCHECKED ||
2078                             pp->state == PATH_WILD)
2079                                 pp->chkrstate = pp->state = newstate;
2080                         if (pp->state == PATH_TIMEOUT)
2081                                 pp->state = PATH_DOWN;
2082                         if (pp->state == PATH_UP && !pp->size) {
2083                                 condlog(3, "%s: device size is 0, "
2084                                         "path unusable", pp->dev);
2085                                 pp->state = PATH_GHOST;
2086                         }
2087                 } else {
2088                         condlog(3, "%s: path inaccessible", pp->dev);
2089                         pp->chkrstate = pp->state = path_state;
2090                 }
2091         }
2092
2093         if ((mask & DI_WWID) && !strlen(pp->wwid)) {
2094                 get_uid(pp, path_state, pp->udev,
2095                         (pp->retriggers >= conf->retrigger_tries));
2096                 if (!strlen(pp->wwid)) {
2097                         if (pp->bus == SYSFS_BUS_UNDEF)
2098                                 return PATHINFO_SKIPPED;
2099                         if (pp->initialized != INIT_FAILED) {
2100                                 pp->initialized = INIT_MISSING_UDEV;
2101                                 pp->tick = conf->retrigger_delay;
2102                         }
2103                         return PATHINFO_OK;
2104                 }
2105                 else
2106                         pp->tick = 1;
2107         }
2108
2109         if (mask & DI_BLACKLIST && mask & DI_WWID) {
2110                 if (filter_wwid(conf->blist_wwid, conf->elist_wwid,
2111                                 pp->wwid, pp->dev) > 0) {
2112                         return PATHINFO_SKIPPED;
2113                 }
2114         }
2115
2116          /*
2117           * Retrieve path priority, even for PATH_DOWN paths if it has never
2118           * been successfully obtained before.
2119           */
2120         if ((mask & DI_PRIO) && path_state == PATH_UP && strlen(pp->wwid)) {
2121                 if (pp->state != PATH_DOWN || pp->priority == PRIO_UNDEF) {
2122                         get_prio(pp);
2123                 }
2124         }
2125
2126         if ((mask & DI_ALL) == DI_ALL)
2127                 pp->initialized = INIT_OK;
2128         return PATHINFO_OK;
2129
2130 blank:
2131         /*
2132          * Recoverable error, for example faulty or offline path
2133          */
2134         pp->chkrstate = pp->state = PATH_DOWN;
2135         if (pp->initialized == INIT_NEW || pp->initialized == INIT_FAILED)
2136                 memset(pp->wwid, 0, WWID_SIZE);
2137
2138         return PATHINFO_OK;
2139 }