[libmultipath] blacklist logging overhaul
authorChristophe Varoqui <cvaroqui@zezette.localdomain>
Thu, 15 Feb 2007 23:59:52 +0000 (00:59 +0100)
committerChristophe Varoqui <cvaroqui@zezette.localdomain>
Thu, 15 Feb 2007 23:59:52 +0000 (00:59 +0100)
Make blacklist functions log as much info as possible.

o exported functions are now called filter_*
o each filter_* challenges exceptions list first, then blacklist if
necessary
o each filter_* is verbose
o each filter_* wraps a silent _filter_*
o filter_path chains _filter_*
o filter_* returns negative if exception list match
o filter_* returns positive if blacklist match
o update all blacklist_*() callers
o fix "show devices" CLI command to show whitelisted devs

libmultipath/blacklist.c
libmultipath/blacklist.h
libmultipath/configure.c
libmultipath/discovery.c
libmultipath/print.c
multipath/main.c
multipathd/cli_handlers.c
multipathd/main.c

index 44987f6..5f7b2f5 100644 (file)
@@ -141,89 +141,183 @@ setup_default_blist (struct config * conf)
 }
 
 int
-blacklist_exceptions (vector elist, char * str)
+_blacklist_exceptions (vector elist, char * str)
 {
         int i;
         struct blentry * ele;
 
         vector_foreach_slot (elist, ele, i) {
-                if (!regexec(&ele->regex, str, 0, NULL, 0)) {
-                       condlog(3, "%s: exception-listed", str);
+                if (!regexec(&ele->regex, str, 0, NULL, 0))
                        return 1;
-               }
        }
         return 0;
 }
 
 int
-blacklist (vector blist, vector elist, char * str)
+_blacklist (vector blist, char * str)
 {
        int i;
        struct blentry * ble;
 
-       if (blacklist_exceptions(elist, str))
-               return 0;
-
        vector_foreach_slot (blist, ble, i) {
-               if (!regexec(&ble->regex, str, 0, NULL, 0)) {
-                       condlog(3, "%s: blacklisted", str);
+               if (!regexec(&ble->regex, str, 0, NULL, 0))
                        return 1;
-               }
        }
        return 0;
 }
 
 int
-blacklist_exceptions_device(vector elist, char * vendor, char * product)
+_blacklist_exceptions_device(vector elist, char * vendor, char * product)
 {
        int i;
        struct blentry_device * ble;
 
        vector_foreach_slot (elist, ble, i) {
                if (!regexec(&ble->vendor_reg, vendor, 0, NULL, 0) &&
-                   !regexec(&ble->product_reg, product, 0, NULL, 0)) {
-                       condlog(3, "%s:%s: exception-listed", vendor, product);
+                   !regexec(&ble->product_reg, product, 0, NULL, 0))
                        return 1;
-               }
        }
        return 0;
 }
 
 int
-blacklist_device (vector blist, vector elist, char * vendor, char * product)
+_blacklist_device (vector blist, char * vendor, char * product)
 {
        int i;
        struct blentry_device * ble;
 
-       if (blacklist_exceptions_device(elist, vendor, product))
-               return 0;
-
        vector_foreach_slot (blist, ble, i) {
                if (!regexec(&ble->vendor_reg, vendor, 0, NULL, 0) &&
-                   !regexec(&ble->product_reg, product, 0, NULL, 0)) {
-                       condlog(3, "%s:%s: blacklisted", vendor, product);
+                   !regexec(&ble->product_reg, product, 0, NULL, 0))
                        return 1;
-               }
        }
        return 0;
 }
 
