Linux Device Mapper development
 help / color / mirror / Atom feed
From: Hannes Reinecke <hare@suse.de>
To: Christophe Varoqui <christophe.varoqui@gmail.com>
Cc: dm-devel@redhat.com
Subject: [PATCH 69/78] Separate out vpd parsing functions
Date: Mon, 16 Mar 2015 13:36:56 +0100	[thread overview]
Message-ID: <1426509425-15978-70-git-send-email-hare@suse.de> (raw)
In-Reply-To: <1426509425-15978-1-git-send-email-hare@suse.de>

Signed-off-by: Hannes Reinecke <hare@suse.de>
---
 libmultipath/discovery.c | 367 +++++++++++++++++++++++++----------------------
 1 file changed, 193 insertions(+), 174 deletions(-)

diff --git a/libmultipath/discovery.c b/libmultipath/discovery.c
index 8e6b228..50444db 100644
--- a/libmultipath/discovery.c
+++ b/libmultipath/discovery.c
@@ -811,9 +811,196 @@ get_geometry(struct path *pp)
 }
 
 static int
+parse_vpd_pg80(const unsigned char *in, char *out, size_t out_len)
+{
+	char *p = NULL;
+	int len = in[3] + (in[2] << 8);
+
+	if (len >= out_len) {
+		condlog(2, "vpd pg80 overflow, %d/%d bytes required",
+			len, (int)out_len);
+		len = out_len;
+	}
+	if (len > 0) {
+		memcpy(out, in + 4, len);
+		out[len] = '\0';
+	}
+	/*
+	 * Strip trailing whitspaces
+	 */
+	p = out + len - 1;
+	while (p > out && *p == ' ') {
+		*p = '\0';
+		p--;
+		len --;
+	}
+	return len;
+}
+
+static int
+parse_vpd_pg83(const unsigned char *in, size_t in_len,
+	       char *out, size_t out_len)
+{
+	unsigned char *d;
+	unsigned char *vpd = NULL;
+	int len = -ENODATA, vpd_type, vpd_len, prio = -1, i, naa_prio;
+
+	d = (unsigned char *)in + 4;
+	while (d < (unsigned char *)in + in_len) {
+		/* Select 'association: LUN' */
+		if ((d[1] & 0x30) != 0) {
+			d += d[3] + 4;
+			continue;
+		}
+		switch (d[1] & 0xf) {
+		case 0x3:
+			/* NAA: Prio 5 */
+			switch (d[4] >> 4) {
+			case 6:
+				/* IEEE Registered Extended: Prio 8 */
+				naa_prio = 8;
+				break;
+			case 5:
+				/* IEEE Registered: Prio 7 */
+				naa_prio = 7;
+				break;
+			case 2:
+				/* IEEE Extended: Prio 6 */
+				naa_prio = 6;
+				break;
+			case 3:
+				/* IEEE Locally assigned: Prio 1 */
+				naa_prio = 1;
+				break;
+			default:
+				/* Default: no priority */
+				naa_prio = -1;
+				break;
+			}
+			if (prio < naa_prio) {
+				prio = naa_prio;
+				vpd = d;
+			}
+			break;
+		case 0x8:
+			/* SCSI Name: Prio 4 */
+			if (memcmp(d + 4, "eui.", 4) &&
+			    memcmp(d + 4, "naa.", 4) &&
+			    memcmp(d + 4, "iqn.", 4))
+				continue;
+			if (prio < 4) {
+				prio = 4;
+				vpd = d;
+			}
+			break;
+		case 0x2:
+			/* EUI-64: Prio 3 */
+			if (prio < 3) {
+				prio = 3;
+				vpd = d;
+			}
+			break;
+		case 0x1:
+			/* T-10 Vendor ID: Prio 2 */
+			if (prio < 2) {
+				prio = 2;
+				vpd = d;
+			}
+			break;
+		}
+		d += d[3] + 4;
+	}
+	if (prio > 0) {
+		vpd_type = vpd[1] & 0xf;
+		vpd_len = vpd[3];
+		vpd += 4;
+		if (vpd_type == 0x2 || vpd_type == 0x3) {
+			int i;
+
+			len = sprintf(out, "%d", vpd_type);
+			for (i = 0; i < vpd_len; i++) {
+				len += sprintf(out + len,
+					       "%02x", vpd[i]);
+				if (len >= out_len)
+					break;
+			}
+		} else if (vpd_type == 0x8) {
+			if (!memcmp("eui.", vpd, 4)) {
+				out[0] =  '2';
+				len = 1;
+				vpd += 4;
+				vpd_len -= 4;
+				for (i = 0; i < vpd_len; i++) {
+					len += sprintf(out + len, "%c",
+						       tolower(vpd[i]));
+					if (len >= out_len)
+						break;
+				}
+				len = vpd_len + 1;
+				out[len] = '\0';
+			} else if (!memcmp("naa.", vpd, 4)) {
+				out[0] = '3';
+				len = 1;
+				vpd += 4;
+				vpd_len -= 4;
+				for (i = 0; i < vpd_len; i++) {
+					len += sprintf(out + len, "%c",
+						       tolower(vpd[i]));
+					if (len >= out_len)
+						break;
+				}
+				len = vpd_len + 1;
+				out[len] = '\0';
+			} else {
+				out[0] = '8';
+				len = 1;
+				vpd += 4;
+				vpd_len -= 4;
+				if (vpd_len > out_len + 2)
+					vpd_len = out_len - 2;
+				memcpy(out, vpd, vpd_len);
+				len = vpd_len + 1;
+				out[len] = '\0';
+			}
+		} else if (vpd_type == 0x1) {
+			unsigned char *p;
+			int p_len;
+
+			out[0] = '1';
+			len = 1;
+			p = vpd;
+			while ((p = memchr(vpd, ' ', vpd_len))) {
+				p_len = p - vpd;
+				if (len + p_len > out_len - 1)
+					p_len = out_len - len - 2;
+				memcpy(out + len, vpd, p_len);
+				len += p_len;
+				if (len >= out_len - 1) {
+					out[len] = '\0';
+					break;
+				}
+				out[len] = '_';
+				len ++;
+				vpd = p;
+				vpd_len -= p_len;
+				while (vpd && *vpd == ' ') {
+					vpd++;
+					vpd_len --;
+				}
+			}
+			if (len > 1 && out[len - 1] == '_') {
+				out[len - 1] = '\0';
+				len--;
+			}
+		}
+	}
+	return len;
+}
+
+static int
 get_vpd (struct udev_device *parent, int fd, int pg, char * str, int maxlen)
 {
-	int len = -ENODATA, buff_len;
+	int len, buff_len;
 	unsigned char buff[4096];
 
 	memset(buff, 0x0, 4096);
@@ -835,179 +1022,11 @@ get_vpd (struct udev_device *parent, int fd, int pg, char * str, int maxlen)
 	if (buff_len > 4096)
 		condlog(3, "vpd pg%02x page truncated", pg);
 
-	if (pg == 0x80) {
-		char *p = NULL;
-		len = buff[3] + (buff[2] << 8);
-		if (len >= maxlen) {
-			condlog(3, "vpd pg%02x overflow, %d/%d bytes required",
-				pg, len, maxlen);
-			return -EINVAL;
-		}
-		if (len > 0) {
-			memcpy(str, buff + 4, len);
-			str[len] = '\0';
-		}
-		p = str + len - 1;
-		while (p > str && *p == ' ') {
-			*p = '\0';
-			p--;
-			len --;
-		}
-	} else if (pg == 0x83) {
-		unsigned char *d;
-		unsigned char *vpd = NULL;
-		int vpd_type, vpd_len, prio = -1, i, naa_prio;
-
-		d = (unsigned char *)buff + 4;
-		while (d < (unsigned char *)buff + buff_len) {
-			/* Select 'association: LUN' */
-			if ((d[1] & 0x30) != 0) {
-				d += d[3] + 4;
-				continue;
-			}
-			switch (d[1] & 0xf) {
-			case 0x3:
-				/* NAA: Prio 5 */
-				switch (d[4] >> 4) {
-				case 6:
-					/* IEEE Registered Extended: Prio 8 */
-					naa_prio = 8;
-					break;
-				case 5:
-					/* IEEE Registered: Prio 7 */
-					naa_prio = 7;
-					break;
-				case 2:
-					/* IEEE Extended: Prio 6 */
-					naa_prio = 6;
-					break;
-				case 3:
-					/* IEEE Locally assigned: Prio 1 */
-					naa_prio = 1;
-					break;
-				default:
-					/* Default: no priority */
-					naa_prio = -1;
-					break;
-				}
-				if (prio < naa_prio) {
-					prio = naa_prio;
-					vpd = d;
-				}
-				break;
-			case 0x8:
-				/* SCSI Name: Prio 4 */
-				if (memcmp(d + 4, "eui.", 4) &&
-				    memcmp(d + 4, "naa.", 4) &&
-				    memcmp(d + 4, "iqn.", 4))
-					continue;
-				if (prio < 4) {
-					prio = 4;
-					vpd = d;
-				}
-				break;
-			case 0x2:
-				/* EUI-64: Prio 3 */
-				if (prio < 3) {
-					prio = 3;
-					vpd = d;
-				}
-				break;
-			case 0x1:
-				/* T-10 Vendor ID: Prio 2 */
-				if (prio < 2) {
-					prio = 2;
-					vpd = d;
-				}
-				break;
-			}
-			d += d[3] + 4;
-		}
-		if (prio > 0) {
-			vpd_type = vpd[1] & 0xf;
-			vpd_len = vpd[3];
-			vpd += 4;
-			if (vpd_type == 0x2 || vpd_type == 0x3) {
-				int i;
-
-				len = sprintf(str, "%d", vpd_type);
-				for (i = 0; i < vpd_len; i++) {
-					len += sprintf(str + len,
-						       "%02x", vpd[i]);
-					if (len >= maxlen)
-						break;
-				}
-			} else if (vpd_type == 0x8) {
-				if (!memcmp("eui.", vpd, 4)) {
-					str[0] =  '2';
-					len = 1;
-					vpd += 4;
-					vpd_len -= 4;
-					for (i = 0; i < vpd_len; i++) {
-						len += sprintf(str + len, "%c",
-							       tolower(vpd[i]));
-						if (len >= maxlen)
-							break;
-					}
-					len = vpd_len + 1;
-					str[len] = '\0';
-				} else if (!memcmp("naa.", vpd, 4)) {
-					str[0] = '3';
-					len = 1;
-					vpd += 4;
-					vpd_len -= 4;
-					for (i = 0; i < vpd_len; i++) {
-						len += sprintf(str + len, "%c",
-							       tolower(vpd[i]));
-						if (len >= maxlen)
-							break;
-					}
-					len = vpd_len + 1;
-					str[len] = '\0';
-				} else {
-					str[0] = '8';
-					len = 1;
-					vpd += 4;
-					vpd_len -= 4;
-					if (vpd_len > maxlen + 2)
-						vpd_len = maxlen - 2;
-					memcpy(str, vpd, vpd_len);
-					len = vpd_len + 1;
-					str[len] = '\0';
-				}
-			} else if (vpd_type == 0x1) {
-				unsigned char *p;
-				int p_len;
-
-				str[0] = '1';
-				len = 1;
-				p = vpd;
-				while ((p = memchr(vpd, ' ', vpd_len))) {
-					p_len = p - vpd;
-					if (len + p_len > maxlen - 1)
-						p_len = maxlen - len - 2;
-					memcpy(str + len, vpd, p_len);
-					len += p_len;
-					if (len >= maxlen - 1) {
-						str[len] = '\0';
-						break;
-					}
-					str[len] = '_';
-					len ++;
-					vpd = p;
-					vpd_len -= p_len;
-					while (vpd && *vpd == ' ') {
-						vpd++;
-						vpd_len --;
-					}
-				}
-				if (len > 1 && str[len - 1] == '_') {
-					str[len - 1] = '\0';
-					len--;
-				}
-			}
-		}
-	} else
+	if (pg == 0x80)
+		len = parse_vpd_pg80(buff, str, maxlen);
+	else if (pg == 0x83)
+		len = parse_vpd_pg83(buff, buff_len, str, maxlen);
+	else
 		len = -ENOSYS;
 
 	return len;
-- 
1.8.4.5

  parent reply	other threads:[~2015-03-16 12:36 UTC|newest]

Thread overview: 98+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2015-03-16 12:35 [PATCH 00/78] SUSE SLES resync Hannes Reinecke
2015-03-16 12:35 ` [PATCH 01/78] libmultipath: remove compilation warning in devmapper.c Hannes Reinecke
2015-03-16 12:35 ` [PATCH 02/78] mpath_persist: Do not call exit() from a shared library Hannes Reinecke
2015-03-16 12:35 ` [PATCH 03/78] libmultipath: filter for missing property in get_refwwid() Hannes Reinecke
2015-03-16 12:35 ` [PATCH 04/78] Double uevent stacksize yet again Hannes Reinecke
2015-03-16 12:35 ` [PATCH 05/78] discovery: do not fail discovery on individual devices Hannes Reinecke
2015-03-16 12:35 ` [PATCH 06/78] libmultipath: Prefer deprecated 'getuid' callout Hannes Reinecke
2015-03-16 12:35 ` [PATCH 07/78] libmultipath: Skip paths with empty wwid Hannes Reinecke
2015-03-16 12:35 ` [PATCH 08/78] Make systemd installation path configurable Hannes Reinecke
2015-03-16 12:35 ` [PATCH 09/78] Add multipath rules for systemd support Hannes Reinecke
2015-03-16 12:35 ` [PATCH 10/78] Fixup multipathd.socket to resolve ordering dependeny Hannes Reinecke
2015-03-16 12:35 ` [PATCH 11/78] Fixup dependencies in multipathd.service Hannes Reinecke
2015-03-16 12:35 ` [PATCH 12/78] multipathd: set correct PID when running in debug mode Hannes Reinecke
2015-03-16 12:36 ` [PATCH 13/78] Do not print empty device strings during discovery Hannes Reinecke
2015-03-16 12:36 ` [PATCH 14/78] kpartx.rules: do not call blkid Hannes Reinecke
2015-03-16 12:36 ` [PATCH 15/78] Use 'SCSI_IDENT_.*' as the default property whitelist Hannes Reinecke
2015-03-16 12:36 ` [PATCH 16/78] Fixup wwid blacklist printing Hannes Reinecke
2015-03-16 12:36 ` [PATCH 17/78] Allow for empty path argument when printing information Hannes Reinecke
2015-03-16 12:36 ` [PATCH 18/78] Disable reassign maps per default Hannes Reinecke
2015-03-16 12:36 ` [PATCH 19/78] multipathd: implement 'list path <path>' cli command Hannes Reinecke
2015-03-16 12:36 ` [PATCH 20/78] Make checker_put() and prio_put() idempotent Hannes Reinecke
2015-03-16 12:36 ` [PATCH 21/78] Remove trailing linefeed from sysfs attributes Hannes Reinecke
2015-03-16 12:36 ` [PATCH 22/78] multipath: implement option '-u' for uevents Hannes Reinecke
2015-03-16 12:36 ` [PATCH 23/78] Install multipath rule under '56-multipath.rules' Hannes Reinecke
2015-03-16 12:36 ` [PATCH 24/78] multipath.rules: Whitelist devices Hannes Reinecke
2015-03-16 12:36 ` [PATCH 25/78] multipath.rules: fixup race condition with systemd Hannes Reinecke
2015-03-16 12:36 ` [PATCH 26/78] 11-dm-mpath.rules: Import blkid values if all paths are down Hannes Reinecke
2015-03-27  3:42   ` Benjamin Marzinski
2015-03-27 16:03     ` Hannes Reinecke
2015-03-27 16:14       ` Benjamin Marzinski
2015-03-16 12:36 ` [PATCH 27/78] kpartx.rules: Skip kpartx for multipath events Hannes Reinecke
2015-03-16 12:36 ` [PATCH 28/78] multipathd: handle DOMAP_RETRY Hannes Reinecke
2015-03-16 12:36 ` [PATCH 29/78] multipathd: cleanup foreground operation Hannes Reinecke
2015-03-16 12:36 ` [PATCH 30/78] Update hwtable for EMC XtremIO Hannes Reinecke
2015-03-16 12:36 ` [PATCH 31/78] multipath: check for running daemon when called with '-u' Hannes Reinecke
2015-03-16 12:36 ` [PATCH 32/78] Revert 'return PATH_DOWN for quiesced paths' Hannes Reinecke
2015-03-16 12:36 ` [PATCH 33/78] Do not treat 'transport-offline' paths as 'offline' Hannes Reinecke
2015-03-16 12:36 ` [PATCH 34/78] Check for valid DM_DEVICE_INFO before proceeding Hannes Reinecke
2015-03-16 12:36 ` [PATCH 35/78] Separate out uevent parsing functions Hannes Reinecke
2015-03-16 12:36 ` [PATCH 36/78] Use poll() when receiving uevents Hannes Reinecke
2015-03-16 12:36 ` [PATCH 37/78] mpath_persist: cleanup Hannes Reinecke
2015-03-16 12:36 ` [PATCH 38/78] kpartx: use standard 'major' and 'minor' macros Hannes Reinecke
2015-03-16 12:36 ` [PATCH 39/78] multipath: Use standard 'major' macro Hannes Reinecke
2015-03-16 12:36 ` [PATCH 40/78] Remove sysfs_get_dev Hannes Reinecke
2015-03-16 12:36 ` [PATCH 41/78] Add paths with a size of '0' as 'ghost' paths Hannes Reinecke
2015-03-16 12:36 ` [PATCH 42/78] Remove last argument from verify_paths() Hannes Reinecke
2015-03-16 12:36 ` [PATCH 43/78] Fixup device-mapper 'cookie' handling Hannes Reinecke
2015-03-25 16:30   ` Benjamin Marzinski
2015-03-25 16:59     ` Benjamin Marzinski
2015-03-26 14:20     ` Hannes Reinecke
2015-03-16 12:36 ` [PATCH 44/78] multipath: do not print state 'orphan' for option '-l' Hannes Reinecke
2015-03-16 12:36 ` [PATCH 45/78] Return error when receiving CLI packet Hannes Reinecke
2015-03-16 12:36 ` [PATCH 46/78] Implement 'uxsock_timeout' keyword Hannes Reinecke
2015-03-16 12:36 ` [PATCH 47/78] Do not print empty multipaths section Hannes Reinecke
2015-03-16 12:36 ` [PATCH 48/78] multipathd: reload map if reinstate failed Hannes Reinecke
2015-03-16 12:36 ` [PATCH 49/78] multipathd: do not remove paths without uevents Hannes Reinecke
2015-03-16 12:36 ` [PATCH 50/78] Allow zero-sized devices during configuration Hannes Reinecke
2015-03-27  3:56   ` Benjamin Marzinski
2015-03-27  7:16     ` Hannes Reinecke
2015-03-16 12:36 ` [PATCH 51/78] Rework uev_add_path() Hannes Reinecke
2015-03-16 12:36 ` [PATCH 52/78] multipathd: Issue warning on CLI command timeout Hannes Reinecke
2015-03-16 12:36 ` [PATCH 53/78] Use strlen() when checking for valid wwid Hannes Reinecke
2015-03-16 12:36 ` [PATCH 54/78] multipathd: Use standard lists for CLI handling Hannes Reinecke
2015-03-16 12:36 ` [PATCH 55/78] uxlsnr: use typedef for trigger function Hannes Reinecke
2015-03-16 12:36 ` [PATCH 56/78] multipathd: lock cli client list Hannes Reinecke
2015-03-16 12:36 ` [PATCH 57/78] multipath: enable sync support Hannes Reinecke
2015-03-16 12:36 ` [PATCH 58/78] Remove dm_udev_XXX wrapper functions Hannes Reinecke
2015-03-16 12:36 ` [PATCH 59/78] Revert to ACT_RELOAD in domap if the map exists Hannes Reinecke
2015-03-16 12:36 ` [PATCH 60/78] multipathd: use local variable for watchdog configuration Hannes Reinecke
2015-03-16 12:36 ` [PATCH 61/78] Ignore devices when sysfs_get_tgt_nodename fails Hannes Reinecke
2015-03-16 12:36 ` [PATCH 62/78] Skip USB devices during discovery Hannes Reinecke
2015-03-16 12:36 ` [PATCH 63/78] Read wwid from sysfs vpg_pg83 attribute Hannes Reinecke
2015-03-16 12:36 ` [PATCH 64/78] Assign local priority for NAA VPD descriptor Hannes Reinecke
2015-03-16 12:36 ` [PATCH 65/78] Use sysfs attribute vpd_pg80 to read serial number Hannes Reinecke
2015-03-16 12:36 ` [PATCH 66/78] Update multipath.conf.5 to clarify wwid generation Hannes Reinecke
2015-03-16 12:36 ` [PATCH 67/78] libmultipath: Fall back to SG_IO if no UID could be assigned Hannes Reinecke
2015-03-16 12:36 ` [PATCH 68/78] libmultipath: unset 'uid_attribute' on failure Hannes Reinecke
2015-03-27  4:10   ` Benjamin Marzinski
2015-03-27  7:17     ` Hannes Reinecke
2015-03-16 12:36 ` Hannes Reinecke [this message]
2015-03-16 12:36 ` [PATCH 70/78] multipathd: use SG_IO as fallback to generate uid Hannes Reinecke
2015-03-16 12:36 ` [PATCH 71/78] Do not automatically fall back to vpd uid generation Hannes Reinecke
2015-03-16 12:36 ` [PATCH 72/78] libmultipath: make vpd page 0x80 optional Hannes Reinecke
2015-03-16 12:37 ` [PATCH 73/78] multipathd: push down lock in checkerloop() Hannes Reinecke
2015-03-27  4:21   ` Benjamin Marzinski
2015-03-16 12:37 ` [PATCH 74/78] Allow specific CLI commands to run unlocked Hannes Reinecke
2015-03-27  5:38   ` Benjamin Marzinski
2015-03-16 12:37 ` [PATCH 75/78] Push down vector lock during uevent processing Hannes Reinecke
2015-03-27  5:46   ` Benjamin Marzinski
2015-03-16 12:37 ` [PATCH 76/78] multipathd: timeout CLI commands when waiting for lock Hannes Reinecke
2015-03-16 12:37 ` [PATCH 77/78] multipathd: asynchronous configuration Hannes Reinecke
2015-03-27  5:58   ` Benjamin Marzinski
2015-03-27  8:09     ` Hannes Reinecke
2015-03-16 12:37 ` [PATCH 78/78] multipathd: trigger all devices on startup Hannes Reinecke
2015-03-27  5:59   ` Benjamin Marzinski
2015-03-27  7:22     ` Hannes Reinecke
2015-03-29 16:28 ` [PATCH 00/78] SUSE SLES resync Christophe Varoqui
2015-03-30  6:07   ` Hannes Reinecke

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1426509425-15978-70-git-send-email-hare@suse.de \
    --to=hare@suse.de \
    --cc=christophe.varoqui@gmail.com \
    --cc=dm-devel@redhat.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox