--- old/usr/src/lib/libdisasm/common/dis_s390x.c	2015-10-14 16:30:24.756400492 -0400
+++ new/usr/src/lib/libdisasm/common/dis_s390x.c	2015-10-14 16:30:24.760193270 -0400
@@ -16,6 +16,7 @@
 #include <stdio.h>
 #include <libdisasm.h>
 #include <sys/sysmacros.h>
+#include <sys/debug.h>
 #include <sys/byteorder.h>
 
 #include "libdisasm_impl.h"
@@ -70,7 +71,7 @@
  * Extended opcode tables indicade which additional bits of the instruction
  * should be inspected.  These bits are used as an index into the sub table.
  *
- * Multiple mnemonic tables, are used to print different mnemonics depending
+ * Multiple mnemonic tables are used to print different mnemonics depending
  * on the architecture.  Over the years, certain instructions got a new
  * preferred mnemonic.  For example, 0xa70 is test-under-mask-high (tmh) on
  * System/390.  On z/Architecture systems, the instruction behaves
@@ -95,6 +96,10 @@
  * we print:
  *
  *    bne  0x123(%r1,%r2)
+ *
+ * Note that we are using designated initializers via the INSTR/TABLE/MULTI
+ * macros and therefore the below tables can be sparse.  We rely on unset
+ * entries having zero format fields (aka. IF_INVAL) per C99.
  */
 
 /* BEGIN CSTYLED */
@@ -181,20 +186,20 @@
 struct inst_table {
 	union {
 		struct {
-			const char *name;
-			unsigned flags;
-		} inst;
+			const char *it_name;
+			unsigned it_flags;
+		} it_inst;
 		struct {
-			const struct inst_table *ptr;
-			uint8_t off:4;
-			uint8_t shift:4;
-			uint8_t mask;
-		} table;
+			const struct inst_table *it_ptr;
+			uint8_t it_off:4;
+			uint8_t it_shift:4;
+			uint8_t it_mask;
+		} it_table;
 		struct {
-			const struct inst_table *ptr;
-		} multi;
-	} u;
-	enum ifmt fmt;
+			const struct inst_table *it_ptr;
+		} it_multi;
+	} it_u;
+	enum ifmt it_fmt;
 };
 
 #define	BITFLD(a, b)		DECL_BITFIELD2(b:4, a:4)
@@ -530,24 +535,24 @@
 };
 
 #define	INSTR(op, m, fm, fl)	[op] = { \
-					.u.inst = { \
-						.name = (m), \
-						.flags = (fl), \
+					.it_u.it_inst = { \
+						.it_name = (m), \
+						.it_flags = (fl), \
 					}, \
-					.fmt = (fm), \
+					.it_fmt = (fm), \
 				}
 #define	TABLE(op, tbl, o, s, m)	[op] = { \
-					.u.table = { \
-						.ptr = (tbl), \
-						.off = (o), \
-						.shift = (s), \
-						.mask = (m), \
+					.it_u.it_table = { \
+						.it_ptr = (tbl), \
+						.it_off = (o), \
+						.it_shift = (s), \
+						.it_mask = (m), \
 					}, \
-					.fmt = IF_TBL, \
+					.it_fmt = IF_TBL, \
 				}
 #define	MULTI(op, tbl)		[op] = { \
-					.u.multi.ptr = (tbl), \
-					.fmt = IF_MULTI, \
+					.it_u.it_multi.it_ptr = (tbl), \
+					.it_fmt = IF_MULTI, \
 				}
 
 /*
@@ -1790,12 +1795,17 @@
 static inline uint32_t
 val_8_4_8(uint32_t hi, uint32_t mid, uint32_t lo)
 {
+	ASSERT0(hi & ~0xff);
+	ASSERT0(mid & ~0xf);
+	ASSERT0(lo & ~0xff);
 	return ((hi << 12) | (mid << 8) | lo);
 }
 
 static inline uint32_t
 val_16_16(uint32_t hi, uint32_t lo)
 {
+	ASSERT0(hi & ~0xffff);
+	ASSERT0(lo & ~0xffff);
 	return ((BE_16(hi) << 16) | BE_16(lo));
 }
 
@@ -1808,6 +1818,8 @@
 static inline uint32_t
 val_8_16(uint32_t hi, uint32_t lo)
 {
+	ASSERT0(hi & ~0xff);
+	ASSERT0(lo & ~0xffff);
 	return ((hi << 16) | BE_16(lo));
 }
 
@@ -1816,6 +1828,7 @@
 {
 	int32_t tmp = val_8_16(hi, lo);
 
+	/* sign extend */
 	if (tmp & 0x00800000)
 		return (0xff000000 | tmp);
 	return (tmp);
@@ -1824,6 +1837,8 @@
 static inline uint32_t
 val_4_8(uint32_t hi, uint32_t lo)
 {
+	ASSERT0(hi & ~0xf);
+	ASSERT0(lo & ~0xff);
 	return ((hi << 8) | lo);
 }
 
@@ -1832,6 +1847,7 @@
 {
 	uint32_t tmp = val_4_8(hi, lo);
 
+	/* sign extend */
 	if (tmp & 0x800)
 		return (0xfffff000 | tmp);
 	return (tmp);
@@ -2468,30 +2484,30 @@
 	const struct inst_table *tbl = &tbl_xx[inst->raw[0]];
 	int tmp;
 
-	while (tbl->fmt == IF_TBL || tbl->fmt == IF_MULTI) {
-		if (tbl->fmt == IF_TBL) {
+	while (tbl->it_fmt == IF_TBL || tbl->it_fmt == IF_MULTI) {
+		if (tbl->it_fmt == IF_TBL) {
 			int idx;
 
-			idx   = inst->raw[tbl->u.table.off];
-			idx >>= tbl->u.table.shift;
-			idx  &= tbl->u.table.mask;
-
-			tbl = &tbl->u.table.ptr[idx];
-		} else if (tbl->fmt == IF_MULTI) {
-			tbl = &tbl->u.multi.ptr[mach];
+			idx   = inst->raw[tbl->it_u.it_table.it_off];
+			idx >>= tbl->it_u.it_table.it_shift;
+			idx  &= tbl->it_u.it_table.it_mask;
+
+			tbl = &tbl->it_u.it_table.it_ptr[idx];
+		} else if (tbl->it_fmt == IF_MULTI) {
+			tbl = &tbl->it_u.it_multi.it_ptr[mach];
 		}
 	}
 
-	if (tbl->fmt == IF_INVAL)
+	if (tbl->it_fmt == IF_INVAL)
 		goto inval;
 
-	if ((tbl->u.inst.flags & mach) == 0)
+	if ((tbl->it_u.it_inst.it_flags & mach) == 0)
 		goto inval;
 
-	tmp = snprintf(buf, buflen, "%-7s ", tbl->u.inst.name);
+	tmp = snprintf(buf, buflen, "%-7s ", tbl->it_u.it_inst.it_name);
 
-	fmt_fxns[tbl->fmt](addr, inst, buf + tmp, buflen - tmp,
-	    tbl->u.inst.flags);
+	fmt_fxns[tbl->it_fmt](addr, inst, buf + tmp, buflen - tmp,
+	    tbl->it_u.it_inst.it_flags);
 
 	return (0);
 