+#define LOG_BLIST(M) \
+       if (vendor && product)                                           \
+               condlog(3, "%s: (%s:%s) %s", dev, vendor, product, (M)); \
+       else if (wwid)                                                   \
+               condlog(3, "%s: (%s) %s", dev, wwid, (M));               \
+       else                                                             \
+               condlog(3, "%s: %s", dev, (M))
+
+void
+log_filter (char *dev, char *vendor, char *product, char *wwid, int r)
+{
+       /*
+        * Try to sort from most likely to least.
+        */
+       switch (r) {
+       case MATCH_NOTHING:
+               break;
+       case MATCH_DEVICE_BLIST:
+               LOG_BLIST("vendor/product blacklisted");
+               break;
+       case MATCH_WWID_BLIST:
+               LOG_BLIST("wwid blacklisted");
+               break;
+       case MATCH_DEVNODE_BLIST:
+               LOG_BLIST("device node name blacklisted");
+               break;
+       case MATCH_DEVICE_BLIST_EXCEPT:
+               LOG_BLIST("vendor/product whitelisted");
+               break;
+       case MATCH_WWID_BLIST_EXCEPT:
+               LOG_BLIST("wwid whitelisted");
+               break;
+       case MATCH_DEVNODE_BLIST_EXCEPT:
+               LOG_BLIST("device node name whitelisted");
+               break;
+       }
+}
+
 int
-blacklist_path (struct config * conf, struct path * pp)
+_filter_device (vector blist, vector elist, char * vendor, char * product)
 {
-       if (blacklist(conf->blist_devnode, conf->elist_devnode, pp->dev))
-               return 1;
+       if (!vendor || !product)
+               return 0;
+       if (_blacklist_exceptions_device(elist, vendor, product))
+               return MATCH_DEVICE_BLIST_EXCEPT;
+       if (_blacklist_device(blist, vendor, product))
+               return MATCH_DEVICE_BLIST;
+       return 0;
+}
 
-       if (blacklist(conf->blist_wwid, conf->elist_wwid, pp->wwid))
-               return 1;
+int
+filter_device (vector blist, vector elist, char * vendor, char * product)
+{
+       int r = _filter_device(blist, elist, vendor, product);
+       log_filter(NULL, vendor, product, NULL, r);
+       return r;
+}
 
-       if (pp->vendor_id && pp->product_id &&
-           blacklist_device(conf->blist_device, conf->elist_device, pp->vendor_id, pp->product_id))
-               return 1;
+int
+_filter_devnode (vector blist, vector elist, char * dev)
+{
+       if (!dev)
+               return 0;
+       if (_blacklist_exceptions(elist, dev))
+               return MATCH_DEVNODE_BLIST_EXCEPT;
+       if (_blacklist(blist, dev))
+               return MATCH_DEVNODE_BLIST;
+       return 0;
+}
+
+int
+filter_devnode (vector blist, vector elist, char * dev)
+{
+       int r = _filter_devnode(blist, elist, dev);
+       log_filter(dev, NULL, NULL, NULL, r);
+       return r;
+}
+
+int
+_filter_wwid (vector blist, vector elist, char * wwid)
+{
+       if (!wwid)
+               return 0;
+       if (_blacklist_exceptions(elist, wwid))
+               return MATCH_WWID_BLIST_EXCEPT;
+       if (_blacklist(blist, wwid))
+               return MATCH_WWID_BLIST;
+       return 0;
+}
+
+int
+filter_wwid (vector blist, vector elist, char * wwid)
+{
+       int r = _filter_wwid(blist, elist, wwid);
+       log_filter(NULL, NULL, NULL, wwid, r);
+       return r;
+}
 
+int
+_filter_path (struct config * conf, struct path * pp)
+{
+       int r;
+
+       r = _filter_devnode(conf->blist_devnode, conf->elist_devnode,pp->dev);
+       if (r)
+               return r;
+       r = _filter_wwid(conf->blist_devnode, conf->elist_devnode, pp->wwid);
+       if (r)
+               return r;
+       r = _filter_device(conf->blist_device, conf->elist_device,
+                          pp->vendor_id, pp->product_id);
+       if (r)
+               return r;
        return 0;
 }
 
+int
+filter_path (struct config * conf, struct path * pp)
+{
+       int r=_filter_path(conf, pp);
+       log_filter(pp->dev, pp->vendor_id, pp->product_id, pp->wwid, r);
+       return r;
+}
+
 void
 free_blacklist (vector blist)
 {
index 99c6fd1..cdbebef 100644 (file)
@@ -3,6 +3,14 @@
 
 #include "regex.h"
 
+#define MATCH_NOTHING       0
+#define MATCH_WWID_BLIST    1
+#define MATCH_DEVICE_BLIST  2
+#define MATCH_DEVNODE_BLIST 3
+#define MATCH_WWID_BLIST_EXCEPT    -MATCH_WWID_BLIST
+#define MATCH_DEVICE_BLIST_EXCEPT  -MATCH_DEVICE_BLIST
+#define MATCH_DEVNODE_BLIST_EXCEPT -MATCH_DEVNODE_BLIST
+
 struct blentry {
        char * str;
        regex_t regex;
@@ -19,9 +27,10 @@ struct blentry_device {
 
 int setup_default_blist (struct config *);
 int alloc_ble_device (vector);
-int blacklist (vector, vector, char *);
-int blacklist_device (vector, vector, char *, char *);
-int blacklist_path (struct config *, struct path *);
+int filter_devnode (vector, vector, char *);
+int filter_wwid (vector, vector, char *);
+int filter_device (vector, vector, char *, char *);
+int filter_path (struct config *, struct path *);
 int store_ble (vector, char *, int);
 int set_ble_device (vector, char *, char *, int);
 void free_blacklist (vector);
index 9d17022..fba04a4 100644 (file)
@@ -420,7 +420,7 @@ coalesce_paths (struct vectors * vecs, vector newmp, char * refwwid)
 
                /* 1. if path has no unique id or wwid blacklisted */
                if (memcmp(empty_buff, pp1->wwid, WWID_SIZE) == 0 ||
-                   blacklist_path(conf, pp1))
+                   filter_path(conf, pp1) > 0)
                        continue;
 
                /* 2. if path already coalesced */
index cf56f9c..f270f71 100644 (file)
@@ -61,7 +61,8 @@ path_discover (vector pathvec, struct config * conf, char * devname, int flag)
        if (!devname)
                return 0;
 
-       if (blacklist(conf->blist_devnode, conf->elist_devnode, devname))
+       if (filter_devnode(conf->blist_devnode, conf->elist_devnode,
+                          devname) > 0)
                return 0;
 
        if(safe_sprintf(path, "%s/block/%s/device", sysfs_path,
index 4a23ccb..e50f37d 100644 (file)
@@ -1101,12 +1101,10 @@ snprint_devices (char * buff, int len, struct vectors *vecs)
         struct sysfs_class_device * dev;
        int threshold = MAX_LINE_LEN;
        int fwd = 0;
-
+       int r;
 
        struct path * pp;
 
-
-
         if (!(class = sysfs_open_class("block")))
                 return 0;
 
@@ -1122,14 +1120,19 @@ snprint_devices (char * buff, int len, struct vectors *vecs)
         dlist_for_each_data(ls, dev, struct sysfs_class_device) {
                if ((len - fwd - threshold)  <= 0)
                        return len;
-               fwd += snprintf(buff + fwd, len - fwd, "    %s ", dev->name);
+               fwd += snprintf(buff + fwd, len - fwd, "    %s", dev->name);
                pp = find_path_by_dev(vecs->pathvec, dev->name);
-               if (blacklist(conf->blist_devnode, conf->elist_devnode,
-                             dev->name) || pp == NULL)
-                       fwd += snprintf(buff + fwd, len - fwd,
-                                       "(blacklisted)\n");
-                else
-                       fwd += snprintf(buff + fwd, len - fwd, "\n");
+               if (!pp) {
+                       r = filter_devnode(conf->blist_devnode,
+                                          conf->elist_devnode, dev->name);
+                       if (r > 0)
+                               fwd += snprintf(buff + fwd, len - fwd,
+                                               " (blacklisted)");
+                       else if (r < 0)
+                               fwd += snprintf(buff + fwd, len - fwd,
+                                               " (whitelisted)");
+               }
+               fwd += snprintf(buff + fwd, len - fwd, "\n");
         }
         sysfs_close_class(class);
 
index faccdbb..67076db 100644 (file)
@@ -224,7 +224,7 @@ configure (void)
        vecs.mpvec = curmp;
 
        /*
-        * if we have a blacklisted device parameter, exit early
+        * dev is "/dev/" . "sysfs block dev"
         */
        if (conf->dev) {
                if (!strncmp(conf->dev, "/dev/", 5) &&
@@ -234,8 +234,12 @@ configure (void)
                        dev = conf->dev;
        }
        
-       if (dev && blacklist(conf->blist_devnode, conf->elist_devnode, dev))
-               goto out;
+       /*
+        * if we have a blacklisted device parameter, exit early
+        */
+       if (dev && 
+           (filter_devnode(conf->blist_devnode, conf->elist_devnode, dev) > 0))
+                       goto out;
        
        /*
         * scope limiting must be translated into a wwid
@@ -249,8 +253,8 @@ configure (void)
                        goto out;
                }
                condlog(3, "scope limited to %s", refwwid);
-
-               if (blacklist(conf->blist_wwid, conf->elist_wwid, refwwid))
+               if (filter_wwid(conf->blist_wwid, conf->elist_wwid,
+                               refwwid) > 0)
                        goto out;
        }
 
index 9cd5902..4938e84 100644 (file)
@@ -286,8 +286,8 @@ cli_add_path (void * v, char ** reply, int * len, void * data)
 
        condlog(2, "%s: add path (operator)", param);
 
-       if (blacklist(conf->blist_devnode, conf->elist_devnode, param) ||
-           (r = ev_add_path(param, vecs)) == 2) {
+       if (filter_devnode(conf->blist_devnode, conf->elist_devnode,
+           param) > 0 || (r = ev_add_path(param, vecs)) == 2) {
                *reply = strdup("blacklisted");
                *len = strlen(*reply) + 1;
                condlog(2, "%s: path blacklisted", param);
@@ -315,7 +315,7 @@ cli_add_map (void * v, char ** reply, int * len, void * data)
 
        condlog(2, "%s: add map (operator)", param);
 
-       if (blacklist(conf->blist_wwid, conf->elist_wwid, param)) {
+       if (filter_wwid(conf->blist_wwid, conf->elist_wwid, param) > 0) {
                *reply = strdup("blacklisted");
                *len = strlen(*reply) + 1;
                condlog(2, "%s: map blacklisted", param);
index 4bb9f0c..dbd12bb 100644 (file)
@@ -376,7 +376,7 @@ ev_add_path (char * devname, struct vectors * vecs)
                condlog(0, "%s: failed to get path uid", devname);
                return 1; /* leave path added to pathvec */
        }
-       if (blacklist_path(conf, pp)){
+       if (filter_path(conf, pp)){
                int i = find_slot(vecs->pathvec, (void *)pp);
                if (i != -1)
                        vector_del_slot(vecs->pathvec, i);
@@ -667,7 +667,8 @@ uev_trigger (struct uevent * uev, void * trigger_data)
        /*
         * path add/remove event
         */
-       if (blacklist(conf->blist_devnode, conf->elist_devnode, devname))
+       if (filter_devnode(conf->blist_devnode, conf->elist_devnode,
+                          devname) > 0)
                goto out;
 
        if (!strncmp(uev->action, "add", 3)) {
@@ -1041,7 +1042,7 @@ configure (struct vectors * vecs, int start_waiters)
        path_discovery(vecs->pathvec, conf, DI_ALL);
 
        vector_foreach_slot (vecs->pathvec, pp, i){
-               if (blacklist_path(conf, pp)){
+               if (filter_path(conf, pp)){
                        vector_del_slot(vecs->pathvec, i);
                        free_path(pp);
                        i--;
@@ -1069,10 +1070,6 @@ configure (struct vectors * vecs, int start_waiters)
 
        sync_maps_state(mpvec);
 
-       if (conf->verbosity > 2)
-               vector_foreach_slot(mpvec, mpp, i)
-                       print_map(mpp);
-
        /*
         * purge dm of old maps
         */