9820 Want risc-v disassembler
Reviewed by: Dan McDonald <danmcd@joyent.com>
Reviewed by: Richard Lowe <richlowe@richlowe.net>
Approved by: Garrett D'Amore <garrett@damore.org>
diff --git a/usr/src/cmd/dis/dis_main.c b/usr/src/cmd/dis/dis_main.c
index 2886f41..db785ef 100644
--- a/usr/src/cmd/dis/dis_main.c
+++ b/usr/src/cmd/dis/dis_main.c
@@ -26,6 +26,7 @@
  * Copyright 2011 Jason King.  All rights reserved.
  * Copyright 2012 Joshua M. Clulow <josh@sysmgr.org>
  * Copyright 2015 Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
+ * Copyright 2018, Joyent, Inc.
  */
 
 #include <ctype.h>
@@ -579,6 +580,29 @@
 			}
 			break;
 
+		case EM_RISCV:
+			/*
+			 * RISC-V is defined to be litle endian. The current ISA
+			 * makes it clear that the 64-bit instructions can
+			 * co-exist with the 32-bit ones and therefore we don't
+			 * need a separate elf class at this time.
+			 */
+			if (ehdr.e_ident[EI_DATA] != ELFDATA2LSB) {
+				warn("invalid EI_DATA field for RISC-V object");
+				return;
+			}
+
+			if (ehdr.e_ident[EI_CLASS] == ELFCLASS32) {
+				g_flags |= DIS_RISCV_32;
+			} else if (ehdr.e_ident[EI_CLASS] == ELFCLASS64) {
+				g_flags |= DIS_RISCV_64;
+			} else {
+				warn("invalid EI_CLASS field for RISC-V "
+				    "object");
+				return;
+			}
+			break;
+
 		default:
 			die("%s: unsupported ELF machine 0x%x", filename,
 			    ehdr.e_machine);
diff --git a/usr/src/lib/libdisasm/Makefile.com b/usr/src/lib/libdisasm/Makefile.com
index b465f56..2afa0e3 100644
--- a/usr/src/lib/libdisasm/Makefile.com
+++ b/usr/src/lib/libdisasm/Makefile.com
@@ -23,6 +23,7 @@
 # Use is subject to license terms.
 # Copyright 2012 Joshua M. Clulow <josh@sysmgr.org>
 # Copyright 2015 Nexenta Systems, Inc.  All rights reserved.
+# Copyright (c) 2018, Joyent, Inc.
 #
 
 #
@@ -58,6 +59,7 @@
 			$(COMDIR)/dis_sparc_fmt.c \
 			$(COMDIR)/dis_sparc_instr.c
 SRCS_s390x=		$(COMDIR)/dis_s390x.c
+SRCS_riscv=		$(COMDIR)/dis_riscv.c
 
 OBJECTS_i386=		dis_i386.o \
 			dis_tables.o
@@ -65,6 +67,7 @@
 			dis_sparc_fmt.o \
 			dis_sparc_instr.o
 OBJECTS_s390x=		dis_s390x.o
+OBJECTS_riscv=		dis_riscv.o
 
 #
 # We build the regular shared library with support for all architectures.
@@ -74,7 +77,8 @@
 OBJECTS_library=	$(OBJECTS_common) \
 			$(OBJECTS_i386) \
 			$(OBJECTS_sparc) \
-			$(OBJECTS_s390x)
+			$(OBJECTS_s390x) \
+			$(OBJECTS_riscv)
 OBJECTS_standalone=	$(OBJECTS_common) \
 			$(OBJECTS_$(MACH))
 OBJECTS=		$(OBJECTS_$(CURTYPE))
@@ -84,7 +88,8 @@
 SRCS_library=		$(SRCS_common) \
 			$(SRCS_i386) \
 			$(SRCS_sparc) \
-			$(SRCS_s390x)
+			$(SRCS_s390x) \
+			$(SRCS_riscv)
 SRCS_standalone=	$(SRCS_common) \
 			$(SRCS_$(MACH))
 SRCS=			$(SRCS_$(CURTYPE))
diff --git a/usr/src/lib/libdisasm/common/dis_riscv.c b/usr/src/lib/libdisasm/common/dis_riscv.c
new file mode 100644
index 0000000..fa7cc30
--- /dev/null
+++ b/usr/src/lib/libdisasm/common/dis_riscv.c
@@ -0,0 +1,2000 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright (c) 2018, Joyent, Inc.
+ */
+
+/*
+ * RISC-V Instruction set decoder
+ */
+
+#include <libdisasm.h>
+#include <sys/byteorder.h>
+#include <sys/debug.h>
+
+#include "libdisasm_impl.h"
+
+#include <stdio.h>
+
+extern int strcmp(const char *, const char *);
+
+/*
+ * Register names based on their ABI name.
+ */
+static const char *dis_riscv_regs[32] = {
+	"x0", "ra", "sp", "gp", "tp", "t0", "t1", "t2",
+	"s0", "s1", "a0", "a1", "a2", "a3", "a4", "a5",
+	"a6", "a7", "s2", "s3", "s4", "s5", "s6", "s7",
+	"s8", "s9", "s10", "s11", "t3", "t4", "t5", "t6"
+};
+
+static const char *dis_riscv_fpregs[32] = {
+	"ft0", "ft1", "ft2", "ft3", "ft4", "ft5", "ft6", "ft7",
+	"fs0", "fs1", "fa0", "fa1", "fa2", "fa3", "fa4", "fa5",
+	"fa6", "fa7", "fs2", "fs3", "fs4", "fs5", "fs6", "fs7",
+	"fs8", "fs9", "fs10", "fs11", "ft8", "ft9", "ft10", "ft11",
+};
+
+static const char *dis_riscv_c_regs[8] = {
+	"s0", "s1", "a0", "a1", "a2", "a3", "a4", "a5"
+};
+
+static const char *dis_riscv_c_fpregs[8] = {
+	"fs0", "fs1", "fa0", "fa1", "fa2", "fa3", "fa4", "fa5"
+};
+
+/*
+ * RM names have the leading comma in them because the last value represents
+ * that the hardware register decides the rounding mode and therefore nothing
+ * should be appended to the instruction.
+ */
+static const char *dis_riscv_rm[8] = {
+	",rne", ",rtz", ",rdn", ",rup", ",rmm", ",???", ",???", ""
+};
+
+typedef struct dis_riscv_csr {
+	uint_t		drc_val;
+	const char	*drc_name;
+} dis_riscv_csr_t;
+
+/*
+ * The current set of CSR names as per Table 2.2-2.5 from RISC-V Privileged
+ * Architectures V1.10. These include all of the ones in the User-Level ISA.
+ * These are ordered per the doc.
+ */
+static dis_riscv_csr_t dis_riscv_csr_map[] = {
+	/* User Trap */
+	{ 0x000, "ustatus" },	{ 0x004, "uie" },	{ 0x005, "utvec" },
+	/* User Trap Handling */
+	{ 0x040, "uscratch" },	{ 0x041, "uepc" },	{ 0x042, "ucause" },
+	{ 0x043, "utval" },	{ 0x044, "uip" },
+	/* User Floating-Point CSRs */
+	{ 0x001, "fflags" },	{ 0x002, "frm" },	{ 0x003, "fcsr" },
+	/* User Counters/Timers */
+	{ 0xc00, "cycle" },	{ 0xc01, "time" },	{ 0xc02, "instret" },
+	{ 0xc03, "hpmcounter3" },	{ 0xc04, "hpmcounter4" },
+	{ 0xc05, "hpmcounter5" },	{ 0xc06, "hpmcounter6" },
+	{ 0xc07, "hpmcounter7" },	{ 0xc08, "hpmcounter8" },
+	{ 0xc09, "hpmcounter9" },	{ 0xc0a, "hpmcounter10" },
+	{ 0xc0b, "hpmcounter11" },	{ 0xc0c, "hpmcounter12" },
+	{ 0xc0d, "hpmcounter13" },	{ 0xc0e, "hpmcounter14" },
+	{ 0xc0f, "hpmcounter15" },	{ 0xc10, "hpmcounter16" },
+	{ 0xc11, "hpmcounter17" },	{ 0xc12, "hpmcounter18" },
+	{ 0xc13, "hpmcounter19" },	{ 0xc14, "hpmcounter20" },
+	{ 0xc15, "hpmcounter21" },	{ 0xc16, "hpmcounter22" },
+	{ 0xc17, "hpmcounter23" },	{ 0xc18, "hpmcounter24" },
+	{ 0xc19, "hpmcounter25" },	{ 0xc1a, "hpmcounter26" },
+	{ 0xc1b, "hpmcounter27" },	{ 0xc1c, "hpmcounter28" },
+	{ 0xc1d, "hpmcounter29" },	{ 0xc1e, "hpmcounter30" },
+	{ 0xc1f, "hpmcounter31" },
+	{ 0xc80, "cycleh" },	{ 0xc81, "timeh" },	{ 0xc82, "instreth" },
+	{ 0xc83, "hpmcounter3h" },	{ 0xc84, "hpmcounter4h" },
+	{ 0xc85, "hpmcounter5h" },	{ 0xc86, "hpmcounter6h" },
+	{ 0xc87, "hpmcounter7h" },	{ 0xc88, "hpmcounter8h" },
+	{ 0xc89, "hpmcounter9h" },	{ 0xc8a, "hpmcounter10h" },
+	{ 0xc8b, "hpmcounter11h" },	{ 0xc8c, "hpmcounter12h" },
+	{ 0xc8d, "hpmcounter13h" },	{ 0xc8e, "hpmcounter14h" },
+	{ 0xc8f, "hpmcounter15h" },	{ 0xc90, "hpmcounter16h" },
+	{ 0xc91, "hpmcounter17h" },	{ 0xc92, "hpmcounter18h" },
+	{ 0xc93, "hpmcounter19h" },	{ 0xc94, "hpmcounter20h" },
+	{ 0xc95, "hpmcounter21h" },	{ 0xc96, "hpmcounter22h" },
+	{ 0xc97, "hpmcounter23h" },	{ 0xc98, "hpmcounter24h" },
+	{ 0xc99, "hpmcounter25h" },	{ 0xc9a, "hpmcounter26h" },
+	{ 0xc9b, "hpmcounter27h" },	{ 0xc9c, "hpmcounter28h" },
+	{ 0xc9d, "hpmcounter29h" },	{ 0xc9e, "hpmcounter30h" },
+	{ 0xc9f, "hpmcounter31h" },
+	/* Supervisor Trap Status */
+	{ 0x100, "sstatus" },	{ 0x102, "sedeleg" },	{ 0x103, "sideleg" },
+	{ 0x104, "sie" },	{ 0x105, "stvec" },	{ 0x106, "scounteren" },
+	/* Supervisor Trap Handling */
+	{ 0x140, "sscratch" },	{ 0x141, "sepc" },	{ 0x142, "scause" },
+	{ 0x143, "stval" },	{ 0x144, "sip" },
+	/* Supervisor Protection and Translation */
+	{ 0x180, "satp" },
+	/* Machine Information Registers */
+	{ 0xf11, "mvendorid" },	{ 0xf12, "marchid" },
+	{ 0xf13, "mimpid" },	{ 0xf14, "mhartid" },
+	/* Machine Trap Setup */
+	{ 0x300, "mstatus" },	{ 0x301, "misa" },	{ 0x302, "medeleg" },
+	{ 0x303, "mideleg" },	{ 0x304, "mie" },	{ 0x305, "mtvec" },
+	{ 0x306, "mcounteren" },
+	/* Machine Trap Handling */
+	{ 0x340, "mscratch" },	{ 0x341, "mepc" },	{ 0x342, "mcause" },
+	{ 0x343, "mtval" },	{ 0x344, "mip" },
+	/* Machine Protection and Translation */
+	{ 0x3a0, "pmpcfg0" },	{ 0x3a1, "pmpcfg1" },
+	{ 0x3a2, "pmpcfg2" },	{ 0x3a3, "pmpcfg3" },
+	{ 0x3b0, "pmpaddr0" },	{ 0x3b1, "pmpaddr1" },
+	{ 0x3b2, "pmpaddr2" },	{ 0x3b3, "pmpaddr3" },
+	{ 0x3b4, "pmpaddr4" },	{ 0x3b5, "pmpaddr5" },
+	{ 0x3b6, "pmpaddr6" },	{ 0x3b7, "pmpaddr7" },
+	{ 0x3b8, "pmpaddr8" },	{ 0x3b9, "pmpaddr9" },
+	{ 0x3ba, "pmpaddr10" },	{ 0x3bb, "pmpaddr11" },
+	{ 0x3bc, "pmpaddr12" },	{ 0x3bd, "pmpaddr13" },
+	{ 0x3be, "pmpaddr14" },	{ 0x3bf, "pmpaddr15" }
+};
+
+typedef enum dis_riscv_csr_alias_type {
+	DIS_RISCV_CSR_READ,
+	DIS_RISCV_CSR_READ_GEN,
+	DIS_RISCV_CSR_SWAP,
+	DIS_RISCV_CSR_SWAP_IMM,
+	DIS_RISCV_CSR_WRITE,
+	DIS_RISCV_CSR_WRITE_GEN,
+	DIS_RISCV_CSR_WRITE_IMM,
+	DIS_RISCV_CSR_WRITE_IMM_GEN
+} dis_riscv_csr_alias_type_t;
+
+typedef struct dis_riscv_csr_alias {
+	const char *drca_alias;
+	dis_riscv_csr_alias_type_t drca_type;
+	const char *drca_base;
+	const char *drca_csr;
+	int drca_rd;
+	int drca_rs;
+} dis_riscv_csr_alias_t;
+
+/*
+ * Table of aliases. A NULL or -1 indicates a don't care.
+ */
+static dis_riscv_csr_alias_t dis_riscv_csr_alias[] = {
+	{ "rdinstret", DIS_RISCV_CSR_READ, "csrrs", "instret", -1, 0 },
+	{ "rdinstreth", DIS_RISCV_CSR_READ, "csrrs", "instreth", -1, 0 },
+	{ "rdcycle", DIS_RISCV_CSR_READ, "csrrs", "cycle", -1, 0 },
+	{ "rdcycleh", DIS_RISCV_CSR_READ, "csrrs", "cycleh", -1, 0 },
+	{ "rdtime", DIS_RISCV_CSR_READ, "csrrs", "time", -1, 0 },
+	{ "rdtimeh", DIS_RISCV_CSR_READ, "csrrs", "timeh", -1, 0 },
+	{ "frcsr", DIS_RISCV_CSR_READ, "csrrs", "fcsr", -1, 0 },
+	{ "fscsr", DIS_RISCV_CSR_WRITE, "csrrw", "fcsr", 0, -1 },
+	{ "fscsr", DIS_RISCV_CSR_SWAP, "csrrw", "fcsr", -1, -1 },
+	{ "frrm", DIS_RISCV_CSR_READ, "csrrs", "frm", -1, 0 },
+	{ "fsrm", DIS_RISCV_CSR_WRITE, "csrrw", "frm", 0, -1 },
+	{ "fsrm", DIS_RISCV_CSR_SWAP, "csrrw", "frm", -1, -1 },
+	{ "fsrmi", DIS_RISCV_CSR_WRITE_IMM, "csrrwi", "frm", 0, -1 },
+	{ "fsrmi", DIS_RISCV_CSR_SWAP_IMM, "csrrwi", "frm", -1, -1 },
+	{ "frflags", DIS_RISCV_CSR_READ, "csrrs", "fflags", -1, 0 },
+	{ "fsflags", DIS_RISCV_CSR_WRITE, "csrrw", "fflags", 0, -1 },
+	{ "fsflags", DIS_RISCV_CSR_SWAP, "csrrw", "fflags", -1, -1 },
+	{ "fsflagsi", DIS_RISCV_CSR_WRITE_IMM, "csrrwi", "fflags", 0, -1 },
+	{ "fsflagsi", DIS_RISCV_CSR_SWAP_IMM, "csrrwi", "fflags", -1, -1 },
+	/*
+	 * These are the generic aliases that aren't based on the CSR. Keep
+	 * them last.
+	 */
+	{ "csrr", DIS_RISCV_CSR_READ_GEN, "csrrs", NULL, -1, 0 },
+	{ "csrw", DIS_RISCV_CSR_WRITE_GEN, "csrrw", NULL, 0, -1 },
+	{ "csrs", DIS_RISCV_CSR_WRITE_GEN, "csrrs", NULL, 0, -1 },
+	{ "csrc", DIS_RISCV_CSR_WRITE_GEN, "csrrc", NULL, 0, -1 },
+	{ "csrwi", DIS_RISCV_CSR_WRITE_IMM_GEN, "csrrwi", NULL, 0, -1 },
+	{ "csrsi", DIS_RISCV_CSR_WRITE_IMM_GEN, "csrrsi", NULL, 0, -1 },
+	{ "csrci", DIS_RISCV_CSR_WRITE_IMM_GEN, "csrrci", NULL, 0, -1 },
+};
+
+/*
+ * Take an n-bit value whose sign bit is indicated by the big sign and convert
+ * to a signed type.
+ */
+static uint_t
+dis_riscv_sign_extend(uint_t val, uint_t sbit, const char **sign)
+{
+	VERIFY3U(sbit, <=, 31);
+
+	if (val >= 1 << sbit) {
+		*sign = "-";
+		return ((1 << (sbit + 1)) - val);
+	} else {
+		*sign = "";
+		return (val);
+	}
+}
+
+/*
+ * Four byte decode tables. This is derived from the RV32/64G Instruction Set
+ * Listings. We describe a table entry based on the opcode and optional opcodes
+ * based on the type of instruction that it is and its encoding format. Most
+ * sets of instructions have one of several uniform encoding types.
+ *
+ *  31             25 24     20 19  15 14    12  11        7  6      0
+ * |    funct7       |   r2    |  rs1 | funct3 | rd          | opcode | R-type
+ * |    imm[11:0]              |  rs1 | funct3 | rd          | opcode | I-type
+ * |    imm[11:5]    |   r2    |  rs1 | funct3 | imm[4:0]    | opcode | S-type
+ * |    imm[12|10:5] |   r2    |  rs1 | funct3 | imm[4:1|11] | opcode | B-type
+ * |    imm[31:12]                             | rd          | opcode | U-type
+ * |    imm[10|10:1|11|19:12]                  | rd          | opcode | J-type
+ */
+typedef enum dis_riscv_itype {
+	DIS_RISCV_I_R_TYPE,
+	DIS_RISCV_I_I_TYPE,
+	DIS_RISCV_I_S_TYPE,
+	DIS_RISCV_I_B_TYPE,
+	DIS_RISCV_I_U_TYPE,
+	DIS_RISCV_I_J_TYPE,
+	DIS_RISCV_I_R4_TYPE,
+	/*
+	 * This is a variant of the standard R type where the first bit of
+	 * funct7 is actually used for this shift.
+	 */
+	DIS_RISCV_I_SHIFT64_TYPE,
+	/*
+	 * This type isn't explicitly defined in the ISA doc; however, it is a
+	 * standard format that is for all of the Atomic class instructions.
+	 * This is treated like an R-type, except the funct7 is really a funct5.
+	 * The load variant is similar; however, rs2 must be zero.
+	 */
+	DIS_RISCV_I_RV32A_TYPE,
+	DIS_RISCV_I_RV32A_LOAD_TYPE,
+	/*
+	 * This is a custom type we've defined where the first value is the
+	 * instruction mask and the second value is the value of the bits in it.
+	 * This is used for a few irregular instructions ala FENCE and ECALL.
+	 */
+	DIS_RISCV_I_MASK_TYPE,
+	/*
+	 * This type is used for FP arguments that use rs2 as an opcode.
+	 */
+	DIS_RISCV_I_FP_RS2OP_TYPE,
+	/*
+	 * This type uses the opcode and funct7 and uses funct3 as a rounding
+	 * mode argument.
+	 */
+	DIS_RISCV_I_FP_RM_TYPE,
+	/*
+	 * This fp type uses the opcode, funct7, funct3, and rs2 as an op type.
+	 */
+	DIS_RISCV_I_FP_R_RS2_TYPE,
+} dis_riscv_itype_t;
+
+#define	DIS_RISCV_OPCODE(x)	((x) & 0x7f)
+#define	DIS_RISCV_FUNCT3(x)	(((x) >> 12) & 0x7)
+#define	DIS_RISCV_FUNCT7(x)	(((x) >> 25) & 0x7f)
+#define	DIS_RISCV_RD(x)		(((x) >> 7) & 0x1f)
+#define	DIS_RISCV_RS1(x)	(((x) >> 15) & 0x1f)
+#define	DIS_RISCV_RS2(x)	(((x) >> 20) & 0x1f)
+#define	DIS_RISCV_FP_RS3(x)	(((x) >> 27) & 0x1f)
+#define	DIS_RISCV_FUNCT2(x)	(((x) >> 25) & 0x03)
+
+/*
+ * SHIFT funct7 variant.
+ */
+#define	DIS_RISCV_SFUNCT7(x)	(((x) >> 26) & 0x3f)
+
+#define	DIS_RISCV_UIMM(x)	(((x) >> 12) & 0xfffff)
+
+#define	DIS_RISCV_IIMM(x)	(((x) >> 20) & 0xfff)
+
+#define	DIS_RISCV_BIMM_12(x)	(((x) >> 19) & 0x1000)
+#define	DIS_RISCV_BIMM_11(x)	(((x) & 0x80) << 4)
+#define	DIS_RISCV_BIMM_10_5(x)	(((x) >> 20) & 0x7e0)
+#define	DIS_RISCV_BIMM_4_1(x)	(((x) >> 7) & 0x1e)
+
+#define	DIS_RISCV_SIMM_UP(x)	((((x) >> 25) & 0x7f) << 5)
+#define	DIS_RISCV_SIMM_LOW(x)	(((x) >> 7) & 0x1f)
+
+#define	DIS_RISCV_JIMM_20(x)	(((x) & 0x80000000) >> 11)
+#define	DIS_RISCV_JIMM_19_12(x)	((x) & 0xff000)
+#define	DIS_RISCV_JIMM_11(x)	(((x) & 100000) >> 9)
+#define	DIS_RISCV_JIMM_10_1(x)	(((x) & 0x7fe00000) >> 20)
+
+#define	DIS_RISCV_RVA_FUNCT5(x)	(((x) >> 27) & 0x1f)
+#define	DIS_RISCV_RVA_AQ(x)	(((x) >> 26) & 0x1)
+#define	DIS_RISCV_RVA_RL(x)	(((x) >> 25) & 0x1)
+
+struct dis_riscv_instr;
+typedef void (*dis_riscv_func_t)(dis_handle_t *, uint32_t,
+    struct dis_riscv_instr *, char *, size_t);
+
+typedef struct dis_riscv_instr {
+	const char 		*drv_name;
+	dis_riscv_itype_t	drv_type;
+	dis_riscv_func_t	drv_print;
+	uint_t			drv_opcode;
+	uint_t			drv_funct3;
+	uint_t			drv_funct7;
+	uint_t			drv_funct2;
+} dis_riscv_instr_t;
+
+/*ARGSUSED*/
+static void
+dis_riscv_rtype_32(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s,%s", table->drv_name,
+	    dis_riscv_regs[DIS_RISCV_RD(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS2(instr)]);
+}
+
+static void
+dis_riscv_itype_32(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t imm = dis_riscv_sign_extend(DIS_RISCV_IIMM(instr), 11, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,%s0%o",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], s, imm);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,%s0x%x",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], s, imm);
+	}
+}
+
+static void
+dis_riscv_btype_32(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t bimm = DIS_RISCV_BIMM_12(instr) | DIS_RISCV_BIMM_11(instr) |
+	    DIS_RISCV_BIMM_10_5(instr) | DIS_RISCV_BIMM_4_1(instr);
+	uint_t imm = dis_riscv_sign_extend(bimm, 12, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,%s0%o",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], s, imm);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,%s0x%x",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], s, imm);
+	}
+}
+
+static void
+dis_riscv_load(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t imm = dis_riscv_sign_extend(DIS_RISCV_IIMM(instr), 11, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0%o(%s)",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    s, imm, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0x%x(%s)",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    s, imm, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	}
+}
+
+static void
+dis_riscv_stype_32(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t simm = DIS_RISCV_SIMM_UP(instr) | DIS_RISCV_SIMM_LOW(instr);
+	uint_t val = dis_riscv_sign_extend(simm, 11, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0%o(%s)",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RS2(instr)],
+		    s, val, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0x%x(%s)",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RS2(instr)],
+		    s, val, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	}
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_utype_32(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,0x%x", table->drv_name,
+	    dis_riscv_regs[DIS_RISCV_RD(instr)], DIS_RISCV_UIMM(instr));
+}
+
+static void
+dis_riscv_jtype_32(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t jimm = DIS_RISCV_JIMM_20(instr) | DIS_RISCV_JIMM_19_12(instr) |
+	    DIS_RISCV_JIMM_11(instr) | DIS_RISCV_JIMM_10_1(instr);
+	uint_t imm = dis_riscv_sign_extend(jimm, 20, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0%o",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    s, imm);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0x%x",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    s, imm);
+	}
+}
+
+/*
+ * The shift instructions are a variant on the R-type instructions where RS2 is
+ * an immediate to perform the shift by as opposed to a register.
+ */
+static void
+dis_riscv_shift_32(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,0%o",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], DIS_RISCV_RS2(instr));
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,0x%x",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], DIS_RISCV_RS2(instr));
+	}
+}
+
+/*
+ * The 64-bit version of shift instructions steals an extra bit from funct7 to
+ * construct the shift amount.
+ */
+static void
+dis_riscv_shift_64(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	uint_t shift = DIS_RISCV_RS2(instr) | ((instr & (1UL << 25)) >> 20);
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,0%o",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], shift);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,0x%x",
+		    table->drv_name, dis_riscv_regs[DIS_RISCV_RD(instr)],
+		    dis_riscv_regs[DIS_RISCV_RS1(instr)], shift);
+	}
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_csr(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	uint_t rd, csr, rs, i;
+	const char *csrstr = NULL;
+	char csrval[32];
+	dis_riscv_csr_alias_t *alias = NULL;
+
+	rd = DIS_RISCV_RD(instr);
+	rs = DIS_RISCV_RS1(instr);
+	csr = DIS_RISCV_IIMM(instr);
+
+	for (i = 0; i < ARRAY_SIZE(dis_riscv_csr_map); i++) {
+		if (csr == dis_riscv_csr_map[i].drc_val) {
+			csrstr = dis_riscv_csr_map[i].drc_name;
+			break;
+		}
+	}
+
+	if (csrstr == NULL) {
+		(void) dis_snprintf(csrval, sizeof (csrval), "0x%x", csr);
+		csrstr = csrval;
+	}
+
+	for (i = 0; i < ARRAY_SIZE(dis_riscv_csr_alias); i++) {
+		dis_riscv_csr_alias_t *a = &dis_riscv_csr_alias[i];
+		if (strcmp(a->drca_base, table->drv_name) != 0)
+			continue;
+		if (a->drca_csr != NULL && strcmp(a->drca_csr, csrstr) != 0)
+			continue;
+		if (a->drca_rd != -1 && a->drca_rd != rd)
+			continue;
+		if (a->drca_rs != -1 && a->drca_rs != rs)
+			continue;
+		alias = a;
+		break;
+	}
+
+	if (alias == NULL) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s,%s", table->drv_name,
+		    dis_riscv_regs[rd], csrstr, dis_riscv_regs[rs]);
+		return;
+	}
+
+	switch (alias->drca_type) {
+	case DIS_RISCV_CSR_READ:
+		(void) dis_snprintf(buf, buflen, "%s %s", alias->drca_alias,
+		    dis_riscv_regs[rd]);
+		break;
+	case DIS_RISCV_CSR_READ_GEN:
+		(void) dis_snprintf(buf, buflen, "%s %s,%s", alias->drca_alias,
+		    dis_riscv_regs[rd], csrstr);
+		break;
+	case DIS_RISCV_CSR_SWAP:
+		(void) dis_snprintf(buf, buflen, "%s %s,%s", alias->drca_alias,
+		    dis_riscv_regs[rd], dis_riscv_regs[rs]);
+		break;
+	case DIS_RISCV_CSR_WRITE:
+		(void) dis_snprintf(buf, buflen, "%s %s", alias->drca_alias,
+		    dis_riscv_regs[rs]);
+		break;
+	case DIS_RISCV_CSR_WRITE_GEN:
+		(void) dis_snprintf(buf, buflen, "%s %s,%s", alias->drca_alias,
+		    csrstr, dis_riscv_regs[rs]);
+		break;
+	default:
+		(void) dis_snprintf(buf, buflen, "<unknown>");
+		break;
+	}
+}
+
+static void
+dis_riscv_csri(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	uint_t rd, csr, imm, i;
+	const char *csrstr = NULL;
+	char csrval[32];
+	dis_riscv_csr_alias_t *alias = NULL;
+
+	rd = DIS_RISCV_RD(instr);
+	imm = DIS_RISCV_RS1(instr);
+	csr = DIS_RISCV_IIMM(instr);
+
+	for (i = 0; i < ARRAY_SIZE(dis_riscv_csr_map); i++) {
+		if (csr == dis_riscv_csr_map[i].drc_val) {
+			csrstr = dis_riscv_csr_map[i].drc_name;
+			break;
+		}
+	}
+
+	if (csrstr == NULL) {
+		(void) dis_snprintf(csrval, sizeof (csrval), "0x%x", csr);
+		csrstr = csrval;
+	}
+
+	for (i = 0; i < ARRAY_SIZE(dis_riscv_csr_alias); i++) {
+		dis_riscv_csr_alias_t *a = &dis_riscv_csr_alias[i];
+		if (strcmp(a->drca_base, table->drv_name) != 0)
+			continue;
+		if (a->drca_csr != NULL && strcmp(a->drca_csr, csrstr) != 0)
+			continue;
+		if (a->drca_rd != -1 && a->drca_rd != rd)
+			continue;
+		if (a->drca_rs != -1)
+			continue;
+		alias = a;
+		break;
+	}
+
+	if (alias == NULL) {
+		if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+			(void) dis_snprintf(buf, buflen, "%s %s,%s,0%o",
+			    table->drv_name, dis_riscv_regs[rd], csrstr, imm);
+		} else {
+			(void) dis_snprintf(buf, buflen, "%s %s,%s,0x%x",
+			    table->drv_name, dis_riscv_regs[rd], csrstr, imm);
+		}
+		return;
+	}
+
+	switch (alias->drca_type) {
+	case DIS_RISCV_CSR_SWAP_IMM:
+		if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+			(void) dis_snprintf(buf, buflen, "%s %s,0%o",
+			    alias->drca_alias, dis_riscv_regs[rd], imm);
+		} else {
+			(void) dis_snprintf(buf, buflen, "%s %s,0x%x",
+			    alias->drca_alias, dis_riscv_regs[rd], imm);
+		}
+		break;
+	case DIS_RISCV_CSR_WRITE_IMM:
+		if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+			(void) dis_snprintf(buf, buflen, "%s 0%o",
+			    alias->drca_alias, imm);
+		} else {
+			(void) dis_snprintf(buf, buflen, "%s 0x%x",
+			    alias->drca_alias, imm);
+		}
+		break;
+	case DIS_RISCV_CSR_WRITE_IMM_GEN:
+		if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+			(void) dis_snprintf(buf, buflen, "%s %s,0%o",
+			    alias->drca_alias, csrstr, imm);
+		} else {
+			(void) dis_snprintf(buf, buflen, "%s %s,0x%x",
+			    alias->drca_alias, csrstr, imm);
+		}
+		break;
+	default:
+		(void) dis_snprintf(buf, buflen, "<unknown>");
+		break;
+	}
+}
+
+#define	DIS_RISCV_FENCE_PRED(x)	(((x) >> 24) & 0xf)
+#define	DIS_RISCV_FENCE_SUCC(x)	(((x) >> 20) & 0xf)
+#define	DIS_RISCV_FENCE_I	0x8
+#define	DIS_RISCV_FENCE_O	0x4
+#define	DIS_RISCV_FENCE_R	0x2
+#define	DIS_RISCV_FENCE_W	0x1
+#define	DIS_RISCV_FENCE_IORW	0xf
+
+/*ARGSUSED*/
+static void
+dis_riscv_fence(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	uint_t pred, succ;
+
+	pred = DIS_RISCV_FENCE_PRED(instr);
+	succ = DIS_RISCV_FENCE_SUCC(instr);
+
+	/*
+	 * If both halves are iorw that is aliased to just an empty fence
+	 * instruction per Chapter 20 - RISC-V Assembly Programmer's Handbook in
+	 * the RISC-V user spec.
+	 */
+	if (pred == DIS_RISCV_FENCE_IORW && succ == DIS_RISCV_FENCE_IORW) {
+		(void) dis_snprintf(buf, buflen, "%s", table->drv_name);
+		return;
+	}
+
+	(void) dis_snprintf(buf, buflen, "%s %s%s%s%s, %s%s%s%s",
+	    table->drv_name,
+	    pred & DIS_RISCV_FENCE_I ? "i" : "",
+	    pred & DIS_RISCV_FENCE_O ? "o" : "",
+	    pred & DIS_RISCV_FENCE_R ? "r" : "",
+	    pred & DIS_RISCV_FENCE_W ? "w" : "",
+	    succ & DIS_RISCV_FENCE_I ? "i" : "",
+	    succ & DIS_RISCV_FENCE_O ? "o" : "",
+	    succ & DIS_RISCV_FENCE_R ? "r" : "",
+	    succ & DIS_RISCV_FENCE_W ? "w" : "");
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_name(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s", table->drv_name);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_rs1_rs2(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s", table->drv_name,
+	    dis_riscv_regs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS2(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_rv32a_load(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_instr_t *table, char *buf, size_t buflen)
+{
+	const char *suffix = "";
+
+	if (DIS_RISCV_RVA_AQ(instr) && DIS_RISCV_RVA_RL(instr)) {
+		suffix = ".aqrl";
+	} else if (DIS_RISCV_RVA_AQ(instr)) {
+		suffix = ".aq";
+	} else if (DIS_RISCV_RVA_RL(instr)) {
+		suffix = ".rl";
+	}
+
+	(void) dis_snprintf(buf, buflen, "%s%s %s,(%s)", table->drv_name,
+	    suffix, dis_riscv_regs[DIS_RISCV_RD(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_rv32a(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *suffix = "";
+
+	if (DIS_RISCV_RVA_AQ(instr) && DIS_RISCV_RVA_RL(instr)) {
+		suffix = ".aqrl";
+	} else if (DIS_RISCV_RVA_AQ(instr)) {
+		suffix = ".aq";
+	} else if (DIS_RISCV_RVA_RL(instr)) {
+		suffix = ".rl";
+	}
+
+	(void) dis_snprintf(buf, buflen, "%s%s %s,%s,(%s)", table->drv_name,
+	    suffix, dis_riscv_regs[DIS_RISCV_RD(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS2(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+}
+
+static void
+dis_riscv_fp_load(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t imm = dis_riscv_sign_extend(DIS_RISCV_IIMM(instr), 11, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0%o(%s)",
+		    table->drv_name, dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+		    s, imm, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0x%x(%s)",
+		    table->drv_name, dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+		    s, imm, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	}
+}
+
+static void
+dis_riscv_fp_store(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t simm = DIS_RISCV_SIMM_UP(instr) | DIS_RISCV_SIMM_LOW(instr);
+	uint_t val = dis_riscv_sign_extend(simm, 11, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0%o(%s)",
+		    table->drv_name, dis_riscv_fpregs[DIS_RISCV_RS2(instr)],
+		    s, val, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0x%x(%s)",
+		    table->drv_name, dis_riscv_fpregs[DIS_RISCV_RS2(instr)],
+		    s, val, dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+	}
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_r(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s,%s", table->drv_name,
+	    dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS2(instr)]);
+}
+
+/*
+ * Variant of fp_r type that goes to integer destination registers.
+ */
+/*ARGSUSED*/
+static void
+dis_riscv_fp_r_fpi(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s,%s", table->drv_name,
+	    dis_riscv_regs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS2(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_r4(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s,%s,%s%s", table->drv_name,
+	    dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS2(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_FP_RS3(instr)],
+	    dis_riscv_rm[DIS_RISCV_FUNCT3(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_rs2_fp(dis_handle_t *dhp, uint32_t instr, dis_riscv_instr_t *table,
+    char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s%s", table->drv_name,
+	    dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_rm[DIS_RISCV_FUNCT3(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_rs2_fp_nr(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s", table->drv_name,
+	    dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_rs2_fpi(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s%s", table->drv_name,
+	    dis_riscv_regs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_rm[DIS_RISCV_FUNCT3(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_rs2_ifp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s%s", table->drv_name,
+	    dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_rm[DIS_RISCV_FUNCT3(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_rs2_fpi_nr(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s", table->drv_name,
+	    dis_riscv_regs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)]);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_rs2_ifp_nr(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s", table->drv_name,
+	    dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+	    dis_riscv_regs[DIS_RISCV_RS1(instr)]);
+}
+
+
+/*ARGSUSED*/
+static void
+dis_riscv_fp_rm(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s,%s%s", table->drv_name,
+	    dis_riscv_fpregs[DIS_RISCV_RD(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS1(instr)],
+	    dis_riscv_fpregs[DIS_RISCV_RS2(instr)],
+	    dis_riscv_rm[DIS_RISCV_FUNCT3(instr)]);
+}
+
+#define	DIS_RISCV_R32(str, op, f3, f7)	\
+	{ str, DIS_RISCV_I_R_TYPE, dis_riscv_rtype_32, op, f3, f7 }
+#define	DIS_RISCV_I32(str, op, f3)	\
+	{ str, DIS_RISCV_I_I_TYPE, dis_riscv_itype_32, op, f3 }
+#define	DIS_RISCV_S32(str, op, f3)	\
+	{ str, DIS_RISCV_I_S_TYPE, dis_riscv_stype_32, op, f3 }
+#define	DIS_RISCV_B32(str, op, f3)	\
+	{ str, DIS_RISCV_I_B_TYPE, dis_riscv_btype_32, op, f3 }
+#define	DIS_RISCV_U32(str, op)		\
+	{ str, DIS_RISCV_I_U_TYPE, dis_riscv_utype_32, op }
+#define	DIS_RISCV_J32(str, op)		\
+	{ str, DIS_RISCV_I_J_TYPE, dis_riscv_jtype_32, op }
+
+/*
+ * These are non-standard types that we've defined because they require
+ * different handling.
+ */
+#define	DIS_RISCV_SHIFT32(str, op, f3, f7)	\
+	{ str, DIS_RISCV_I_R_TYPE, dis_riscv_shift_32, op, f3, f7 }
+#define	DIS_RISCV_SHIFT64(str, op, f3, f7)	\
+	{ str, DIS_RISCV_I_SHIFT64_TYPE, dis_riscv_shift_64, op, f3, f7 }
+#define	DIS_RISCV_CSR(str, op, f3)		\
+	{ str, DIS_RISCV_I_I_TYPE, dis_riscv_csr, op, f3 }
+#define	DIS_RISCV_CSRI(str, op, f3)		\
+	{ str, DIS_RISCV_I_I_TYPE, dis_riscv_csri, op, f3 }
+#define	DIS_RISCV_LOAD(str, op, f3)		\
+	{ str, DIS_RISCV_I_I_TYPE, dis_riscv_load, op, f3 }
+
+#define	DIS_RISCV_MASK(str, mask, val, func)	\
+	{ str, DIS_RISCV_I_MASK_TYPE, func, mask, val }
+
+
+/*
+ * Atomic-extension specific entries
+ */
+#define	DIS_RISCV_A32(str, op, f3, f5)		\
+	{ str, DIS_RISCV_I_RV32A_TYPE, dis_riscv_rv32a, op, f3, f5 }
+#define	DIS_RISCV_A32LOAD(str, op, f3, f5, f2)	\
+	{ str, DIS_RISCV_I_RV32A_LOAD_TYPE, dis_riscv_rv32a_load, op, f3, \
+	    f5, f2 }
+
+/*
+ * Floating-point specific entries
+ */
+#define	DIS_RISCV_FP_LOAD(str, op, f3)				\
+	{ str, DIS_RISCV_I_I_TYPE, dis_riscv_fp_load, op, f3 }
+#define	DIS_RISCV_FP_STORE(str, op, f3)				\
+	{ str, DIS_RISCV_I_S_TYPE, dis_riscv_fp_store, op, f3 }
+#define	DIS_RISCV_FP_R(str, op, f3, f7)				\
+	{ str, DIS_RISCV_I_R_TYPE, dis_riscv_fp_r, op, f3, f7 }
+#define	DIS_RISCV_FP_R4(str, op, f2)				\
+	{ str, DIS_RISCV_I_R4_TYPE, dis_riscv_fp_r4, op, 0, 0, f2 }
+#define	DIS_RISCV_FP_RS2_FP(str, op, rs2, f7)			\
+	{ str, DIS_RISCV_I_FP_RS2OP_TYPE, dis_riscv_fp_rs2_fp, op, rs2, f7 }
+#define	DIS_RISCV_FP_RS2_FP_NR(str, op, rs2, f7)		\
+	{ str, DIS_RISCV_I_FP_RS2OP_TYPE, dis_riscv_fp_rs2_fp_nr, op, rs2, f7 }
+#define	DIS_RISCV_FP_RS2_FPI(str, op, rs2, f7)			\
+	{ str, DIS_RISCV_I_FP_RS2OP_TYPE, dis_riscv_fp_rs2_fpi, op, rs2, f7 }
+#define	DIS_RISCV_FP_RS2_IFP(str, op, rs2, f7)			\
+	{ str, DIS_RISCV_I_FP_RS2OP_TYPE, dis_riscv_fp_rs2_ifp, op, rs2, f7 }
+#define	DIS_RISCV_FP_RS2_IFP_NR(str, op, rs2, f7)		\
+	{ str, DIS_RISCV_I_FP_RS2OP_TYPE, dis_riscv_fp_rs2_ifp_nr, op, rs2, f7 }
+#define	DIS_RISCV_FP_RM(str, op, f7)				\
+	{ str, DIS_RISCV_I_FP_RM_TYPE, dis_riscv_fp_rm, op, 0, f7 }
+#define	DIS_RISCV_FP_R_RS2_FPI(str, op, f3, rs2, f7)		\
+	{ str, DIS_RISCV_I_FP_R_RS2_TYPE, dis_riscv_fp_rs2_fpi, op, f3, f7, \
+	    rs2 }
+#define	DIS_RISCV_FP_R_RS2_IFP(str, op, f3, rs2, f7)		\
+	{ str, DIS_RISCV_I_FP_R_RS2_TYPE, dis_riscv_fp_rs2_ifp, op, f3, f7, \
+	    rs2 }
+#define	DIS_RISCV_FP_R_RS2_FPI_NR(str, op, f3, rs2, f7)		\
+	{ str, DIS_RISCV_I_FP_R_RS2_TYPE, dis_riscv_fp_rs2_fpi_nr, op, f3, \
+	    f7, rs2 }
+#define	DIS_RISCV_FP_R_RS2_IFP_NR(str, op, f3, rs2, f7)		\
+	{ str, DIS_RISCV_I_FP_R_RS2_TYPE, dis_riscv_fp_rs2_ifp_nr, op, f3, \
+	    f7, rs2 }
+#define	DIS_RISCV_FP_RI(str, op, f3, f7) 			\
+	{ str, DIS_RISCV_I_R_TYPE, dis_riscv_fp_r_fpi, op, f3, f7 }
+
+/*
+ * This table is ordered such that it follows the ordering in the RISC-V ISA
+ * Manual.
+ */
+static dis_riscv_instr_t dis_riscv_4byte[] = {
+	/*
+	 * RV32I
+	 */
+	DIS_RISCV_U32("lui", 0x37),
+	DIS_RISCV_U32("auipc", 0x17),
+	DIS_RISCV_J32("jal", 0x6f),
+	/* ret is a special case of jalr */
+	DIS_RISCV_MASK("ret", 0xffffffff, 0x00008067, dis_riscv_name),
+	DIS_RISCV_I32("jalr", 0x67, 0x0),
+	DIS_RISCV_B32("beq", 0x63, 0x0),
+	DIS_RISCV_B32("bne", 0x63, 0x1),
+	DIS_RISCV_B32("blt", 0x63, 0x4),
+	DIS_RISCV_B32("bge", 0x63, 0x5),
+	DIS_RISCV_B32("bltu", 0x63, 0x6),
+	DIS_RISCV_B32("bgeu", 0x63, 0x7),
+	DIS_RISCV_LOAD("lb", 0x03, 0x0),
+	DIS_RISCV_LOAD("lh", 0x03, 0x1),
+	DIS_RISCV_LOAD("lw", 0x03, 0x2),
+	DIS_RISCV_LOAD("lbu", 0x03, 0x4),
+	DIS_RISCV_LOAD("lhu", 0x03, 0x5),
+	DIS_RISCV_S32("sb", 0x23, 0x0),
+	DIS_RISCV_S32("sh", 0x23, 0x1),
+	DIS_RISCV_S32("sw", 0x23, 0x2),
+	/* nop is addi x0, x0, 0 */
+	DIS_RISCV_MASK("nop", 0xffffffff, 0x00000013, dis_riscv_name),
+	DIS_RISCV_I32("addi", 0x13, 0x0),
+	DIS_RISCV_I32("slti", 0x13, 0x2),
+	DIS_RISCV_I32("sltiu", 0x13, 0x3),
+	DIS_RISCV_I32("xori", 0x13, 0x4),
+	DIS_RISCV_I32("ori", 0x13, 0x6),
+	DIS_RISCV_I32("andi", 0x13, 0x7),
+	DIS_RISCV_SHIFT32("slli", 0x13, 0x1, 0x00),
+	DIS_RISCV_SHIFT32("srli", 0x13, 0x5, 0x00),
+	DIS_RISCV_SHIFT32("srai", 0x13, 0x5, 0x20),
+	DIS_RISCV_R32("add", 0x33, 0x0, 0x00),
+	DIS_RISCV_R32("sub", 0x33, 0x0, 0x20),
+	DIS_RISCV_R32("sll", 0x33, 0x1, 0x00),
+	DIS_RISCV_R32("slt", 0x33, 0x2, 0x00),
+	DIS_RISCV_R32("sltu", 0x33, 0x3, 0x00),
+	DIS_RISCV_R32("xor", 0x33, 0x4, 0x00),
+	DIS_RISCV_R32("srl", 0x33, 0x5, 0x00),
+	DIS_RISCV_R32("sra", 0x33, 0x5, 0x20),
+	DIS_RISCV_R32("or", 0x33, 0x6, 0x00),
+	DIS_RISCV_R32("and", 0x33, 0x7, 0x00),
+	DIS_RISCV_MASK("fence", 0xf00fffff, 0xf, dis_riscv_fence),
+	DIS_RISCV_MASK("fence.i", 0xfffff00f, 0x100f, dis_riscv_name),
+	DIS_RISCV_MASK("ecall", 0xffffffff, 0x73, dis_riscv_name),
+	DIS_RISCV_MASK("ebreak", 0xffffffff, 0x100073, dis_riscv_name),
+	DIS_RISCV_CSR("csrrw", 0x73, 0x1),
+	DIS_RISCV_CSR("csrrs", 0x73, 0x2),
+	DIS_RISCV_CSR("csrrc", 0x73, 0x3),
+	DIS_RISCV_CSRI("csrrwi", 0x73, 0x5),
+	DIS_RISCV_CSRI("csrrsi", 0x73, 0x6),
+	DIS_RISCV_CSRI("csrrci", 0x73, 0x7),
+	/*
+	 * RV64I
+	 */
+	DIS_RISCV_LOAD("lwu", 0x03, 0x6),
+	DIS_RISCV_LOAD("ld", 0x03, 0x3),
+	DIS_RISCV_S32("sd", 0x23, 0x3),
+	DIS_RISCV_SHIFT64("slli", 0x13, 0x1, 0x0),
+	DIS_RISCV_SHIFT64("srli", 0x13, 0x5, 0x0),
+	DIS_RISCV_SHIFT64("srai", 0x13, 0x5, 0x10),
+	DIS_RISCV_I32("addiw", 0x1b, 0x0),
+	DIS_RISCV_SHIFT32("slliw", 0x1b, 0x1, 0x0),
+	DIS_RISCV_SHIFT32("srliw", 0x1b, 0x5, 0x0),
+	DIS_RISCV_SHIFT32("sraiw", 0x1b, 0x5, 0x20),
+	DIS_RISCV_R32("addw", 0x3b, 0x0, 0x00),
+	DIS_RISCV_R32("subw", 0x3b, 0x0, 0x20),
+	DIS_RISCV_R32("sllw", 0x3b, 0x1, 0x00),
+	DIS_RISCV_R32("srlw", 0x3b, 0x5, 0x00),
+	DIS_RISCV_R32("sraw", 0x3b, 0x5, 0x20),
+	/*
+	 * RV32M
+	 */
+	DIS_RISCV_R32("mul", 0x33, 0x0, 0x01),
+	DIS_RISCV_R32("mulh", 0x33, 0x1, 0x01),
+	DIS_RISCV_R32("mulhsu", 0x33, 0x2, 0x01),
+	DIS_RISCV_R32("mulhu", 0x33, 0x3, 0x01),
+	DIS_RISCV_R32("div", 0x33, 0x4, 0x01),
+	DIS_RISCV_R32("divu", 0x33, 0x5, 0x01),
+	DIS_RISCV_R32("rem", 0x33, 0x6, 0x01),
+	DIS_RISCV_R32("remu", 0x33, 0x7, 0x01),
+	/*
+	 * RV64M
+	 */
+	DIS_RISCV_R32("mulw", 0x3b, 0x0, 0x01),
+	DIS_RISCV_R32("divw", 0x3b, 0x4, 0x01),
+	DIS_RISCV_R32("divuw", 0x3b, 0x5, 0x01),
+	DIS_RISCV_R32("remw", 0x3b, 0x6, 0x01),
+	DIS_RISCV_R32("remuw", 0x3b, 0x7, 0x01),
+	/*
+	 * RV32A
+	 */
+	DIS_RISCV_A32LOAD("lr.w", 0x2f, 0x2, 0x02, 0x0),
+	DIS_RISCV_A32("sc.w", 0x2f, 0x2, 0x03),
+	DIS_RISCV_A32("amoswap.w", 0x2f, 0x2, 0x01),
+	DIS_RISCV_A32("amoadd.w", 0x2f, 0x2, 0x00),
+	DIS_RISCV_A32("amoxor.w", 0x2f, 0x2, 0x04),
+	DIS_RISCV_A32("amoand.w", 0x2f, 0x2, 0x0c),
+	DIS_RISCV_A32("amoor.w", 0x2f, 0x2, 0x08),
+	DIS_RISCV_A32("amomin.w", 0x2f, 0x2, 0x10),
+	DIS_RISCV_A32("amomax.w", 0x2f, 0x2, 0x14),
+	DIS_RISCV_A32("amominu.w", 0x2f, 0x2, 0x18),
+	DIS_RISCV_A32("amomaxu.w", 0x2f, 0x2, 0x1c),
+	/*
+	 * RV64A
+	 */
+	DIS_RISCV_A32LOAD("lr.d", 0x2f, 0x3, 0x02, 0x0),
+	DIS_RISCV_A32("sc.d", 0x2f, 0x3, 0x03),
+	DIS_RISCV_A32("amoswap.d", 0x2f, 0x3, 0x01),
+	DIS_RISCV_A32("amoadd.d", 0x2f, 0x3, 0x00),
+	DIS_RISCV_A32("amoxor.d", 0x2f, 0x3, 0x04),
+	DIS_RISCV_A32("amoand.d", 0x2f, 0x3, 0x0c),
+	DIS_RISCV_A32("amoor.d", 0x2f, 0x3, 0x08),
+	DIS_RISCV_A32("amomin.d", 0x2f, 0x3, 0x10),
+	DIS_RISCV_A32("amomax.d", 0x2f, 0x3, 0x14),
+	DIS_RISCV_A32("amominu.d", 0x2f, 0x3, 0x18),
+	DIS_RISCV_A32("amomaxu.d", 0x2f, 0x3, 0x1c),
+	/*
+	 * RV32F
+	 */
+	DIS_RISCV_FP_LOAD("flw", 0x07, 0x2),
+	DIS_RISCV_FP_STORE("fsw", 0x27, 0x2),
+	DIS_RISCV_FP_R4("fmadd.s", 0x43, 0x0),
+	DIS_RISCV_FP_R4("fmsub.s", 0x47, 0x0),
+	DIS_RISCV_FP_R4("fnmsub.s", 0x4b, 0x0),
+	DIS_RISCV_FP_R4("fnmadd.s", 0x4f, 0x0),
+	DIS_RISCV_FP_RM("fadd.s", 0x53, 0x00),
+	DIS_RISCV_FP_RM("fsub.s", 0x53, 0x04),
+	DIS_RISCV_FP_RM("fmul.s", 0x53, 0x08),
+	DIS_RISCV_FP_RM("fdiv.s", 0x53, 0xc),
+	DIS_RISCV_FP_RS2_FP("fsqrt.s", 0x53, 0x00, 0x2c),
+	DIS_RISCV_FP_R("fsgnj.s", 0x53, 0x0, 0x10),
+	DIS_RISCV_FP_R("fsgnjn.s", 0x53, 0x1, 0x10),
+	DIS_RISCV_FP_R("fsgnjx.s", 0x53, 0x2, 0x10),
+	DIS_RISCV_FP_R("fmin.s", 0x53, 0x0, 0x14),
+	DIS_RISCV_FP_R("fmax.s", 0x53, 0x1, 0x14),
+	DIS_RISCV_FP_RS2_FPI("fcvt.w.s", 0x53, 0x00, 0x60),
+	DIS_RISCV_FP_RS2_FPI("fcvt.wu.s", 0x53, 0x01, 0x60),
+	DIS_RISCV_FP_R_RS2_FPI_NR("fmv.x.w", 0x53, 0x00, 0x00, 0x70),
+	DIS_RISCV_FP_RI("feq.s", 0x53, 0x2, 0x50),
+	DIS_RISCV_FP_RI("flt.s", 0x53, 0x1, 0x50),
+	DIS_RISCV_FP_RI("fle.s", 0x53, 0x0, 0x50),
+	DIS_RISCV_FP_R_RS2_FPI_NR("fclass.s", 0x53, 0x1, 0x00, 0x70),
+	DIS_RISCV_FP_RS2_IFP("fcvt.s.w", 0x53, 0x00, 0x68),
+	DIS_RISCV_FP_RS2_IFP("fcvt.s.wu", 0x53, 0x01, 0x68),
+	DIS_RISCV_FP_R_RS2_IFP_NR("fmv.w.x", 0x53, 0x0, 0x00, 0x78),
+	/*
+	 * RV64F
+	 */
+	DIS_RISCV_FP_RS2_FPI("fcvt.l.s", 0x53, 0x02, 0x60),
+	DIS_RISCV_FP_RS2_FPI("fcvt.lu.s", 0x53, 0x03, 0x60),
+	DIS_RISCV_FP_RS2_IFP("fcvt.s.l", 0x53, 0x02, 0x68),
+	DIS_RISCV_FP_RS2_IFP("fcvt.s.lu", 0x53, 0x03, 0x68),
+	/*
+	 * RV32D
+	 */
+	DIS_RISCV_FP_LOAD("fld", 0x07, 0x3),
+	DIS_RISCV_FP_STORE("fsd", 0x27, 0x3),
+	DIS_RISCV_FP_R4("fmadd.d", 0x43, 0x1),
+	DIS_RISCV_FP_R4("fmsub.d", 0x47, 0x1),
+	DIS_RISCV_FP_R4("fnmsub.d", 0x4b, 0x1),
+	DIS_RISCV_FP_R4("fnmadd.d", 0x4f, 0x1),
+	DIS_RISCV_FP_RM("fadd.d", 0x53, 0x01),
+	DIS_RISCV_FP_RM("fsub.d", 0x53, 0x05),
+	DIS_RISCV_FP_RM("fmul.d", 0x53, 0x09),
+	DIS_RISCV_FP_RM("fdiv.d", 0x53, 0xd),
+	DIS_RISCV_FP_RS2_FP("fsqrt.d", 0x53, 0x00, 0x2d),
+	DIS_RISCV_FP_R("fsgnj.d", 0x53, 0x0, 0x11),
+	DIS_RISCV_FP_R("fsgnjn.d", 0x53, 0x1, 0x11),
+	DIS_RISCV_FP_R("fsgnjx.d", 0x53, 0x2, 0x11),
+	DIS_RISCV_FP_R("fmin.d", 0x53, 0x0, 0x15),
+	DIS_RISCV_FP_R("fmax.d", 0x53, 0x1, 0x15),
+	DIS_RISCV_FP_RS2_FP("fcvt.s.d", 0x53, 0x01, 0x20),
+	DIS_RISCV_FP_RS2_FP_NR("fcvt.d.s", 0x53, 0x00, 0x21),
+	DIS_RISCV_FP_RI("feq.d", 0x53, 0x2, 0x51),
+	DIS_RISCV_FP_RI("flt.d", 0x53, 0x1, 0x51),
+	DIS_RISCV_FP_RI("fle.d", 0x53, 0x0, 0x51),
+	DIS_RISCV_FP_R_RS2_FPI_NR("fclass.d", 0x53, 0x1, 0x00, 0x71),
+	DIS_RISCV_FP_RS2_FPI("fcvt.w.d", 0x53, 0x00, 0x61),
+	DIS_RISCV_FP_RS2_FPI("fcvt.wu.d", 0x53, 0x01, 0x61),
+	DIS_RISCV_FP_RS2_IFP_NR("fcvt.d.w", 0x53, 0x00, 0x69),
+	DIS_RISCV_FP_RS2_IFP_NR("fcvt.d.wu", 0x53, 0x01, 0x69),
+	/*
+	 * RV64D
+	 */
+	DIS_RISCV_FP_RS2_FPI("fcvt.l.d", 0x53, 0x02, 0x61),
+	DIS_RISCV_FP_RS2_FPI("fcvt.lu.d", 0x53, 0x03, 0x61),
+	DIS_RISCV_FP_R_RS2_FPI_NR("fmv.x.d", 0x53, 0x0, 0x00, 0x71),
+	DIS_RISCV_FP_RS2_IFP("fcvt.d.l", 0x53, 0x02, 0x69),
+	DIS_RISCV_FP_RS2_IFP("fcvt.d.lu", 0x53, 0x03, 0x69),
+	DIS_RISCV_FP_R_RS2_IFP_NR("fmv.d.x", 0x53, 0x0, 0x00, 0x79),
+	/*
+	 * Privileged Instructions from RISC-V Privileged Architectures V1.10.
+	 */
+	DIS_RISCV_MASK("uret", 0xffffffff, 0x00200073, dis_riscv_name),
+	DIS_RISCV_MASK("sret", 0xffffffff, 0x10200073, dis_riscv_name),
+	DIS_RISCV_MASK("mret", 0xffffffff, 0x30200073, dis_riscv_name),
+	DIS_RISCV_MASK("wfi", 0xffffffff, 0x10500073, dis_riscv_name),
+	DIS_RISCV_MASK("sfence.vma", 0xfe007fff, 0x12000073, dis_riscv_rs1_rs2)
+};
+
+static void
+dis_riscv_decode_4byte(dis_handle_t *dhp, uint32_t instr, char *buf,
+    size_t buflen)
+{
+	uint_t i;
+
+	for (i = 0; i < ARRAY_SIZE(dis_riscv_4byte); i++) {
+		dis_riscv_instr_t *t = &dis_riscv_4byte[i];
+		switch (t->drv_type) {
+		case DIS_RISCV_I_R_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT3(instr) == t->drv_funct3 &&
+			    DIS_RISCV_FUNCT7(instr) == t->drv_funct7) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_I_TYPE:
+		case DIS_RISCV_I_S_TYPE:
+		case DIS_RISCV_I_B_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT3(instr) == t->drv_funct3) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_U_TYPE:
+		case DIS_RISCV_I_J_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_R4_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT2(instr) == t->drv_funct2) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_MASK_TYPE:
+			if ((instr & t->drv_opcode) == t->drv_funct3) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_SHIFT64_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT3(instr) == t->drv_funct3 &&
+			    DIS_RISCV_SFUNCT7(instr) == t->drv_funct7) {
+				break;
+			}
+			continue;
+
+		case DIS_RISCV_I_RV32A_LOAD_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT3(instr) == t->drv_funct3 &&
+			    DIS_RISCV_RVA_FUNCT5(instr) == t->drv_funct7 &&
+			    DIS_RISCV_RS2(instr) == t->drv_funct2) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_RV32A_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT3(instr) == t->drv_funct3 &&
+			    DIS_RISCV_RVA_FUNCT5(instr) == t->drv_funct7) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_FP_RS2OP_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_RS2(instr) == t->drv_funct3 &&
+			    DIS_RISCV_FUNCT7(instr) == t->drv_funct7) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_FP_RM_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT7(instr) == t->drv_funct7) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_I_FP_R_RS2_TYPE:
+			if (DIS_RISCV_OPCODE(instr) == t->drv_opcode &&
+			    DIS_RISCV_FUNCT3(instr) == t->drv_funct3 &&
+			    DIS_RISCV_RS2(instr) == t->drv_funct2 &&
+			    DIS_RISCV_FUNCT7(instr) == t->drv_funct7) {
+				break;
+			}
+			continue;
+		default:
+			continue;
+		}
+
+		t->drv_print(dhp, instr, t, buf, buflen);
+		return;
+	}
+
+	(void) dis_snprintf(buf, buflen, "<unknown>");
+}
+
+/*
+ * Two byte decode table types.
+ */
+typedef enum dis_riscv_ctype {
+	/*
+	 * Indicates that we should match based on the opcode and funct3.
+	 */
+	DIS_RISCV_C_FUNCT3,
+	/*
+	 * Indicates that we should match the instruction based on a mask.
+	 */
+	DIS_RISCV_C_MATCH
+} dis_riscv_ctype_t;
+
+/*
+ * The compact forms are depending on the elf class. This is used to keep track
+ * of the class and match it.
+ */
+typedef enum dis_riscv_c_class {
+	DIS_RISCV_CL_ALL,
+	DIS_RISCV_CL_32,
+	DIS_RISCV_CL_64,
+	DIS_RISCV_CL_32_64,
+	DIS_RISCV_CL_64_128
+} dis_riscv_c_class_t;
+
+struct dis_riscv_c_instr;
+typedef void (*dis_riscv_c_func_t)(dis_handle_t *, uint32_t,
+    struct dis_riscv_c_instr *, char *, size_t);
+
+typedef struct dis_riscv_c_instr {
+	const char		*drv_c_name;
+	dis_riscv_ctype_t	drv_c_type;
+	dis_riscv_c_func_t	drv_c_print;
+	dis_riscv_c_class_t 	drv_c_class;
+	uint_t			drv_c_opcode;
+	uint_t			drv_c_funct;
+	uint_t			drv_c_mask;
+	uint_t			drv_c_match;
+} dis_riscv_c_instr_t;
+
+#define	DIS_RISCV_C_OPCODE(x)	((x) & 0x03)
+#define	DIS_RISCV_C_FUNCT3(x)	(((x) & 0xe000) >> 13)
+
+#define	DIS_RISCV_C_RS1(x)	(((x) & 0x0f80) >> 7)
+#define	DIS_RISCV_C_RS2(x)	(((x) & 0x007c) >> 2)
+#define	DIS_RISCV_C_RD(x)	DIS_RISCV_C_RS1(x)
+
+#define	DIS_RISCV_C_RS1P(x)	(((x) & 0x0380) >> 7)
+#define	DIS_RISCV_C_RS2P(x)	DIS_RISCV_C_RDP(x)
+#define	DIS_RISCV_C_RDP(x)	(((x) & 0x001c) >> 2)
+
+/*
+ * CJ format immediate extractor
+ */
+#define	DIS_RISCV_C_J_11(x)	(((x) & 0x1000) >> 1)
+#define	DIS_RISCV_C_J_4(x)	(((x) & 0x0800) >> 7)
+#define	DIS_RISCV_C_J_9_8(x)	(((x) & 0x0600) >> 1)
+#define	DIS_RISCV_C_J_10(x)	(((x) & 0x0100) << 2)
+#define	DIS_RISCV_C_J_6(x)	(((x) & 0x0080) >> 1)
+#define	DIS_RISCV_C_J_7(x)	(((x) & 0x0040) << 1)
+#define	DIS_RISCV_C_J_3_1(x)	(((x) & 0x0038) >> 3)
+#define	DIS_RISCV_C_J_5(x)	(((x) & 0x0004) << 3)
+
+/*
+ * Compact Branch extractor
+ */
+#define	DIS_RISCV_C_B_8(x)	(((x) & 0x1000) >> 4)
+#define	DIS_RISCV_C_B_4_3(x)	(((x) & 0x0c00) >> 7)
+#define	DIS_RISCV_C_B_7_6(x)	(((x) & 0x0060) << 1)
+#define	DIS_RISCV_C_B_2_1(x)	(((x) & 0x0018) >> 2)
+#define	DIS_RISCV_C_B_5(x)	(((x) & 0x0004) << 3)
+
+/*
+ * c.addi16spn extractor
+ */
+#define	DIS_RISCV_C_A16_9(x)	(((x) & 0x1000) >> 3)
+#define	DIS_RISCV_C_A16_4(x)	(((x) & 0x0040) >> 2)
+#define	DIS_RISCV_C_A16_6(x)	(((x) & 0x0020) << 1)
+#define	DIS_RISCV_C_A16_8_7(x)	(((x) & 0x0018) << 4)
+#define	DIS_RISCV_C_A16_5(x)	(((x) & 0x0004) << 3)
+
+/*
+ * c.addi4spn extractor
+ */
+#define	DIS_RISCV_C_A4_5_4(x)	(((x) & 0x1800) >> 7)
+#define	DIS_RISCV_C_A4_9_6(x)	(((x) & 0x0700) >> 2)
+#define	DIS_RISCV_C_A4_2(x)	(((x) & 0x0040) >> 4)
+#define	DIS_RISCV_C_A4_3(x)	(((x) & 0x0020) >> 2)
+
+/*ARGSUSED*/
+static void
+dis_riscv_c_name(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s", table->drv_c_name);
+}
+
+static void
+dis_riscv_c_loadstore(dis_handle_t *dhp, const char *name, const char *dreg,
+    const char *sreg, uint32_t off, char *buf, size_t buflen)
+{
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,0%o(%s)", name, dreg,
+		    off, sreg);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,0x%x(%s)", name, dreg,
+		    off, sreg);
+	}
+}
+
+static void
+dis_riscv_c_lwsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x000c) << 4) |
+	    ((instr & 0x1000) >> 7) | ((instr & 0x0070) >> 2);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RD(instr)], dis_riscv_regs[2], imm, buf,
+	    buflen);
+}
+
+static void
+dis_riscv_c_ldsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x001c) << 4) |
+	    ((instr & 0x1000) >> 7) | ((instr & 0x0060) >> 2);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RD(instr)], dis_riscv_regs[2],
+	    imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_flwsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x000c) << 4) |
+	    ((instr & 0x1000) >> 7) | ((instr & 0x0070) >> 2);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_fpregs[DIS_RISCV_C_RD(instr)], dis_riscv_regs[2],
+	    imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_fldsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x001c) << 4) |
+	    ((instr & 0x1000) >> 7) | ((instr & 0x0060) >> 2);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_fpregs[DIS_RISCV_C_RD(instr)], dis_riscv_regs[2],
+	    imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_swsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0180) >> 1) | ((instr & 0x1e00) >> 7);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RS2(instr)], dis_riscv_regs[2], imm,
+	    buf, buflen);
+}
+
+static void
+dis_riscv_c_sdsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0380) >> 1) | ((instr & 0x1c00) >> 7);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RS2(instr)], dis_riscv_regs[2], imm,
+	    buf, buflen);
+}
+
+static void
+dis_riscv_c_fswsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0180) >> 1) | ((instr & 0x1e00) >> 7);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_fpregs[DIS_RISCV_C_RS2(instr)], dis_riscv_regs[2], imm,
+	    buf, buflen);
+}
+
+static void
+dis_riscv_c_fsdsp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0380) >> 1) | ((instr & 0x1c00) >> 7);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_fpregs[DIS_RISCV_C_RS2(instr)], dis_riscv_regs[2], imm,
+	    buf, buflen);
+}
+
+static void
+dis_riscv_c_lw(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0020) << 1) | ((instr & 0x1c) >> 7) |
+	    ((instr & 0x0040) >> 3);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_c_regs[DIS_RISCV_C_RDP(instr)],
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)],
+	    imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_ld(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0060) << 1) | ((instr & 0x1c) >> 7);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_c_regs[DIS_RISCV_C_RDP(instr)],
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)],
+	    imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_flw(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0020) << 1) | ((instr & 0x1c) >> 7) |
+	    ((instr & 0x0040) >> 3);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_c_fpregs[DIS_RISCV_C_RDP(instr)],
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)],
+	    imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_fld(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint32_t imm = ((instr & 0x0060) << 1) | ((instr & 0x1c) >> 7);
+
+	dis_riscv_c_loadstore(dhp, table->drv_c_name,
+	    dis_riscv_c_fpregs[DIS_RISCV_C_RDP(instr)],
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)],
+	    imm, buf, buflen);
+}
+
+/*
+ * The J type has the 11 bit immediate arranged as:
+ *
+ *  offset[11|4|9:8|10|6|7|3:1|5] going from bits 2 to 12.
+ */
+static void
+dis_riscv_c_j(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t jimm = DIS_RISCV_C_J_11(instr) | DIS_RISCV_C_J_10(instr) |
+	    DIS_RISCV_C_J_9_8(instr) | DIS_RISCV_C_J_7(instr) |
+	    DIS_RISCV_C_J_6(instr) | DIS_RISCV_C_J_5(instr) |
+	    DIS_RISCV_C_J_4(instr) | DIS_RISCV_C_J_3_1(instr);
+	uint_t imm = dis_riscv_sign_extend(jimm, 11, &s);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s0%o", table->drv_c_name,
+		    s, imm);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s0x%x", table->drv_c_name,
+		    s, imm);
+	}
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_c_jr(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s", table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RS1(instr)]);
+}
+
+static void
+dis_riscv_c_regimm(dis_handle_t *dhp, const char *instr, const char *dreg,
+    const char *sign, uint_t imm, char *buf, size_t buflen)
+{
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0%o", instr, dreg,
+		    sign, imm);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,%s0x%x", instr, dreg,
+		    sign, imm);
+	}
+}
+
+static void
+dis_riscv_c_branch(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t bimm = DIS_RISCV_C_B_8(instr) | DIS_RISCV_C_B_7_6(instr) |
+	    DIS_RISCV_C_B_5(instr) | DIS_RISCV_C_B_4_3(instr) |
+	    DIS_RISCV_C_B_2_1(instr);
+	uint_t imm = dis_riscv_sign_extend(bimm, 8, &s);
+
+	dis_riscv_c_regimm(dhp, table->drv_c_name,
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)], s, imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_bigimmint(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t limm = ((instr & 0x1000) >> 7) | ((instr & 0x007c) >> 2);
+	uint_t imm = dis_riscv_sign_extend(limm, 5, &s);
+
+	dis_riscv_c_regimm(dhp, table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RD(instr)], s, imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_zext_bigimmint(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint_t imm = ((instr & 0x1000) >> 7) | ((instr & 0x007c) >> 2);
+
+	dis_riscv_c_regimm(dhp, table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RD(instr)], "", imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_addi16sp(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t aimm = DIS_RISCV_C_A16_9(instr) | DIS_RISCV_C_A16_8_7(instr) |
+	    DIS_RISCV_C_A16_6(instr) | DIS_RISCV_C_A16_5(instr) |
+	    DIS_RISCV_C_A16_4(instr);
+	int imm = dis_riscv_sign_extend(aimm, 9, &s);
+
+	dis_riscv_c_regimm(dhp, table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RD(instr)], s, imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_addi4spn(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint_t imm = DIS_RISCV_C_A4_9_6(instr) | DIS_RISCV_C_A4_5_4(instr) |
+	    DIS_RISCV_C_A4_3(instr) | DIS_RISCV_C_A4_2(instr);
+
+	if ((dhp->dh_flags & DIS_OCTAL) != 0) {
+		(void) dis_snprintf(buf, buflen, "%s %s,sp,0%o",
+		    table->drv_c_name, dis_riscv_c_regs[DIS_RISCV_C_RDP(instr)],
+		    imm);
+	} else {
+		(void) dis_snprintf(buf, buflen, "%s %s,sp,0x%x",
+		    table->drv_c_name, dis_riscv_c_regs[DIS_RISCV_C_RDP(instr)],
+		    imm);
+	}
+}
+
+static void
+dis_riscv_c_immint(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	const char *s;
+	uint_t limm = ((instr & 0x1000) >> 7) | ((instr & 0x007c) >> 2);
+	uint_t imm = dis_riscv_sign_extend(limm, 5, &s);
+
+	dis_riscv_c_regimm(dhp, table->drv_c_name,
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)], s, imm, buf, buflen);
+}
+
+static void
+dis_riscv_c_zext_immint(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	uint_t imm = ((instr & 0x1000) >> 7) | ((instr & 0x007c) >> 2);
+
+	dis_riscv_c_regimm(dhp, table->drv_c_name,
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)], "", imm, buf, buflen);
+}
+
+/*ARGSUSED*/
+static void
+dis_riscv_c_bigint(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s", table->drv_c_name,
+	    dis_riscv_regs[DIS_RISCV_C_RD(instr)],
+	    dis_riscv_regs[DIS_RISCV_C_RS2(instr)]);
+}
+
+
+/*ARGSUSED*/
+static void
+dis_riscv_c_int(dis_handle_t *dhp, uint32_t instr,
+    dis_riscv_c_instr_t *table, char *buf, size_t buflen)
+{
+	(void) dis_snprintf(buf, buflen, "%s %s,%s", table->drv_c_name,
+	    dis_riscv_c_regs[DIS_RISCV_C_RS1P(instr)],
+	    dis_riscv_c_regs[DIS_RISCV_C_RS2P(instr)]);
+}
+
+#define	DIS_RISCV_CFUNCT3(name, class, op, funct, print)		\
+	{ name, DIS_RISCV_C_FUNCT3, print, class, op, funct, 0, 0 }
+#define	DIS_RISCV_CMATCH(name, class, op, funct, mask, match, print) 	\
+	{ name, DIS_RISCV_C_MATCH, print, class, op, funct, mask, match }
+
+static dis_riscv_c_instr_t dis_riscv_2byte[] = {
+	/* Quadrant 0 */
+	DIS_RISCV_CFUNCT3("c.addi4spn", DIS_RISCV_CL_32_64, 0x0, 0x0,
+	    dis_riscv_c_addi4spn),
+	DIS_RISCV_CFUNCT3("c.fld", DIS_RISCV_CL_32_64, 0x0, 0x01,
+	    dis_riscv_c_fld),
+	DIS_RISCV_CFUNCT3("c.lw", DIS_RISCV_CL_ALL, 0x0, 0x2,
+	    dis_riscv_c_lw),
+	DIS_RISCV_CFUNCT3("c.flw", DIS_RISCV_CL_32, 0x0, 0x3,
+	    dis_riscv_c_flw),
+	DIS_RISCV_CFUNCT3("f.ld", DIS_RISCV_CL_64_128, 0x0, 0x3,
+	    dis_riscv_c_ld),
+	DIS_RISCV_CFUNCT3("c.fsd", DIS_RISCV_CL_32_64, 0x0, 0x5,
+	    dis_riscv_c_fld),
+	DIS_RISCV_CFUNCT3("c.sw", DIS_RISCV_CL_ALL, 0x0, 0x6,
+	    dis_riscv_c_lw),
+	DIS_RISCV_CFUNCT3("c.fsw", DIS_RISCV_CL_32, 0x0, 0x7,
+	    dis_riscv_c_flw),
+	DIS_RISCV_CFUNCT3("c.sd", DIS_RISCV_CL_64_128, 0x0, 0x7,
+	    dis_riscv_c_ld),
+	/* Quadrant 1 */
+	DIS_RISCV_CMATCH("c.nop", DIS_RISCV_CL_ALL, 0x01, 0x00, 0x1ffc, 0x0,
+	    dis_riscv_c_name),
+	DIS_RISCV_CFUNCT3("c.addi", DIS_RISCV_CL_ALL, 0x01, 0x00,
+	    dis_riscv_c_bigimmint),
+	DIS_RISCV_CFUNCT3("c.jal", DIS_RISCV_CL_32, 0x01, 0x01,
+	    dis_riscv_c_j),
+	DIS_RISCV_CFUNCT3("c.addiw", DIS_RISCV_CL_64_128, 0x01, 0x01,
+	    dis_riscv_c_bigimmint),
+	DIS_RISCV_CFUNCT3("c.li", DIS_RISCV_CL_ALL, 0x01, 0x02,
+	    dis_riscv_c_bigimmint),
+	DIS_RISCV_CMATCH("c.addi16sp", DIS_RISCV_CL_ALL, 0x01, 0x03, 0x0f80,
+	    0x0100, dis_riscv_c_addi16sp),
+	DIS_RISCV_CFUNCT3("c.lui", DIS_RISCV_CL_ALL, 0x01, 0x03,
+	    dis_riscv_c_zext_bigimmint),
+	DIS_RISCV_CMATCH("c.srli", DIS_RISCV_CL_ALL, 0x1, 0x4, 0x0c00, 0x0000,
+	    dis_riscv_c_zext_immint),
+	DIS_RISCV_CMATCH("c.srai", DIS_RISCV_CL_ALL, 0x1, 0x4, 0x0c00, 0x0400,
+	    dis_riscv_c_zext_immint),
+	DIS_RISCV_CMATCH("c.andi", DIS_RISCV_CL_ALL, 0x1, 0x4, 0x0c00, 0x0800,
+	    dis_riscv_c_immint),
+	DIS_RISCV_CMATCH("c.sub", DIS_RISCV_CL_ALL, 0x1, 0x4, 0x1c60, 0x0c00,
+	    dis_riscv_c_int),
+	DIS_RISCV_CMATCH("c.xor", DIS_RISCV_CL_ALL, 0x1, 0x4, 0x1c60, 0x0c20,
+	    dis_riscv_c_int),
+	DIS_RISCV_CMATCH("c.or", DIS_RISCV_CL_ALL, 0x1, 0x4, 0x1c60, 0x0c40,
+	    dis_riscv_c_int),
+	DIS_RISCV_CMATCH("c.and", DIS_RISCV_CL_ALL, 0x1, 0x4, 0x1c60, 0x0c60,
+	    dis_riscv_c_int),
+	DIS_RISCV_CMATCH("c.subw", DIS_RISCV_CL_64_128, 0x1, 0x4, 0x1c60,
+	    0x1c00, dis_riscv_c_int),
+	DIS_RISCV_CMATCH("c.addw", DIS_RISCV_CL_64_128, 0x1, 0x4, 0x1c60,
+	    0x1c20, dis_riscv_c_int),
+	DIS_RISCV_CFUNCT3("c.j", DIS_RISCV_CL_ALL, 0x1, 0x5,
+	    dis_riscv_c_j),
+	DIS_RISCV_CFUNCT3("c.beqz", DIS_RISCV_CL_ALL, 0x1, 0x6,
+	    dis_riscv_c_branch),
+	DIS_RISCV_CFUNCT3("c.bnez", DIS_RISCV_CL_ALL, 0x1, 0x7,
+	    dis_riscv_c_branch),
+	/* Quadrant 2 */
+	DIS_RISCV_CFUNCT3("c.slli", DIS_RISCV_CL_ALL, 0x2, 0x0,
+	    dis_riscv_c_zext_bigimmint),
+	DIS_RISCV_CFUNCT3("c.fldsp", DIS_RISCV_CL_32_64, 0x2, 0x1,
+	    dis_riscv_c_fldsp),
+	DIS_RISCV_CFUNCT3("c.lwsp", DIS_RISCV_CL_ALL, 0x2, 0x2,
+	    dis_riscv_c_lwsp),
+	DIS_RISCV_CFUNCT3("c.flwsp", DIS_RISCV_CL_32, 0x2, 0x3,
+	    dis_riscv_c_flwsp),
+	DIS_RISCV_CFUNCT3("c.ldsp", DIS_RISCV_CL_64_128, 0x2, 0x3,
+	    dis_riscv_c_ldsp),
+	DIS_RISCV_CMATCH("c.jr", DIS_RISCV_CL_ALL, 0x2, 0x4, 0x107c, 0x0,
+	    dis_riscv_c_jr),
+	DIS_RISCV_CMATCH("c.mv", DIS_RISCV_CL_ALL, 0x2, 0x4, 0x1000, 0x0,
+	    dis_riscv_c_bigint),
+	DIS_RISCV_CMATCH("c.ebreak", DIS_RISCV_CL_ALL, 0x2, 0x4, 0x1ffc, 0x1000,
+	    dis_riscv_c_name),
+	DIS_RISCV_CMATCH("c.jalr", DIS_RISCV_CL_ALL, 0x2, 0x4, 0x107c, 0x1000,
+	    dis_riscv_c_jr),
+	DIS_RISCV_CMATCH("c.add", DIS_RISCV_CL_ALL, 0x2, 0x4, 0x1000, 0x1000,
+	    dis_riscv_c_bigint),
+	DIS_RISCV_CFUNCT3("c.fsdsp", DIS_RISCV_CL_32_64, 0x2, 0x5,
+	    dis_riscv_c_fsdsp),
+	DIS_RISCV_CFUNCT3("c.swsp", DIS_RISCV_CL_ALL, 0x2, 0x6,
+	    dis_riscv_c_swsp),
+	DIS_RISCV_CFUNCT3("c.fswsp", DIS_RISCV_CL_32, 0x2, 0x7,
+	    dis_riscv_c_fswsp),
+	DIS_RISCV_CFUNCT3("c.sdsp", DIS_RISCV_CL_64_128, 0x2, 0x7,
+	    dis_riscv_c_sdsp),
+};
+
+static void
+dis_riscv_decode_2byte(dis_handle_t *dhp, uint32_t instr, char *buf,
+    size_t buflen)
+{
+	uint_t i;
+
+	for (i = 0; i < ARRAY_SIZE(dis_riscv_2byte); i++) {
+		dis_riscv_c_instr_t *t = &dis_riscv_2byte[i];
+		switch (t->drv_c_class) {
+		case DIS_RISCV_CL_ALL:
+			break;
+		case DIS_RISCV_CL_32:
+			if ((dhp->dh_flags & DIS_RISCV_32) == 0)
+				continue;
+			break;
+		case DIS_RISCV_CL_64:
+			if ((dhp->dh_flags & DIS_RISCV_64) == 0)
+				continue;
+			break;
+		case DIS_RISCV_CL_32_64:
+			if ((dhp->dh_flags &
+			    (DIS_RISCV_32 | DIS_RISCV_64)) == 0) {
+				continue;
+			}
+			break;
+		case DIS_RISCV_CL_64_128:
+			if ((dhp->dh_flags & DIS_RISCV_64) == 0)
+				continue;
+			break;
+		}
+
+		switch (t->drv_c_type) {
+		case DIS_RISCV_C_FUNCT3:
+			if (DIS_RISCV_C_OPCODE(instr) == t->drv_c_opcode &&
+			    DIS_RISCV_C_FUNCT3(instr) == t->drv_c_funct) {
+				break;
+			}
+			continue;
+		case DIS_RISCV_C_MATCH:
+			if (DIS_RISCV_C_OPCODE(instr) == t->drv_c_opcode &&
+			    DIS_RISCV_C_FUNCT3(instr) == t->drv_c_funct &&
+			    ((instr & t->drv_c_mask) == t->drv_c_match)) {
+				break;
+			}
+			continue;
+		default:
+			continue;
+		}
+
+		t->drv_c_print(dhp, instr, t, buf, buflen);
+		return;
+	}
+
+	(void) dis_snprintf(buf, buflen, "<unknown>");
+}
+
+
+/*
+ * RISC-V instructions always come in parcels of two bytes. Read the next two
+ * byte parcel and advance the address in the handle. Also, take care of endian
+ * issues if required.
+ */
+static int
+dis_riscv_read_parcel(dis_handle_t *dhp, uint16_t *valp)
+{
+	if ((dhp->dh_addr % 2) != 0)
+		return (-1);
+
+	if (dhp->dh_read(dhp->dh_data, dhp->dh_addr, valp, sizeof (*valp)) !=
+	    sizeof (*valp))
+		return (-1);
+
+	*valp = LE_16(*valp);
+
+	dhp->dh_addr += 2;
+
+	return (0);
+}
+
+/*
+ * The first 'parcel' (uint16_t) of any instruction can be used to determine the
+ * instruction length. This is derived from Section 1.2 Instruction Length
+ * Encoding of Volume I: RISC-V User-Level ISA V2.2.
+ *
+ *  | xxxxxxxxxxxxxxaa | 16-bit iff aa != 11
+ *  | xxxxxxxxxxxbbb11 | 32-bit iff bbb != 111
+ *  | xxxxxxxxxx011111 | 48-bit iff bbb != 111
+ *  | xxxxxxxxx0111111 | 64-bit iff bbb != 111
+ *  | xnnnxxxxx1111111 | (80 + 16*nnn)-bit iff nnn != 111
+ */
+#define	RISCV_LEN_16_MASK	0x0003
+#define	RISCV_LEN_32_MASK	0x001c
+#define	RISCV_LEN_48_MASK	0x0020
+#define	RISCV_LEN_64_MASK	0x0040
+#define	RISCV_LEN_80_MASK	0x7000
+#define	RISCV_LEN_80_SHIFT	12
+
+static int
+dis_riscv_decode_len(uint16_t instr)
+{
+	if ((instr & RISCV_LEN_16_MASK) != RISCV_LEN_16_MASK)
+		return (2);
+
+	if ((instr & RISCV_LEN_32_MASK) != RISCV_LEN_32_MASK)
+		return (4);
+
+	if ((instr & RISCV_LEN_48_MASK) != RISCV_LEN_48_MASK)
+		return (6);
+
+	if ((instr & RISCV_LEN_64_MASK) != RISCV_LEN_64_MASK)
+		return (8);
+
+	if ((instr & RISCV_LEN_80_MASK) != RISCV_LEN_80_MASK) {
+		uint_t factor = (instr & RISCV_LEN_80_MASK) >>
+		    RISCV_LEN_80_SHIFT;
+		return ((10 + 2 * factor));
+	}
+
+	return (-1);
+}
+
+static int
+dis_riscv_supports_flags(int flags)
+{
+	int archflags = flags & DIS_ARCH_MASK;
+
+	return (archflags == DIS_RISCV_32 || archflags == DIS_RISCV_64);
+}
+
+static int
+dis_riscv_disassemble(dis_handle_t *dhp, uint64_t addr, char *buf,
+    size_t buflen)
+{
+	int len;
+	uint16_t parcel;
+	uint32_t instr;
+
+
+	dhp->dh_addr = addr;
+
+	/*
+	 * All instructions have to be 2-byte aligned. Most have to be four byte
+	 * aligned, but we determine that after we decode the instruction size.
+	 * The 2-byte alignment check is done when we read the parcel.
+	 */
+	if (dis_riscv_read_parcel(dhp, &parcel) != 0)
+		return (-1);
+
+	len = dis_riscv_decode_len(parcel);
+	if (len < 2 || (len % 2) != 0)
+		return (-1);
+	switch (len) {
+	case 2:
+		instr = parcel;
+		dis_riscv_decode_2byte(dhp, instr, buf, buflen);
+		break;
+	case 4:
+		instr = parcel;
+		if (dis_riscv_read_parcel(dhp, &parcel) != 0)
+			return (-1);
+		instr |= parcel << 16;
+		dis_riscv_decode_4byte(dhp, instr, buf, buflen);
+		break;
+	default:
+		/*
+		 * This case represents a valid instruction length, but
+		 * something we don't understand. Treat this as an unknown
+		 * instruction. However, read the rest of the length of the
+		 * instruction to make sure that we read things correctly.
+		 */
+		(void) dis_snprintf(buf, buflen, "<unknown>");
+		for (; len > 0; len -= 2) {
+			if (dis_riscv_read_parcel(dhp, &parcel) != 0) {
+				return (-1);
+			}
+		}
+		break;
+	}
+
+	return (0);
+}
+
+/*ARGSUSED*/
+static int
+dis_riscv_min_instrlen(dis_handle_t *dhp)
+{
+	return (2);
+}
+
+/*ARGSUSED*/
+static int
+dis_riscv_max_instrlen(dis_handle_t *dhp)
+{
+	return (22);
+}
+
+static int
+dis_riscv_instrlen(dis_handle_t *dhp, uint64_t addr)
+{
+	int ret;
+	uint16_t parcel;
+
+	dhp->dh_addr = addr;
+
+	if (dis_riscv_read_parcel(dhp, &parcel) != 0)
+		return (-1);
+
+	/*
+	 * Get length based on this parcel. Check for required alignment. 2-byte
+	 * alignment was already taken care of when we read the parcel.
+	 */
+	ret = dis_riscv_decode_len(parcel);
+	if (ret >= 4 && (addr % 4) != 0)
+		return (-1);
+
+	return (ret);
+}
+
+dis_arch_t dis_arch_riscv = {
+	.da_supports_flags = dis_riscv_supports_flags,
+	.da_disassemble = dis_riscv_disassemble,
+	.da_min_instrlen = dis_riscv_min_instrlen,
+	.da_max_instrlen = dis_riscv_max_instrlen,
+	.da_instrlen = dis_riscv_instrlen
+};
diff --git a/usr/src/lib/libdisasm/common/libdisasm.c b/usr/src/lib/libdisasm/common/libdisasm.c
index 97e64c8..7e5f545 100644
--- a/usr/src/lib/libdisasm/common/libdisasm.c
+++ b/usr/src/lib/libdisasm/common/libdisasm.c
@@ -24,6 +24,7 @@
  * Use is subject to license terms.
  * Copyright 2012 Joshua M. Clulow <josh@sysmgr.org>
  * Copyright 2015 Nexenta Systems, Inc.  All rights reserved.
+ * Copyright 2018, Joyent, Inc.
  */
 
 #include <libdisasm.h>
@@ -55,6 +56,9 @@
 #if !defined(DIS_STANDALONE) || defined(__s390) || defined(__s390x)
 extern dis_arch_t dis_arch_s390;
 #endif
+#if !defined(DIS_STANDALONE) || defined(__riscv)
+extern dis_arch_t dis_arch_riscv;
+#endif
 
 static dis_arch_t *dis_archs[] = {
 #if !defined(DIS_STANDALONE) || defined(__i386) || defined(__amd64)
@@ -66,6 +70,9 @@
 #if !defined(DIS_STANDALONE) || defined(__s390) || defined(__s390x)
 	&dis_arch_s390,
 #endif
+#if !defined(DIS_STANDALONE) || defined(__riscv)
+	&dis_arch_riscv,
+#endif
 	NULL
 };
 
diff --git a/usr/src/lib/libdisasm/common/libdisasm.h b/usr/src/lib/libdisasm/common/libdisasm.h
index 7c35db4..374daf4 100644
--- a/usr/src/lib/libdisasm/common/libdisasm.h
+++ b/usr/src/lib/libdisasm/common/libdisasm.h
@@ -24,6 +24,7 @@
  * Use is subject to license terms.
  * Copyright 2012 Joshua M. Clulow <josh@sysmgr.org>
  * Copyright 2015 Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
+ * Copyright 2018, Joyent, Inc.
  */
 
 #ifndef	_LIBDISASM_H
@@ -55,6 +56,10 @@
 #define	DIS_S390_31		0x400
 #define	DIS_S390_64		0x800
 
+/* risc-v disassembler flags */
+#define	DIS_RISCV_32		0x2000
+#define	DIS_RISCV_64		0x4000
+
 /* generic disassembler flags */
 #define	DIS_OCTAL		0x040
 #define	DIS_NOIMMSYM		0x080
@@ -62,7 +67,8 @@
 #define	DIS_ARCH_MASK		(DIS_SPARC_V8 | \
 		DIS_SPARC_V9 | DIS_SPARC_V9_SGI | DIS_SPARC_V9_OPL | \
 		DIS_X86_SIZE16 | DIS_X86_SIZE32 | DIS_X86_SIZE64 | \
-		DIS_S370 | DIS_S390_31 | DIS_S390_64)
+		DIS_S370 | DIS_S390_31 | DIS_S390_64 | DIS_RISCV_32 | \
+		DIS_RISCV_64)
 
 typedef int (*dis_lookup_f)(void *, uint64_t, char *, size_t, uint64_t *,
     size_t *);
diff --git a/usr/src/pkg/manifests/system-test-utiltest.mf b/usr/src/pkg/manifests/system-test-utiltest.mf
index 714efb2..5d32bf8 100644
--- a/usr/src/pkg/manifests/system-test-utiltest.mf
+++ b/usr/src/pkg/manifests/system-test-utiltest.mf
@@ -28,6 +28,8 @@
 dir path=opt/util-tests/tests
 dir path=opt/util-tests/tests/dis
 dir path=opt/util-tests/tests/dis/i386
+dir path=opt/util-tests/tests/dis/risc-v
+dir path=opt/util-tests/tests/dis/risc-v-c
 dir path=opt/util-tests/tests/dis/sparc
 dir path=opt/util-tests/tests/files
 dir path=opt/util-tests/tests/libnvpair_json
@@ -39,124 +41,168 @@
 file path=opt/util-tests/tests/allowed-ips mode=0555
 file path=opt/util-tests/tests/date_test mode=0555
 file path=opt/util-tests/tests/dis/distest mode=0555
-file path=opt/util-tests/tests/dis/i386/32.adx.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.adx.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.aes.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.aes.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.avx.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.avx.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.avx2.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.avx2.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.avx512.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.avx512.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.bmi1.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.bmi1.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.bmi2.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.bmi2.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.f16c.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.f16c.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-pd.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-pd.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-ps.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-ps.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-sd.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-sd.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-ss.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.fma-ss.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.lzcnt.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.lzcnt.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.movbe.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.movbe.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.opmask.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.opmask.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.pclmulqdq.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.pclmulqdq.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.popcnt.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.popcnt.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sha.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sha.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sse-3.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sse-3.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sse-4.1.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sse-4.1.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sse-4.2.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.sse-4.2.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.ssse3.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.ssse3.s mode=0555
-file path=opt/util-tests/tests/dis/i386/32.xsave.out mode=0555
-file path=opt/util-tests/tests/dis/i386/32.xsave.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.adx.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.adx.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.aes.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.aes.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.avx.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.avx.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.avx2.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.avx2.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.avx512.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.avx512.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.bmi1.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.bmi1.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.bmi2.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.bmi2.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.ept.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.ept.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.f16c.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.f16c.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-pd.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-pd.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-ps.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-ps.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-sd.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-sd.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-ss.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.fma-ss.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.lzcnt.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.lzcnt.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.movbe.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.movbe.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.opmask.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.opmask.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.pclmulqdq.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.pclmulqdq.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.popcnt.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.popcnt.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.random.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.random.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sha.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sha.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sse-3.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sse-3.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sse-4.1.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sse-4.1.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sse-4.2.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.sse-4.2.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.ssse3.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.ssse3.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.vmx.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.vmx.s mode=0555
-file path=opt/util-tests/tests/dis/i386/64.xsave.out mode=0555
-file path=opt/util-tests/tests/dis/i386/64.xsave.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.cpuid.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.cpuid.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.fence.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.fence.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.msr.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.msr.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.mwait.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.mwait.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.random.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.random.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.sep.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.sep.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.smap.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.smap.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.tsc.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.tsc.s mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.vmx.out mode=0555
-file path=opt/util-tests/tests/dis/i386/tst.vmx.s mode=0555
-file path=opt/util-tests/tests/dis/sparc/tst.regs.out mode=0555
-file path=opt/util-tests/tests/dis/sparc/tst.regs.s mode=0555
+file path=opt/util-tests/tests/dis/i386/32.adx.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.adx.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.aes.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.aes.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx2-gather.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx2-gather.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx2.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx2.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx512.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.avx512.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.bmi1.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.bmi1.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.bmi2.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.bmi2.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.f16c.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.f16c.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-pd.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-pd.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-ps.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-ps.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-sd.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-sd.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-ss.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.fma-ss.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.lzcnt.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.lzcnt.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.movbe.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.movbe.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.opmask.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.opmask.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.pclmulqdq.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.pclmulqdq.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.popcnt.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.popcnt.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sha.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sha.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sse-3.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sse-3.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sse-4.1.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sse-4.1.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sse-4.2.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.sse-4.2.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.ssse3.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.ssse3.s mode=0444
+file path=opt/util-tests/tests/dis/i386/32.xsave.out mode=0444
+file path=opt/util-tests/tests/dis/i386/32.xsave.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.adx.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.adx.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.aes.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.aes.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx2-gather.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx2-gather.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx2.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx2.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx512.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.avx512.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.bmi1.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.bmi1.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.bmi2.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.bmi2.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.ept.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.ept.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.f16c.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.f16c.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-pd.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-pd.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-ps.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-ps.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-sd.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-sd.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-ss.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.fma-ss.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.lzcnt.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.lzcnt.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.movbe.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.movbe.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.opmask.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.opmask.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.pclmulqdq.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.pclmulqdq.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.popcnt.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.popcnt.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.random.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.random.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sha.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sha.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sse-3.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sse-3.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sse-4.1.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sse-4.1.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sse-4.2.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.sse-4.2.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.ssse3.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.ssse3.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.vmx.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.vmx.s mode=0444
+file path=opt/util-tests/tests/dis/i386/64.xsave.out mode=0444
+file path=opt/util-tests/tests/dis/i386/64.xsave.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.cpuid.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.cpuid.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.fence.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.fence.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.msr.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.msr.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.mwait.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.mwait.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.random.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.random.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.sep.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.sep.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.smap.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.smap.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.tsc.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.tsc.s mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.vmx.out mode=0444
+file path=opt/util-tests/tests/dis/i386/tst.vmx.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/32.ldsr.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/32.ldsr.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/64.int.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/64.int.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/64.ldsr.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/64.ldsr.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/tst.int.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/tst.int.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/tst.ldsr.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v-c/tst.ldsr.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64a.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64a.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64d.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64d.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64f.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64f.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64i.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64i.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64m.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/64.rv64m.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.csr.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.csr.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.fpregs.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.fpregs.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.pseudo.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.pseudo.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.regs.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.regs.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32a.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32a.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32d.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32d.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32f.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32f.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32i.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32i.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32m.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.rv32m.s mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.supervisor.out mode=0444
+file path=opt/util-tests/tests/dis/risc-v/tst.supervisor.s mode=0444
+file path=opt/util-tests/tests/dis/sparc/tst.regs.out mode=0444
+file path=opt/util-tests/tests/dis/sparc/tst.regs.s mode=0444
 file path=opt/util-tests/tests/files/gout0 mode=0444
 file path=opt/util-tests/tests/files/gout1 mode=0444
 file path=opt/util-tests/tests/files/gout10 mode=0444
diff --git a/usr/src/test/util-tests/tests/dis/Makefile b/usr/src/test/util-tests/tests/dis/Makefile
index 53cf7cc..3c4c8a5 100644
--- a/usr/src/test/util-tests/tests/dis/Makefile
+++ b/usr/src/test/util-tests/tests/dis/Makefile
@@ -10,94 +10,37 @@
 #
 
 #
-# Copyright 2017 Joyent, Inc.
+# Copyright 2018 Joyent, Inc.
 #
 
 include $(SRC)/Makefile.master
 
 ROOTOPTPKG = $(ROOT)/opt/util-tests
 TESTDIR = $(ROOTOPTPKG)/tests/dis
-ARCHS = i386 sparc
+ARCHS = i386 risc-v risc-v-c sparc
 
 PROG = distest
 
-SPARC_TESTS = \
-	tst.regs
+I386_FILES :sh= (cd i386; print *)
+RISCV_FILES :sh= (cd risc-v; print *)
+RISCV_C_FILES :sh= (cd risc-v-c; print *)
+SPARC_FILES :sh= (cd sparc; print *)
 
-I386_TESTS =		\
-	32.adx 		\
-	32.avx		\
-	32.avx2		\
-	32.avx512	\
-	32.aes 		\
-	32.bmi1 	\
-	32.bmi2 	\
-	32.f16c 	\
-	32.fma-pd 	\
-	32.fma-ps 	\
-	32.fma-sd 	\
-	32.fma-ss 	\
-	32.lzcnt 	\
-	32.movbe	\
-	32.opmask	\
-	32.pclmulqdq	\
-	32.popcnt 	\
-	32.sha		\
-	32.sse-3	\
-	32.sse-4.1 	\
-	32.sse-4.2 	\
-	32.ssse3 	\
-	32.xsave 	\
-	64.avx		\
-	64.avx2		\
-	64.avx512	\
-	64.adx 		\
-	64.aes 		\
-	64.bmi1 	\
-	64.bmi2 	\
-	64.ept 		\
-	64.f16c 	\
-	64.fma-pd 	\
-	64.fma-ps 	\
-	64.fma-sd 	\
-	64.fma-ss 	\
-	64.lzcnt 	\
-	64.movbe	\
-	64.opmask	\
-	64.pclmulqdq	\
-	64.popcnt 	\
-	64.random 	\
-	64.sha		\
-	64.sse-3	\
-	64.sse-4.1 	\
-	64.sse-4.2 	\
-	64.ssse3 	\
-	64.vmx 		\
-	64.xsave 	\
-	tst.cpuid	\
-	tst.fence	\
-	tst.msr		\
-	tst.mwait 	\
-	tst.random	\
-	tst.smap	\
-	tst.sep		\
-	tst.tsc		\
-	tst.vmx
-
-I386_FILES = $(I386_TESTS:%=%.s) $(I386_TESTS:%=%.out)
-ROOTI386 = $(I386_FILES:%=$(TESTDIR)/i386/%)
-
-SPARC_FILES = $(SPARC_TESTS:%=%.s) $(SPARC_TESTS:%=%.out)
-ROOTSPARC = $(SPARC_FILES:%=$(TESTDIR)/sparc/%)
+ROOTFILES = \
+	$(I386_FILES:%=$(TESTDIR)/i386/%)		\
+	$(RISCV_FILES:%=$(TESTDIR)/risc-v/%)		\
+	$(RISCV_C_FILES:%=$(TESTDIR)/risc-v-c/%)	\
+	$(SPARC_FILES:%=$(TESTDIR)/sparc/%)
 
 include $(SRC)/cmd/Makefile.cmd
 include $(SRC)/test/Makefile.com
 
 ARCHDIRS = $(ARCHS:%=$(TESTDIR)/%)
 CMDS = $(PROG:%=$(TESTDIR)/%)
+FILEMODE=0444
 $(CMDS) := FILEMODE = 0555
 
-install: $(CMDS) $(ROOTI386) $(ROOTSPARC)
+install: $(CMDS) $(ROOTFILES)
 
 lint:
 
@@ -105,7 +48,7 @@
 
 clean:
 
-$(CMDS) $(ROOTI386) $(ROOTSPARC): $(TESTDIR) $(ARCHDIRS)
+$(CMDS) $(ROOTFILES): $(TESTDIR) $(ARCHDIRS)
 
 $(TESTDIR) $(ARCHDIRS):
 	$(INS.dir)
diff --git a/usr/src/test/util-tests/tests/dis/distest.ksh b/usr/src/test/util-tests/tests/dis/distest.ksh
index 21b39a6..37a5dd2 100644
--- a/usr/src/test/util-tests/tests/dis/distest.ksh
+++ b/usr/src/test/util-tests/tests/dis/distest.ksh
@@ -11,7 +11,7 @@
 #
 
 #
-# Copyright 2016 Joyent, Inc.
+# Copyright 2018 Joyent, Inc.
 #
 
 #
@@ -78,6 +78,7 @@
 				either be an absolute path or a command on the
 				path.
 USAGE
+	exit 2
 }
 
 #
@@ -196,6 +197,7 @@
 run_single_file()
 {
 	typeset sfile base cmpfile prefix arch gas p flags
+	typeset asflags32 asflags64
 	sfile=$1
 
 	base=${sfile##*/}
@@ -207,16 +209,31 @@
 	gas=${dt_platforms[$arch]}
 	[[ -n $gas ]] || fatal "encountered test $sfile, but missing assembler"
 
+	case "$arch" in
+	"risc-v")
+		asflags32="-march=rv32g"
+		asflags64="-march=rv64g"
+		;;
+	"risc-v-c")
+		asflags32="-march=rv32gc"
+		asflags64="-march=rv64gc"
+		;;
+	*)
+		asflags32="-32"
+		asflags64="-64"
+		;;
+	esac
+
 	case "$prefix" in
 	32)
-		test_one "-32" $sfile $cmpfile
+		test_one $asflags32 $sfile $cmpfile
 		;;
 	64)
-		test_one "-64" $sfile $cmpfile
+		test_one $asflags64 $sfile $cmpfile
 		;;
 	tst)
-		test_one "-32" $sfile $cmpfile "(32-bit)"
-		test_one "-64" $sfile $cmpfile "(64-bit)"
+		test_one $asflags32 $sfile $cmpfile "(32-bit)"
+		test_one $asflags64 $sfile $cmpfile "(64-bit)"
 		;;
 	esac
 }
@@ -270,9 +287,10 @@
 		dt_nodefault="y"
 		;;
 	p)
+		OLDIFS=$IFS
 		IFS="="
 		set -A split $OPTARG
-		IFS=" "
+		IFS=$OLDIFS
 		[[ ${#split[@]} -eq 2 ]] || usage "malformed -p option: $OPTARG"
 		dt_platforms[${split[0]}]=${split[1]}
 		;;
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/32.ldsr.out b/usr/src/test/util-tests/tests/dis/risc-v-c/32.ldsr.out
new file mode 100644
index 0000000..cfd34d3
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/32.ldsr.out
@@ -0,0 +1,7 @@
+    libdis_test:     04 61              c.flw fs1,0x0(a0)
+    libdis_test+0x2: b4 62              c.flw fa3,0x40(a3)
+    libdis_test+0x4: 82 64              c.flwsp fs1,0x0(sp)
+    libdis_test+0x6: 06 6e              c.flwsp ft8,0x40(sp)
+    libdis_test+0x8: d2 77              c.flwsp fa5,0x34(sp)
+    libdis_test+0xa: 0a e0              c.fswsp ft2,0x0(sp)
+    libdis_test+0xc: 36 f0              c.fswsp fa3,0x20(sp)
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/32.ldsr.s b/usr/src/test/util-tests/tests/dis/risc-v-c/32.ldsr.s
new file mode 100644
index 0000000..75959ea
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/32.ldsr.s
@@ -0,0 +1,32 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test RV32C-specific loads and stores.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	c.flw	fs1,(a0)
+	c.flw	fa3,0x40(a3)
+	c.flwsp	fs1,(sp)
+	c.flwsp	ft8,0x40(sp)
+	c.flwsp	fa5,0x34(sp)
+	c.fswsp	ft2,(sp)
+	c.fswsp	fa3,0x20(sp)
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/64.int.out b/usr/src/test/util-tests/tests/dis/risc-v-c/64.int.out
new file mode 100644
index 0000000..4c7abf7
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/64.int.out
@@ -0,0 +1,5 @@
+    libdis_test:     fd 24              c.addiw s1,0x1f
+    libdis_test+0x2: 8d 24              c.addiw s1,0x3
+    libdis_test+0x4: 81 34              c.addiw s1,-0x20
+    libdis_test+0x6: b1 9d              c.addw a1,a2
+    libdis_test+0x8: 15 9c              c.subw s0,a3
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/64.int.s b/usr/src/test/util-tests/tests/dis/risc-v-c/64.int.s
new file mode 100644
index 0000000..25a19b1
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/64.int.s
@@ -0,0 +1,30 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test RV64C-specific integer instructions
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	c.addiw	s1, 0x1f
+	c.addiw	s1, 0x3
+	c.addiw	s1, -0x20
+	c.addw	a1, a2
+	c.subw	s0, a3
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/64.ldsr.out b/usr/src/test/util-tests/tests/dis/risc-v-c/64.ldsr.out
new file mode 100644
index 0000000..af6302d
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/64.ldsr.out
@@ -0,0 +1,10 @@
+    libdis_test:      82 64              c.ldsp s1,0x0(sp)
+    libdis_test+0x2:  06 67              c.ldsp a4,0x40(sp)
+    libdis_test+0x4:  62 7e              c.ldsp t3,0x38(sp)
+    libdis_test+0x6:  82 24              c.fldsp fs1,0x0(sp)
+    libdis_test+0x8:  06 2e              c.fldsp ft8,0x40(sp)
+    libdis_test+0xa:  e2 37              c.fldsp fa5,0x38(sp)
+    libdis_test+0xc:  76 e0              c.sdsp t4,0x0(sp)
+    libdis_test+0xe:  12 f0              c.sdsp tp,0x20(sp)
+    libdis_test+0x10: 0a a0              c.fsdsp ft2,0x0(sp)
+    libdis_test+0x12: 36 b0              c.fsdsp fa3,0x20(sp)
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/64.ldsr.s b/usr/src/test/util-tests/tests/dis/risc-v-c/64.ldsr.s
new file mode 100644
index 0000000..95cccda
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/64.ldsr.s
@@ -0,0 +1,35 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test RV64C-specific loads and stores.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	c.ldsp	s1,(sp)
+	c.ldsp	a4,0x40(sp)
+	c.ldsp	t3,0x38(sp)
+	c.fldsp	fs1,(sp)
+	c.fldsp	ft8,0x40(sp)
+	c.fldsp	fa5,0x38(sp)
+	c.sdsp	t4,(sp)
+	c.sdsp	tp,0x20(sp)
+	c.fsdsp	ft2,(sp)
+	c.fsdsp	fa3,0x20(sp)
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/tst.int.out b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.int.out
new file mode 100644
index 0000000..a6a4802
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.int.out
@@ -0,0 +1,30 @@
+    libdis_test:      d5 40              c.li ra,0x15
+    libdis_test+0x2:  b5 5d              c.li s11,-0x13
+    libdis_test+0x4:  89 64              c.lui s1,0x2
+    libdis_test+0x6:  cd 64              c.lui s1,0x13
+    libdis_test+0x8:  fd 04              c.addi s1,0x1f
+    libdis_test+0xa:  8d 04              c.addi s1,0x3
+    libdis_test+0xc:  81 14              c.addi s1,-0x20
+    libdis_test+0xe:  45 61              c.addi16sp sp,0x30
+    libdis_test+0x10: 39 71              c.addi16sp sp,-0x40
+    libdis_test+0x12: 0c 08              c.addi4spn a1,sp,0x10
+    libdis_test+0x14: 6c 10              c.addi4spn a1,sp,0x2c
+    libdis_test+0x16: 16 0d              c.slli s10,0x5
+    libdis_test+0x18: ce 0e              c.slli t4,0x13
+    libdis_test+0x1a: 0a 04              c.slli s0,0x2
+    libdis_test+0x1c: 11 82              c.srli a2,0x4
+    libdis_test+0x1e: d5 80              c.srli s1,0x15
+    libdis_test+0x20: 91 86              c.srai a3,0x4
+    libdis_test+0x22: e5 87              c.srai a5,0x19
+    libdis_test+0x24: 0d 8b              c.andi a4,0x3
+    libdis_test+0x26: e5 9a              c.andi a3,-0x7
+    libdis_test+0x28: ba 84              c.mv s1,a4
+    libdis_test+0x2a: 3e 85              c.mv a0,a5
+    libdis_test+0x2c: b6 95              c.add a1,a3
+    libdis_test+0x2e: 32 96              c.add a2,a2
+    libdis_test+0x30: 6d 8d              c.and a0,a1
+    libdis_test+0x32: d1 8d              c.or a1,a2
+    libdis_test+0x34: 35 8e              c.xor a2,a3
+    libdis_test+0x36: 99 8e              c.sub a3,a4
+    libdis_test+0x38: 01 00              c.nop
+    libdis_test+0x3a: 02 90              c.ebreak
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/tst.int.s b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.int.s
new file mode 100644
index 0000000..9afab25
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.int.s
@@ -0,0 +1,59 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test common compact integer instructions
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	c.li	ra, 0x15
+	c.li	s11, -0x13
+	c.lui	s1, 0x2
+	c.lui	s1, 0x13
+
+	c.addi	s1, 0x1f
+	c.addi	s1, 0x3
+	c.addi	s1, -0x20
+
+	c.addi16sp	sp, 0x30
+	c.addi16sp	sp, -0x40
+	c.addi4spn	a1, sp, 0x10
+	c.addi4spn	a1, sp, 0x2c
+
+	c.slli	s10, 0x5
+	c.slli	t4, 0x13
+	c.slli	s0, 0x2
+	c.srli	a2, 0x4
+	c.srli	s1, 0x15
+	c.srai	a3, 0x4
+	c.srai	a5, 0x19
+	c.andi	a4, 0x3
+	c.andi	a3, -0x7
+	c.mv	s1, a4
+	c.mv	a0, a5
+	c.add	a1, a3
+	c.add	a2, a2
+	c.and	a0, a1
+	c.or	a1, a2
+	c.xor	a2, a3
+	c.sub	a3, a4
+
+	c.nop
+	c.ebreak
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/tst.ldsr.out b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.ldsr.out
new file mode 100644
index 0000000..f69ae6d
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.ldsr.out
@@ -0,0 +1,9 @@
+    libdis_test:      82 44              c.lwsp s1,0x0(sp)
+    libdis_test+0x2:  06 47              c.lwsp a4,0x40(sp)
+    libdis_test+0x4:  52 5e              c.lwsp t3,0x34(sp)
+    libdis_test+0x6:  76 c0              c.swsp t4,0x0(sp)
+    libdis_test+0x8:  12 d0              c.swsp tp,0x20(sp)
+    libdis_test+0xa:  04 41              c.lw s1,0x0(a0)
+    libdis_test+0xc:  b0 42              c.lw a2,0x40(a3)
+    libdis_test+0xe:  04 21              c.fld fs1,0x0(a0)
+    libdis_test+0x10: b4 22              c.fld fa3,0x40(a3)
diff --git a/usr/src/test/util-tests/tests/dis/risc-v-c/tst.ldsr.s b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.ldsr.s
new file mode 100644
index 0000000..7a4ef32
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v-c/tst.ldsr.s
@@ -0,0 +1,38 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test common compact loads and stores.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	c.lwsp	s1,(sp)
+	c.lwsp	a4,0x40(sp)
+	c.lwsp	t3,0x34(sp)
+	c.swsp	t4,(sp)
+	c.swsp	tp,0x20(sp)
+	/*
+	 * gas 2.30 doesn't support using the ABI aliases. However, that's how
+	 * we disassemble these.
+	 */
+	c.lw	x9,(x10)
+	c.lw	x12,0x40(x13)
+	c.fld	fs1,(a0)
+	c.fld	fa3,0x40(a3)
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64a.out b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64a.out
new file mode 100644
index 0000000..2bb69ce
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64a.out
@@ -0,0 +1,44 @@
+    libdis_test:      2f b4 04 10        lr.d s0,(s1)
+    libdis_test+0x4:  af 34 09 14        lr.d.aq s1,(s2)
+    libdis_test+0x8:  2f b9 09 12        lr.d.rl s2,(s3)
+    libdis_test+0xc:  af 39 0a 16        lr.d.aqrl s3,(s4)
+    libdis_test+0x10: 2f b4 24 19        sc.d s0,s2,(s1)
+    libdis_test+0x14: af b4 34 1d        sc.d.aq s1,s3,(s1)
+    libdis_test+0x18: 2f b9 44 1b        sc.d.rl s2,s4,(s1)
+    libdis_test+0x1c: af b9 54 1f        sc.d.aqrl s3,s5,(s1)
+    libdis_test+0x20: af b2 63 08        amoswap.d t0,t1,(t2)
+    libdis_test+0x24: 2f 33 7e 0c        amoswap.d.aq t1,t2,(t3)
+    libdis_test+0x28: af b3 ce 0b        amoswap.d.rl t2,t3,(t4)
+    libdis_test+0x2c: 2f 3e df 0f        amoswap.d.aqrl t3,t4,(t5)
+    libdis_test+0x30: af b2 63 00        amoadd.d t0,t1,(t2)
+    libdis_test+0x34: 2f 33 7e 04        amoadd.d.aq t1,t2,(t3)
+    libdis_test+0x38: af b3 ce 03        amoadd.d.rl t2,t3,(t4)
+    libdis_test+0x3c: 2f 3e df 07        amoadd.d.aqrl t3,t4,(t5)
+    libdis_test+0x40: af b2 63 20        amoxor.d t0,t1,(t2)
+    libdis_test+0x44: 2f 33 7e 24        amoxor.d.aq t1,t2,(t3)
+    libdis_test+0x48: af b3 ce 23        amoxor.d.rl t2,t3,(t4)
+    libdis_test+0x4c: 2f 3e df 27        amoxor.d.aqrl t3,t4,(t5)
+    libdis_test+0x50: af b2 63 60        amoand.d t0,t1,(t2)
+    libdis_test+0x54: 2f 33 7e 64        amoand.d.aq t1,t2,(t3)
+    libdis_test+0x58: af b3 ce 63        amoand.d.rl t2,t3,(t4)
+    libdis_test+0x5c: 2f 3e df 67        amoand.d.aqrl t3,t4,(t5)
+    libdis_test+0x60: af b2 63 40        amoor.d t0,t1,(t2)
+    libdis_test+0x64: 2f 33 7e 44        amoor.d.aq t1,t2,(t3)
+    libdis_test+0x68: af b3 ce 43        amoor.d.rl t2,t3,(t4)
+    libdis_test+0x6c: 2f 3e df 47        amoor.d.aqrl t3,t4,(t5)
+    libdis_test+0x70: af b2 63 80        amomin.d t0,t1,(t2)
+    libdis_test+0x74: 2f 33 7e 84        amomin.d.aq t1,t2,(t3)
+    libdis_test+0x78: af b3 ce 83        amomin.d.rl t2,t3,(t4)
+    libdis_test+0x7c: 2f 3e df 87        amomin.d.aqrl t3,t4,(t5)
+    libdis_test+0x80: af b2 63 a0        amomax.d t0,t1,(t2)
+    libdis_test+0x84: 2f 33 7e a4        amomax.d.aq t1,t2,(t3)
+    libdis_test+0x88: af b3 ce a3        amomax.d.rl t2,t3,(t4)
+    libdis_test+0x8c: 2f 3e df a7        amomax.d.aqrl t3,t4,(t5)
+    libdis_test+0x90: af b2 63 c0        amominu.d t0,t1,(t2)
+    libdis_test+0x94: 2f 33 7e c4        amominu.d.aq t1,t2,(t3)
+    libdis_test+0x98: af b3 ce c3        amominu.d.rl t2,t3,(t4)
+    libdis_test+0x9c: 2f 3e df c7        amominu.d.aqrl t3,t4,(t5)
+    libdis_test+0xa0: af b2 63 e0        amomaxu.d t0,t1,(t2)
+    libdis_test+0xa4: 2f 33 7e e4        amomaxu.d.aq t1,t2,(t3)
+    libdis_test+0xa8: af b3 ce e3        amomaxu.d.rl t2,t3,(t4)
+    libdis_test+0xac: 2f 3e df e7        amomaxu.d.aqrl t3,t4,(t5)
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64a.s b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64a.s
new file mode 100644
index 0000000..02f4c4c
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64a.s
@@ -0,0 +1,70 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV64A instructions. Instructions are ordered per the
+ * ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	lr.d		s0, (s1)
+	lr.d.aq		s1, (s2)
+	lr.d.rl		s2, (s3)
+	lr.d.aqrl	s3, (s4)
+	sc.d		s0, s2, (s1)
+	sc.d.aq		s1, s3, (s1)
+	sc.d.rl		s2, s4, (s1)
+	sc.d.aqrl	s3, s5, (s1)
+	amoswap.d	t0, t1, (t2)
+	amoswap.d.aq	t1, t2, (t3)
+	amoswap.d.rl	t2, t3, (t4)
+	amoswap.d.aqrl	t3, t4, (t5)
+	amoadd.d	t0, t1, (t2)
+	amoadd.d.aq	t1, t2, (t3)
+	amoadd.d.rl	t2, t3, (t4)
+	amoadd.d.aqrl	t3, t4, (t5)
+	amoxor.d	t0, t1, (t2)
+	amoxor.d.aq	t1, t2, (t3)
+	amoxor.d.rl	t2, t3, (t4)
+	amoxor.d.aqrl	t3, t4, (t5)
+	amoand.d	t0, t1, (t2)
+	amoand.d.aq	t1, t2, (t3)
+	amoand.d.rl	t2, t3, (t4)
+	amoand.d.aqrl	t3, t4, (t5)
+	amoor.d		t0, t1, (t2)
+	amoor.d.aq	t1, t2, (t3)
+	amoor.d.rl	t2, t3, (t4)
+	amoor.d.aqrl	t3, t4, (t5)
+	amomin.d	t0, t1, (t2)
+	amomin.d.aq	t1, t2, (t3)
+	amomin.d.rl	t2, t3, (t4)
+	amomin.d.aqrl	t3, t4, (t5)
+	amomax.d	t0, t1, (t2)
+	amomax.d.aq	t1, t2, (t3)
+	amomax.d.rl	t2, t3, (t4)
+	amomax.d.aqrl	t3, t4, (t5)
+	amominu.d	t0, t1, (t2)
+	amominu.d.aq	t1, t2, (t3)
+	amominu.d.rl	t2, t3, (t4)
+	amominu.d.aqrl	t3, t4, (t5)
+	amomaxu.d	t0, t1, (t2)
+	amomaxu.d.aq	t1, t2, (t3)
+	amomaxu.d.rl	t2, t3, (t4)
+	amomaxu.d.aqrl	t3, t4, (t5)
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64d.out b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64d.out
new file mode 100644
index 0000000..3d54aff
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64d.out
@@ -0,0 +1,26 @@
+    libdis_test:      d3 f2 20 c2        fcvt.l.d t0,ft1
+    libdis_test+0x4:  53 03 21 c2        fcvt.l.d t1,ft2,rne
+    libdis_test+0x8:  d3 93 21 c2        fcvt.l.d t2,ft3,rtz
+    libdis_test+0xc:  53 2e 22 c2        fcvt.l.d t3,ft4,rdn
+    libdis_test+0x10: d3 be 22 c2        fcvt.l.d t4,ft5,rup
+    libdis_test+0x14: 53 4f 23 c2        fcvt.l.d t5,ft6,rmm
+    libdis_test+0x18: 53 73 30 c2        fcvt.lu.d t1,ft0
+    libdis_test+0x1c: d3 83 30 c2        fcvt.lu.d t2,ft1,rne
+    libdis_test+0x20: 53 1e 31 c2        fcvt.lu.d t3,ft2,rtz
+    libdis_test+0x24: d3 ae 31 c2        fcvt.lu.d t4,ft3,rdn
+    libdis_test+0x28: 53 3f 32 c2        fcvt.lu.d t5,ft4,rup
+    libdis_test+0x2c: d3 cf 32 c2        fcvt.lu.d t6,ft5,rmm
+    libdis_test+0x30: 53 8e 05 e2        fmv.x.d t3,fa1
+    libdis_test+0x34: d3 f0 22 d2        fcvt.d.l ft1,t0
+    libdis_test+0x38: 53 01 23 d2        fcvt.d.l ft2,t1,rne
+    libdis_test+0x3c: d3 91 23 d2        fcvt.d.l ft3,t2,rtz
+    libdis_test+0x40: 53 22 2e d2        fcvt.d.l ft4,t3,rdn
+    libdis_test+0x44: d3 b2 2e d2        fcvt.d.l ft5,t4,rup
+    libdis_test+0x48: 53 43 2f d2        fcvt.d.l ft6,t5,rmm
+    libdis_test+0x4c: d3 f0 32 d2        fcvt.d.lu ft1,t0
+    libdis_test+0x50: 53 01 33 d2        fcvt.d.lu ft2,t1,rne
+    libdis_test+0x54: d3 91 33 d2        fcvt.d.lu ft3,t2,rtz
+    libdis_test+0x58: 53 22 3e d2        fcvt.d.lu ft4,t3,rdn
+    libdis_test+0x5c: d3 b2 3e d2        fcvt.d.lu ft5,t4,rup
+    libdis_test+0x60: 53 43 3f d2        fcvt.d.lu ft6,t5,rmm
+    libdis_test+0x64: 53 06 0e f2        fmv.d.x fa2,t3
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64d.s b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64d.s
new file mode 100644
index 0000000..6a3c3b2
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64d.s
@@ -0,0 +1,57 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV64F instructions. Instructions are ordered per
+ * the ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	fcvt.l.d	t0, ft1
+	fcvt.l.d	t1, ft2, rne
+	fcvt.l.d	t2, ft3, rtz
+	fcvt.l.d	t3, ft4, rdn
+	fcvt.l.d	t4, ft5, rup
+	fcvt.l.d	t5, ft6, rmm
+
+	fcvt.lu.d	t1, ft0
+	fcvt.lu.d	t2, ft1, rne
+	fcvt.lu.d	t3, ft2, rtz
+	fcvt.lu.d	t4, ft3, rdn
+	fcvt.lu.d	t5, ft4, rup
+	fcvt.lu.d	t6, ft5, rmm
+
+	fmv.x.d		t3, fa1
+
+	fcvt.d.l	ft1, t0
+	fcvt.d.l	ft2, t1, rne
+	fcvt.d.l	ft3, t2, rtz
+	fcvt.d.l	ft4, t3, rdn
+	fcvt.d.l	ft5, t4, rup
+	fcvt.d.l	ft6, t5, rmm
+
+	fcvt.d.lu	ft1, t0
+	fcvt.d.lu	ft2, t1, rne
+	fcvt.d.lu	ft3, t2, rtz
+	fcvt.d.lu	ft4, t3, rdn
+	fcvt.d.lu	ft5, t4, rup
+	fcvt.d.lu	ft6, t5, rmm
+
+	fmv.d.x		fa2, t3
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64f.out b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64f.out
new file mode 100644
index 0000000..985cc1e
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64f.out
@@ -0,0 +1,24 @@
+    libdis_test:      d3 f2 20 c0        fcvt.l.s t0,ft1
+    libdis_test+0x4:  53 03 21 c0        fcvt.l.s t1,ft2,rne
+    libdis_test+0x8:  d3 93 21 c0        fcvt.l.s t2,ft3,rtz
+    libdis_test+0xc:  53 2e 22 c0        fcvt.l.s t3,ft4,rdn
+    libdis_test+0x10: d3 be 22 c0        fcvt.l.s t4,ft5,rup
+    libdis_test+0x14: 53 4f 23 c0        fcvt.l.s t5,ft6,rmm
+    libdis_test+0x18: 53 73 30 c0        fcvt.lu.s t1,ft0
+    libdis_test+0x1c: d3 83 30 c0        fcvt.lu.s t2,ft1,rne
+    libdis_test+0x20: 53 1e 31 c0        fcvt.lu.s t3,ft2,rtz
+    libdis_test+0x24: d3 ae 31 c0        fcvt.lu.s t4,ft3,rdn
+    libdis_test+0x28: 53 3f 32 c0        fcvt.lu.s t5,ft4,rup
+    libdis_test+0x2c: d3 cf 32 c0        fcvt.lu.s t6,ft5,rmm
+    libdis_test+0x30: d3 f0 22 d0        fcvt.s.l ft1,t0
+    libdis_test+0x34: 53 01 23 d0        fcvt.s.l ft2,t1,rne
+    libdis_test+0x38: d3 91 23 d0        fcvt.s.l ft3,t2,rtz
+    libdis_test+0x3c: 53 22 2e d0        fcvt.s.l ft4,t3,rdn
+    libdis_test+0x40: d3 b2 2e d0        fcvt.s.l ft5,t4,rup
+    libdis_test+0x44: 53 43 2f d0        fcvt.s.l ft6,t5,rmm
+    libdis_test+0x48: d3 f0 32 d0        fcvt.s.lu ft1,t0
+    libdis_test+0x4c: 53 01 33 d0        fcvt.s.lu ft2,t1,rne
+    libdis_test+0x50: d3 91 33 d0        fcvt.s.lu ft3,t2,rtz
+    libdis_test+0x54: 53 22 3e d0        fcvt.s.lu ft4,t3,rdn
+    libdis_test+0x58: d3 b2 3e d0        fcvt.s.lu ft5,t4,rup
+    libdis_test+0x5c: 53 43 3f d0        fcvt.s.lu ft6,t5,rmm
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64f.s b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64f.s
new file mode 100644
index 0000000..1e1418d
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64f.s
@@ -0,0 +1,53 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV64F instructions. Instructions are ordered per
+ * the ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	fcvt.l.s	t0, ft1
+	fcvt.l.s	t1, ft2, rne
+	fcvt.l.s	t2, ft3, rtz
+	fcvt.l.s	t3, ft4, rdn
+	fcvt.l.s	t4, ft5, rup
+	fcvt.l.s	t5, ft6, rmm
+
+	fcvt.lu.s	t1, ft0
+	fcvt.lu.s	t2, ft1, rne
+	fcvt.lu.s	t3, ft2, rtz
+	fcvt.lu.s	t4, ft3, rdn
+	fcvt.lu.s	t5, ft4, rup
+	fcvt.lu.s	t6, ft5, rmm
+
+	fcvt.s.l	ft1, t0
+	fcvt.s.l	ft2, t1, rne
+	fcvt.s.l	ft3, t2, rtz
+	fcvt.s.l	ft4, t3, rdn
+	fcvt.s.l	ft5, t4, rup
+	fcvt.s.l	ft6, t5, rmm
+
+	fcvt.s.lu	ft1, t0
+	fcvt.s.lu	ft2, t1, rne
+	fcvt.s.lu	ft3, t2, rtz
+	fcvt.s.lu	ft4, t3, rdn
+	fcvt.s.lu	ft5, t4, rup
+	fcvt.s.lu	ft6, t5, rmm
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64i.out b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64i.out
new file mode 100644
index 0000000..331ac70
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64i.out
@@ -0,0 +1,25 @@
+    libdis_test:      83 eb f4 7f        lwu s7,0x7ff(s1)
+    libdis_test+0x4:  03 eb 04 00        lwu s6,0x0(s1)
+    libdis_test+0x8:  83 ea 04 80        lwu s5,-0x800(s1)
+    libdis_test+0xc:  03 ba f4 7f        ld s4,0x7ff(s1)
+    libdis_test+0x10: 83 b9 04 00        ld s3,0x0(s1)
+    libdis_test+0x14: 03 b9 04 80        ld s2,-0x800(s1)
+    libdis_test+0x18: a3 3f 53 7e        sd t0,0x7ff(t1)
+    libdis_test+0x1c: 23 b0 63 00        sd t1,0x0(t2)
+    libdis_test+0x20: 23 30 7e 80        sd t2,-0x800(t3)
+    libdis_test+0x24: 13 94 24 00        slli s0,s1,0x2
+    libdis_test+0x28: 13 94 f4 03        slli s0,s1,0x3f
+    libdis_test+0x2c: 13 d4 24 00        srli s0,s1,0x2
+    libdis_test+0x30: 13 d4 f4 03        srli s0,s1,0x3f
+    libdis_test+0x34: 13 d4 24 40        srai s0,s1,0x2
+    libdis_test+0x38: 13 d4 f4 43        srai s0,s1,0x3f
+    libdis_test+0x3c: 9b 80 42 00        addiw ra,t0,0x4
+    libdis_test+0x40: 9b 80 c2 ff        addiw ra,t0,-0x4
+    libdis_test+0x44: 9b 1e 2f 01        slliw t4,t5,0x12
+    libdis_test+0x48: 9b 5e 3f 01        srliw t4,t5,0x13
+    libdis_test+0x4c: 9b 5e 4f 41        sraiw t4,t5,0x14
+    libdis_test+0x50: 3b 84 24 01        addw s0,s1,s2
+    libdis_test+0x54: bb 04 39 41        subw s1,s2,s3
+    libdis_test+0x58: bb 19 5a 01        sllw s3,s4,s5
+    libdis_test+0x5c: bb 59 5a 01        srlw s3,s4,s5
+    libdis_test+0x60: bb 59 5a 41        sraw s3,s4,s5
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64i.s b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64i.s
new file mode 100644
index 0000000..31d6d69
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64i.s
@@ -0,0 +1,52 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV64I instructions. Instructions are ordered per the
+ * ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	lwu	s7, 0x7ff(s1)
+	lwu	s6, (s1)
+	lwu	s5, -0x800(s1)
+	ld	s4, 0x7ff(s1)
+	ld	s3, (s1)
+	ld	s2, -0x800(s1)
+	sd	t0, 0x7ff(t1)
+	sd	t1, (t2)
+	sd	t2, -0x800(t3)
+	slli	s0, s1, 2
+	slli	s0, s1, 63
+	srli	s0, s1, 2
+	srli	s0, s1, 63
+	srai	s0, s1, 2
+	srai	s0, s1, 63
+	addiw	ra, t0, 0x4
+	addiw	ra, t0, -0x4
+	slliw	t4, t5, 0x12
+	srliw	t4, t5, 0x13
+	sraiw	t4, t5, 0x14
+	addw	s0, s1, s2
+	subw	s1, s2, s3
+	sllw	s3, s4, s5
+	srlw	s3, s4, s5
+	sraw	s3, s4, s5
+
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64m.out b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64m.out
new file mode 100644
index 0000000..c807d0c
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64m.out
@@ -0,0 +1,5 @@
+    libdis_test:      3b 84 24 03        mulw s0,s1,s2
+    libdis_test+0x4:  3b ca 6a 03        divw s4,s5,s6
+    libdis_test+0x8:  bb 5a 7b 03        divuw s5,s6,s7
+    libdis_test+0xc:  3b eb 8b 03        remw s6,s7,s8
+    libdis_test+0x10: bb 7b 9c 03        remuw s7,s8,s9
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/64.rv64m.s b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64m.s
new file mode 100644
index 0000000..b31daca
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/64.rv64m.s
@@ -0,0 +1,31 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV64M instructions. Instructions are ordered per the
+ * ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	mulw	s0, s1, s2
+	divw	s4, s5, s6
+	divuw	s5, s6, s7
+	remw	s6, s7, s8
+	remuw	s7, s8, s9
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.csr.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.csr.out
new file mode 100644
index 0000000..9d8fc91
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.csr.out
@@ -0,0 +1,129 @@
+    libdis_test:       73 a3 03 00        csrrs t1,ustatus,t2
+    libdis_test+0x4:   73 a3 43 00        csrrs t1,uie,t2
+    libdis_test+0x8:   73 a3 53 00        csrrs t1,utvec,t2
+    libdis_test+0xc:   73 a3 03 04        csrrs t1,uscratch,t2
+    libdis_test+0x10:  73 a3 13 04        csrrs t1,uepc,t2
+    libdis_test+0x14:  73 a3 23 04        csrrs t1,ucause,t2
+    libdis_test+0x18:  73 a3 33 04        csrrs t1,utval,t2
+    libdis_test+0x1c:  73 a3 43 04        csrrs t1,uip,t2
+    libdis_test+0x20:  73 a3 13 00        csrrs t1,fflags,t2
+    libdis_test+0x24:  73 a3 23 00        csrrs t1,frm,t2
+    libdis_test+0x28:  73 a3 33 00        csrrs t1,fcsr,t2
+    libdis_test+0x2c:  73 a3 03 c0        csrrs t1,cycle,t2
+    libdis_test+0x30:  73 a3 13 c0        csrrs t1,time,t2
+    libdis_test+0x34:  73 a3 23 c0        csrrs t1,instret,t2
+    libdis_test+0x38:  73 a3 33 c0        csrrs t1,hpmcounter3,t2
+    libdis_test+0x3c:  73 a3 43 c0        csrrs t1,hpmcounter4,t2
+    libdis_test+0x40:  73 a3 53 c0        csrrs t1,hpmcounter5,t2
+    libdis_test+0x44:  73 a3 63 c0        csrrs t1,hpmcounter6,t2
+    libdis_test+0x48:  73 a3 73 c0        csrrs t1,hpmcounter7,t2
+    libdis_test+0x4c:  73 a3 83 c0        csrrs t1,hpmcounter8,t2
+    libdis_test+0x50:  73 a3 93 c0        csrrs t1,hpmcounter9,t2
+    libdis_test+0x54:  73 a3 a3 c0        csrrs t1,hpmcounter10,t2
+    libdis_test+0x58:  73 a3 b3 c0        csrrs t1,hpmcounter11,t2
+    libdis_test+0x5c:  73 a3 c3 c0        csrrs t1,hpmcounter12,t2
+    libdis_test+0x60:  73 a3 d3 c0        csrrs t1,hpmcounter13,t2
+    libdis_test+0x64:  73 a3 e3 c0        csrrs t1,hpmcounter14,t2
+    libdis_test+0x68:  73 a3 f3 c0        csrrs t1,hpmcounter15,t2
+    libdis_test+0x6c:  73 a3 03 c1        csrrs t1,hpmcounter16,t2
+    libdis_test+0x70:  73 a3 13 c1        csrrs t1,hpmcounter17,t2
+    libdis_test+0x74:  73 a3 23 c1        csrrs t1,hpmcounter18,t2
+    libdis_test+0x78:  73 a3 33 c1        csrrs t1,hpmcounter19,t2
+    libdis_test+0x7c:  73 a3 43 c1        csrrs t1,hpmcounter20,t2
+    libdis_test+0x80:  73 a3 53 c1        csrrs t1,hpmcounter21,t2
+    libdis_test+0x84:  73 a3 63 c1        csrrs t1,hpmcounter22,t2
+    libdis_test+0x88:  73 a3 73 c1        csrrs t1,hpmcounter23,t2
+    libdis_test+0x8c:  73 a3 83 c1        csrrs t1,hpmcounter24,t2
+    libdis_test+0x90:  73 a3 93 c1        csrrs t1,hpmcounter25,t2
+    libdis_test+0x94:  73 a3 a3 c1        csrrs t1,hpmcounter26,t2
+    libdis_test+0x98:  73 a3 b3 c1        csrrs t1,hpmcounter27,t2
+    libdis_test+0x9c:  73 a3 c3 c1        csrrs t1,hpmcounter28,t2
+    libdis_test+0xa0:  73 a3 d3 c1        csrrs t1,hpmcounter29,t2
+    libdis_test+0xa4:  73 a3 e3 c1        csrrs t1,hpmcounter30,t2
+    libdis_test+0xa8:  73 a3 f3 c1        csrrs t1,hpmcounter31,t2
+    libdis_test+0xac:  73 a3 03 c8        csrrs t1,cycleh,t2
+    libdis_test+0xb0:  73 a3 13 c8        csrrs t1,timeh,t2
+    libdis_test+0xb4:  73 a3 23 c8        csrrs t1,instreth,t2
+    libdis_test+0xb8:  73 a3 33 c8        csrrs t1,hpmcounter3h,t2
+    libdis_test+0xbc:  73 a3 43 c8        csrrs t1,hpmcounter4h,t2
+    libdis_test+0xc0:  73 a3 53 c8        csrrs t1,hpmcounter5h,t2
+    libdis_test+0xc4:  73 a3 63 c8        csrrs t1,hpmcounter6h,t2
+    libdis_test+0xc8:  73 a3 73 c8        csrrs t1,hpmcounter7h,t2
+    libdis_test+0xcc:  73 a3 83 c8        csrrs t1,hpmcounter8h,t2
+    libdis_test+0xd0:  73 a3 93 c8        csrrs t1,hpmcounter9h,t2
+    libdis_test+0xd4:  73 a3 a3 c8        csrrs t1,hpmcounter10h,t2
+    libdis_test+0xd8:  73 a3 b3 c8        csrrs t1,hpmcounter11h,t2
+    libdis_test+0xdc:  73 a3 c3 c8        csrrs t1,hpmcounter12h,t2
+    libdis_test+0xe0:  73 a3 d3 c8        csrrs t1,hpmcounter13h,t2
+    libdis_test+0xe4:  73 a3 e3 c8        csrrs t1,hpmcounter14h,t2
+    libdis_test+0xe8:  73 a3 f3 c8        csrrs t1,hpmcounter15h,t2
+    libdis_test+0xec:  73 a3 03 c9        csrrs t1,hpmcounter16h,t2
+    libdis_test+0xf0:  73 a3 13 c9        csrrs t1,hpmcounter17h,t2
+    libdis_test+0xf4:  73 a3 23 c9        csrrs t1,hpmcounter18h,t2
+    libdis_test+0xf8:  73 a3 33 c9        csrrs t1,hpmcounter19h,t2
+    libdis_test+0xfc:  73 a3 43 c9        csrrs t1,hpmcounter20h,t2
+    libdis_test+0x100: 73 a3 53 c9        csrrs t1,hpmcounter21h,t2
+    libdis_test+0x104: 73 a3 63 c9        csrrs t1,hpmcounter22h,t2
+    libdis_test+0x108: 73 a3 73 c9        csrrs t1,hpmcounter23h,t2
+    libdis_test+0x10c: 73 a3 83 c9        csrrs t1,hpmcounter24h,t2
+    libdis_test+0x110: 73 a3 93 c9        csrrs t1,hpmcounter25h,t2
+    libdis_test+0x114: 73 a3 a3 c9        csrrs t1,hpmcounter26h,t2
+    libdis_test+0x118: 73 a3 b3 c9        csrrs t1,hpmcounter27h,t2
+    libdis_test+0x11c: 73 a3 c3 c9        csrrs t1,hpmcounter28h,t2
+    libdis_test+0x120: 73 a3 d3 c9        csrrs t1,hpmcounter29h,t2
+    libdis_test+0x124: 73 a3 e3 c9        csrrs t1,hpmcounter30h,t2
+    libdis_test+0x128: 73 a3 f3 c9        csrrs t1,hpmcounter31h,t2
+    libdis_test+0x12c: 73 a3 03 10        csrrs t1,sstatus,t2
+    libdis_test+0x130: 73 a3 23 10        csrrs t1,sedeleg,t2
+    libdis_test+0x134: 73 a3 33 10        csrrs t1,sideleg,t2
+    libdis_test+0x138: 73 a3 43 10        csrrs t1,sie,t2
+    libdis_test+0x13c: 73 a3 53 10        csrrs t1,stvec,t2
+    libdis_test+0x140: 73 a3 63 10        csrrs t1,scounteren,t2
+    libdis_test+0x144: 73 a3 03 14        csrrs t1,sscratch,t2
+    libdis_test+0x148: 73 a3 13 14        csrrs t1,sepc,t2
+    libdis_test+0x14c: 73 a3 23 14        csrrs t1,scause,t2
+    libdis_test+0x150: 73 a3 33 14        csrrs t1,stval,t2
+    libdis_test+0x154: 73 a3 43 14        csrrs t1,sip,t2
+    libdis_test+0x158: 73 a3 03 18        csrrs t1,satp,t2
+    libdis_test+0x15c: 73 a3 13 f1        csrrs t1,mvendorid,t2
+    libdis_test+0x160: 73 a3 23 f1        csrrs t1,marchid,t2
+    libdis_test+0x164: 73 a3 33 f1        csrrs t1,mimpid,t2
+    libdis_test+0x168: 73 a3 43 f1        csrrs t1,mhartid,t2
+    libdis_test+0x16c: 73 a3 03 30        csrrs t1,mstatus,t2
+    libdis_test+0x170: 73 a3 13 30        csrrs t1,misa,t2
+    libdis_test+0x174: 73 a3 23 30        csrrs t1,medeleg,t2
+    libdis_test+0x178: 73 a3 33 30        csrrs t1,mideleg,t2
+    libdis_test+0x17c: 73 a3 43 30        csrrs t1,mie,t2
+    libdis_test+0x180: 73 a3 53 30        csrrs t1,mtvec,t2
+    libdis_test+0x184: 73 a3 63 30        csrrs t1,mcounteren,t2
+    libdis_test+0x188: 73 a3 03 34        csrrs t1,mscratch,t2
+    libdis_test+0x18c: 73 a3 13 34        csrrs t1,mepc,t2
+    libdis_test+0x190: 73 a3 23 34        csrrs t1,mcause,t2
+    libdis_test+0x194: 73 a3 33 34        csrrs t1,mtval,t2
+    libdis_test+0x198: 73 a3 43 34        csrrs t1,mip,t2
+    libdis_test+0x19c: 73 a3 03 3a        csrrs t1,pmpcfg0,t2
+    libdis_test+0x1a0: 73 a3 13 3a        csrrs t1,pmpcfg1,t2
+    libdis_test+0x1a4: 73 a3 23 3a        csrrs t1,pmpcfg2,t2
+    libdis_test+0x1a8: 73 a3 33 3a        csrrs t1,pmpcfg3,t2
+    libdis_test+0x1ac: 73 a3 03 3b        csrrs t1,pmpaddr0,t2
+    libdis_test+0x1b0: 73 a3 13 3b        csrrs t1,pmpaddr1,t2
+    libdis_test+0x1b4: 73 a3 23 3b        csrrs t1,pmpaddr2,t2
+    libdis_test+0x1b8: 73 a3 33 3b        csrrs t1,pmpaddr3,t2
+    libdis_test+0x1bc: 73 a3 43 3b        csrrs t1,pmpaddr4,t2
+    libdis_test+0x1c0: 73 a3 53 3b        csrrs t1,pmpaddr5,t2
+    libdis_test+0x1c4: 73 a3 63 3b        csrrs t1,pmpaddr6,t2
+    libdis_test+0x1c8: 73 a3 73 3b        csrrs t1,pmpaddr7,t2
+    libdis_test+0x1cc: 73 a3 83 3b        csrrs t1,pmpaddr8,t2
+    libdis_test+0x1d0: 73 a3 93 3b        csrrs t1,pmpaddr9,t2
+    libdis_test+0x1d4: 73 a3 a3 3b        csrrs t1,pmpaddr10,t2
+    libdis_test+0x1d8: 73 a3 b3 3b        csrrs t1,pmpaddr11,t2
+    libdis_test+0x1dc: 73 a3 c3 3b        csrrs t1,pmpaddr12,t2
+    libdis_test+0x1e0: 73 a3 d3 3b        csrrs t1,pmpaddr13,t2
+    libdis_test+0x1e4: 73 a3 e3 3b        csrrs t1,pmpaddr14,t2
+    libdis_test+0x1e8: 73 a3 f3 3b        csrrs t1,pmpaddr15,t2
+    libdis_test+0x1ec: 73 a3 03 00        csrrs t1,ustatus,t2
+    libdis_test+0x1f0: 73 93 43 00        csrrw t1,uie,t2
+    libdis_test+0x1f4: 73 b3 53 00        csrrc t1,utvec,t2
+    libdis_test+0x1f8: 73 d3 0b 04        csrrwi t1,uscratch,0x17
+    libdis_test+0x1fc: 73 63 1b 04        csrrsi t1,uepc,0x16
+    libdis_test+0x200: 73 f3 2a 04        csrrci t1,ucause,0x15
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.csr.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.csr.s
new file mode 100644
index 0000000..6fb5dd1
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.csr.s
@@ -0,0 +1,168 @@
+/*
+ * This file and its contents are supplied under the terms of the
+	csrrs	t1, CDDL, t2), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of csr instructions and csr names.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	/* User Trap */
+	csrrs	t1, ustatus, t2 
+	csrrs	t1, uie, t2 
+	csrrs	t1, utvec, t2 
+	/* User Trap Handling */
+	csrrs	t1, uscratch, t2 
+	csrrs	t1, uepc, t2 
+	csrrs	t1, ucause, t2 
+	csrrs	t1, utval, t2 
+	csrrs	t1, uip, t2 
+	/* User Floating-Point CSRs */
+	csrrs	t1, fflags, t2 
+	csrrs	t1, frm, t2 
+	csrrs	t1, fcsr, t2 
+	/* User Counters/Timers */
+	csrrs	t1, cycle, t2 
+	csrrs	t1, time, t2 
+	csrrs	t1, instret, t2 
+	csrrs	t1, hpmcounter3, t2 
+	csrrs	t1, hpmcounter4, t2 
+	csrrs	t1, hpmcounter5, t2 
+	csrrs	t1, hpmcounter6, t2 
+	csrrs	t1, hpmcounter7, t2 
+	csrrs	t1, hpmcounter8, t2 
+	csrrs	t1, hpmcounter9, t2 
+	csrrs	t1, hpmcounter10, t2 
+	csrrs	t1, hpmcounter11, t2 
+	csrrs	t1, hpmcounter12, t2 
+	csrrs	t1, hpmcounter13, t2 
+	csrrs	t1, hpmcounter14, t2 
+	csrrs	t1, hpmcounter15, t2 
+	csrrs	t1, hpmcounter16, t2 
+	csrrs	t1, hpmcounter17, t2 
+	csrrs	t1, hpmcounter18, t2 
+	csrrs	t1, hpmcounter19, t2 
+	csrrs	t1, hpmcounter20, t2 
+	csrrs	t1, hpmcounter21, t2 
+	csrrs	t1, hpmcounter22, t2 
+	csrrs	t1, hpmcounter23, t2 
+	csrrs	t1, hpmcounter24, t2 
+	csrrs	t1, hpmcounter25, t2 
+	csrrs	t1, hpmcounter26, t2 
+	csrrs	t1, hpmcounter27, t2 
+	csrrs	t1, hpmcounter28, t2 
+	csrrs	t1, hpmcounter29, t2 
+	csrrs	t1, hpmcounter30, t2 
+	csrrs	t1, hpmcounter31, t2 
+	csrrs	t1, cycleh, t2 
+	csrrs	t1, timeh, t2 
+	csrrs	t1, instreth, t2 
+	csrrs	t1, hpmcounter3h, t2 
+	csrrs	t1, hpmcounter4h, t2 
+	csrrs	t1, hpmcounter5h, t2 
+	csrrs	t1, hpmcounter6h, t2 
+	csrrs	t1, hpmcounter7h, t2 
+	csrrs	t1, hpmcounter8h, t2 
+	csrrs	t1, hpmcounter9h, t2 
+	csrrs	t1, hpmcounter10h, t2 
+	csrrs	t1, hpmcounter11h, t2 
+	csrrs	t1, hpmcounter12h, t2 
+	csrrs	t1, hpmcounter13h, t2 
+	csrrs	t1, hpmcounter14h, t2 
+	csrrs	t1, hpmcounter15h, t2 
+	csrrs	t1, hpmcounter16h, t2 
+	csrrs	t1, hpmcounter17h, t2 
+	csrrs	t1, hpmcounter18h, t2 
+	csrrs	t1, hpmcounter19h, t2 
+	csrrs	t1, hpmcounter20h, t2 
+	csrrs	t1, hpmcounter21h, t2 
+	csrrs	t1, hpmcounter22h, t2
+	csrrs	t1, hpmcounter23h, t2 
+	csrrs	t1, hpmcounter24h, t2 
+	csrrs	t1, hpmcounter25h, t2 
+	csrrs	t1, hpmcounter26h, t2 
+	csrrs	t1, hpmcounter27h, t2 
+	csrrs	t1, hpmcounter28h, t2 
+	csrrs	t1, hpmcounter29h, t2 
+	csrrs	t1, hpmcounter30h, t2 
+	csrrs	t1, hpmcounter31h, t2 
+	/* Supervisor Trap Status */
+	csrrs	t1, sstatus, t2 
+	csrrs	t1, sedeleg, t2 
+	csrrs	t1, sideleg, t2 
+	csrrs	t1, sie, t2 
+	csrrs	t1, stvec, t2 
+	csrrs	t1, scounteren, t2 
+	/* Supervisor Trap Handling */
+	csrrs	t1, sscratch, t2 
+	csrrs	t1, sepc, t2 
+	csrrs	t1, scause, t2 
+	csrrs	t1, stval, t2 
+	csrrs	t1, sip, t2 
+	/* Supervisor Protection and Translation */
+	csrrs	t1, satp, t2 
+	/* Machine Information Registers */
+	csrrs	t1, mvendorid, t2 
+	csrrs	t1, marchid, t2 
+	csrrs	t1, mimpid, t2 
+	csrrs	t1, mhartid, t2 
+	/* Machine Trap Setup */
+	csrrs	t1, mstatus, t2 
+	csrrs	t1, misa, t2 
+	csrrs	t1, medeleg, t2 
+	csrrs	t1, mideleg, t2 
+	csrrs	t1, mie, t2 
+	csrrs	t1, mtvec, t2 
+	csrrs	t1, mcounteren, t2 
+	/* Machine Trap Handling */
+	csrrs	t1, mscratch, t2 
+	csrrs	t1, mepc, t2 
+	csrrs	t1, mcause, t2 
+	csrrs	t1, mtval, t2 
+	csrrs	t1, mip, t2 
+	/* Machine Protection and Translation */
+	csrrs	t1, pmpcfg0, t2 
+	csrrs	t1, pmpcfg1, t2 
+	csrrs	t1, pmpcfg2, t2 
+	csrrs	t1, pmpcfg3, t2 
+	csrrs	t1, pmpaddr0, t2 
+	csrrs	t1, pmpaddr1, t2 
+	csrrs	t1, pmpaddr2, t2 
+	csrrs	t1, pmpaddr3, t2 
+	csrrs	t1, pmpaddr4, t2 
+	csrrs	t1, pmpaddr5, t2 
+	csrrs	t1, pmpaddr6, t2 
+	csrrs	t1, pmpaddr7, t2 
+	csrrs	t1, pmpaddr8, t2 
+	csrrs	t1, pmpaddr9, t2 
+	csrrs	t1, pmpaddr10, t2 
+	csrrs	t1, pmpaddr11, t2 
+	csrrs	t1, pmpaddr12, t2 
+	csrrs	t1, pmpaddr13, t2 
+	csrrs	t1, pmpaddr14, t2 
+	csrrs	t1, pmpaddr15, t2
+	/*
+	 * Various instr variants
+	 */
+	csrrs	t1, ustatus, t2 
+	csrrw	t1, uie, t2 
+	csrrc	t1, utvec, t2 
+	csrrwi	t1, uscratch, 0x17
+	csrrsi	t1, uepc, 0x16
+	csrrci	t1, ucause, 0x15
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.fpregs.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.fpregs.out
new file mode 100644
index 0000000..0eb8fd1
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.fpregs.out
@@ -0,0 +1,64 @@
+    libdis_test:       53 70 00 00        fadd.s ft0,ft0,ft0
+    libdis_test+0x4:   d3 f0 10 00        fadd.s ft1,ft1,ft1
+    libdis_test+0x8:   53 71 21 00        fadd.s ft2,ft2,ft2
+    libdis_test+0xc:   d3 f1 31 00        fadd.s ft3,ft3,ft3
+    libdis_test+0x10:  53 72 42 00        fadd.s ft4,ft4,ft4
+    libdis_test+0x14:  d3 f2 52 00        fadd.s ft5,ft5,ft5
+    libdis_test+0x18:  53 73 63 00        fadd.s ft6,ft6,ft6
+    libdis_test+0x1c:  d3 f3 73 00        fadd.s ft7,ft7,ft7
+    libdis_test+0x20:  53 74 84 00        fadd.s fs0,fs0,fs0
+    libdis_test+0x24:  d3 f4 94 00        fadd.s fs1,fs1,fs1
+    libdis_test+0x28:  53 75 a5 00        fadd.s fa0,fa0,fa0
+    libdis_test+0x2c:  d3 f5 b5 00        fadd.s fa1,fa1,fa1
+    libdis_test+0x30:  53 76 c6 00        fadd.s fa2,fa2,fa2
+    libdis_test+0x34:  d3 f6 d6 00        fadd.s fa3,fa3,fa3
+    libdis_test+0x38:  53 77 e7 00        fadd.s fa4,fa4,fa4
+    libdis_test+0x3c:  d3 f7 f7 00        fadd.s fa5,fa5,fa5
+    libdis_test+0x40:  53 78 08 01        fadd.s fa6,fa6,fa6
+    libdis_test+0x44:  d3 f8 18 01        fadd.s fa7,fa7,fa7
+    libdis_test+0x48:  53 79 29 01        fadd.s fs2,fs2,fs2
+    libdis_test+0x4c:  d3 f9 39 01        fadd.s fs3,fs3,fs3
+    libdis_test+0x50:  53 7a 4a 01        fadd.s fs4,fs4,fs4
+    libdis_test+0x54:  d3 fa 5a 01        fadd.s fs5,fs5,fs5
+    libdis_test+0x58:  53 7b 6b 01        fadd.s fs6,fs6,fs6
+    libdis_test+0x5c:  d3 fb 7b 01        fadd.s fs7,fs7,fs7
+    libdis_test+0x60:  53 7c 8c 01        fadd.s fs8,fs8,fs8
+    libdis_test+0x64:  d3 fc 9c 01        fadd.s fs9,fs9,fs9
+    libdis_test+0x68:  53 7d ad 01        fadd.s fs10,fs10,fs10
+    libdis_test+0x6c:  d3 fd bd 01        fadd.s fs11,fs11,fs11
+    libdis_test+0x70:  53 7e ce 01        fadd.s ft8,ft8,ft8
+    libdis_test+0x74:  d3 fe de 01        fadd.s ft9,ft9,ft9
+    libdis_test+0x78:  53 7f ef 01        fadd.s ft10,ft10,ft10
+    libdis_test+0x7c:  d3 ff ff 01        fadd.s ft11,ft11,ft11
+    libdis_test+0x80:  53 f0 20 00        fadd.s ft0,ft1,ft2
+    libdis_test+0x84:  d3 70 31 00        fadd.s ft1,ft2,ft3
+    libdis_test+0x88:  53 f1 41 00        fadd.s ft2,ft3,ft4
+    libdis_test+0x8c:  d3 71 52 00        fadd.s ft3,ft4,ft5
+    libdis_test+0x90:  53 f2 62 00        fadd.s ft4,ft5,ft6
+    libdis_test+0x94:  d3 72 73 00        fadd.s ft5,ft6,ft7
+    libdis_test+0x98:  53 f3 83 00        fadd.s ft6,ft7,fs0
+    libdis_test+0x9c:  d3 73 94 00        fadd.s ft7,fs0,fs1
+    libdis_test+0xa0:  53 f4 a4 00        fadd.s fs0,fs1,fa0
+    libdis_test+0xa4:  d3 74 b5 00        fadd.s fs1,fa0,fa1
+    libdis_test+0xa8:  53 f5 c5 00        fadd.s fa0,fa1,fa2
+    libdis_test+0xac:  d3 75 d6 00        fadd.s fa1,fa2,fa3
+    libdis_test+0xb0:  53 f6 e6 00        fadd.s fa2,fa3,fa4
+    libdis_test+0xb4:  d3 76 f7 00        fadd.s fa3,fa4,fa5
+    libdis_test+0xb8:  53 f7 07 01        fadd.s fa4,fa5,fa6
+    libdis_test+0xbc:  d3 77 18 01        fadd.s fa5,fa6,fa7
+    libdis_test+0xc0:  53 f8 28 01        fadd.s fa6,fa7,fs2
+    libdis_test+0xc4:  d3 78 39 01        fadd.s fa7,fs2,fs3
+    libdis_test+0xc8:  53 f9 49 01        fadd.s fs2,fs3,fs4
+    libdis_test+0xcc:  d3 79 5a 01        fadd.s fs3,fs4,fs5
+    libdis_test+0xd0:  53 fa 6a 01        fadd.s fs4,fs5,fs6
+    libdis_test+0xd4:  d3 7a 7b 01        fadd.s fs5,fs6,fs7
+    libdis_test+0xd8:  53 fb 8b 01        fadd.s fs6,fs7,fs8
+    libdis_test+0xdc:  d3 7b 9c 01        fadd.s fs7,fs8,fs9
+    libdis_test+0xe0:  53 fc ac 01        fadd.s fs8,fs9,fs10
+    libdis_test+0xe4:  d3 7c bd 01        fadd.s fs9,fs10,fs11
+    libdis_test+0xe8:  53 fd cd 01        fadd.s fs10,fs11,ft8
+    libdis_test+0xec:  d3 7d de 01        fadd.s fs11,ft8,ft9
+    libdis_test+0xf0:  53 fe ee 01        fadd.s ft8,ft9,ft10
+    libdis_test+0xf4:  d3 7e ff 01        fadd.s ft9,ft10,ft11
+    libdis_test+0xf8:  53 ff 0f 00        fadd.s ft10,ft11,ft0
+    libdis_test+0xfc:  d3 7f 10 00        fadd.s ft11,ft0,ft1
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.fpregs.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.fpregs.s
new file mode 100644
index 0000000..e85179c
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.fpregs.s
@@ -0,0 +1,92 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of all of the fp register names.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+
+libdifs_tefst:
+	fadd.s	ft0, ft0, ft0
+	fadd.s	ft1, ft1, ft1
+	fadd.s	ft2, ft2, ft2
+	fadd.s	ft3, ft3, ft3
+	fadd.s	ft4, ft4, ft4
+	fadd.s	ft5, ft5, ft5
+	fadd.s	ft6, ft6, ft6
+	fadd.s	ft7, ft7, ft7
+	fadd.s	fs0, fs0, fs0
+	fadd.s	fs1, fs1, fs1
+	fadd.s	fa0, fa0, fa0
+	fadd.s	fa1, fa1, fa1
+	fadd.s	fa2, fa2, fa2
+	fadd.s	fa3, fa3, fa3
+	fadd.s	fa4, fa4, fa4
+	fadd.s	fa5, fa5, fa5
+	fadd.s	fa6, fa6, fa6
+	fadd.s	fa7, fa7, fa7
+	fadd.s	fs2, fs2, fs2
+	fadd.s	fs3, fs3, fs3
+	fadd.s	fs4, fs4, fs4
+	fadd.s	fs5, fs5, fs5
+	fadd.s	fs6, fs6, fs6
+	fadd.s	fs7, fs7, fs7
+	fadd.s	fs8, fs8, fs8
+	fadd.s	fs9, fs9, fs9
+	fadd.s	fs10, fs10, fs10
+	fadd.s	fs11, fs11, fs11
+	fadd.s	ft8, ft8, ft8
+	fadd.s	ft9, ft9, ft9 
+	fadd.s	ft10, ft10, ft10 
+	fadd.s	ft11, ft11, ft11
+
+	fadd.s	ft0, ft1, ft2
+	fadd.s	ft1, ft2, ft3
+	fadd.s	ft2, ft3, ft4
+	fadd.s	ft3, ft4, ft5
+	fadd.s	ft4, ft5, ft6
+	fadd.s	ft5, ft6, ft7
+	fadd.s	ft6, ft7, fs0
+	fadd.s	ft7, fs0, fs1
+	fadd.s	fs0, fs1, fa0
+	fadd.s	fs1, fa0, fa1
+	fadd.s	fa0, fa1, fa2
+	fadd.s	fa1, fa2, fa3
+	fadd.s	fa2, fa3, fa4
+	fadd.s	fa3, fa4, fa5
+	fadd.s	fa4, fa5, fa6
+	fadd.s	fa5, fa6, fa7
+	fadd.s	fa6, fa7, fs2
+	fadd.s	fa7, fs2, fs3
+	fadd.s	fs2, fs3, fs4
+	fadd.s	fs3, fs4, fs5
+	fadd.s	fs4, fs5, fs6
+	fadd.s	fs5, fs6, fs7
+	fadd.s	fs6, fs7, fs8
+	fadd.s	fs7, fs8, fs9
+	fadd.s	fs8, fs9, fs10
+	fadd.s	fs9, fs10, fs11
+	fadd.s	fs10, fs11, ft8
+	fadd.s	fs11, ft8, ft9
+	fadd.s	ft8, ft9, ft10
+	fadd.s	ft9, ft10, ft11
+	fadd.s	ft10, ft11, ft0
+	fadd.s	ft11, ft0, ft1
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.pseudo.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.pseudo.out
new file mode 100644
index 0000000..e983ca4
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.pseudo.out
@@ -0,0 +1,26 @@
+    libdis_test:      13 00 00 00        nop
+    libdis_test+0x4:  67 80 00 00        ret
+    libdis_test+0x8:  0f 00 f0 0f        fence
+    libdis_test+0xc:  f3 22 20 c0        rdinstret t0
+    libdis_test+0x10: 73 23 00 c0        rdcycle t1
+    libdis_test+0x14: f3 23 10 c0        rdtime t2
+    libdis_test+0x18: 73 23 00 00        csrr t1,ustatus
+    libdis_test+0x1c: 73 10 03 00        csrw ustatus,t1
+    libdis_test+0x20: 73 a0 03 00        csrs ustatus,t2
+    libdis_test+0x24: 73 30 0e 00        csrc ustatus,t3
+    libdis_test+0x28: 73 50 42 00        csrwi uie,0x4
+    libdis_test+0x2c: 73 e0 42 00        csrsi uie,0x5
+    libdis_test+0x30: 73 70 43 00        csrci uie,0x6
+    libdis_test+0x34: 73 24 30 00        frcsr s0
+    libdis_test+0x38: 73 94 34 00        fscsr s0,s1
+    libdis_test+0x3c: 73 90 34 00        fscsr s1
+    libdis_test+0x40: 73 25 20 00        frrm a0
+    libdis_test+0x44: 73 95 25 00        fsrm a0,a1
+    libdis_test+0x48: 73 90 25 00        fsrm a1
+    libdis_test+0x4c: f3 52 22 00        fsrmi t0,0x4
+    libdis_test+0x50: 73 d0 22 00        fsrmi 0x5
+    libdis_test+0x54: 73 25 10 00        frflags a0
+    libdis_test+0x58: 73 95 15 00        fsflags a0,a1
+    libdis_test+0x5c: 73 90 15 00        fsflags a1
+    libdis_test+0x60: f3 52 12 00        fsflagsi t0,0x4
+    libdis_test+0x64: 73 d0 12 00        fsflagsi 0x5
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.pseudo.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.pseudo.s
new file mode 100644
index 0000000..623ad89
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.pseudo.s
@@ -0,0 +1,54 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of various supported pseudo instructions. We only
+ * support disassembling a subset of the common pseudo instructions that map
+ * directly to a single asm instruction. Several of the pseudo-instructions
+ * transform into more than one instruction so we don't support them.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	nop
+	ret
+	fence
+	rdinstret	t0
+	rdcycle		t1
+	rdtime		t2
+	csrr		t1, ustatus
+	csrw		ustatus, t1
+	csrs		ustatus, t2
+	csrc		ustatus, t3
+	csrwi		uie, 0x4
+	csrsi		uie, 0x5
+	csrci		uie, 0x6
+	frcsr		s0
+	fscsr		s0, s1
+	fscsr		s1
+	frrm		a0
+	fsrm		a0, a1
+	fsrm		a1
+	fsrmi		t0, 0x4
+	fsrmi		0x5	
+	frflags		a0
+	fsflags		a0, a1
+	fsflags		a1
+	fsflagsi	t0, 0x4
+	fsflagsi	0x5	
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.regs.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.regs.out
new file mode 100644
index 0000000..a754c51
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.regs.out
@@ -0,0 +1,64 @@
+    libdis_test:       33 00 00 00        add x0,x0,x0
+    libdis_test+0x4:   b3 80 10 00        add ra,ra,ra
+    libdis_test+0x8:   33 01 21 00        add sp,sp,sp
+    libdis_test+0xc:   b3 81 31 00        add gp,gp,gp
+    libdis_test+0x10:  33 02 42 00        add tp,tp,tp
+    libdis_test+0x14:  b3 82 52 00        add t0,t0,t0
+    libdis_test+0x18:  33 03 63 00        add t1,t1,t1
+    libdis_test+0x1c:  b3 83 73 00        add t2,t2,t2
+    libdis_test+0x20:  33 04 84 00        add s0,s0,s0
+    libdis_test+0x24:  b3 84 94 00        add s1,s1,s1
+    libdis_test+0x28:  33 05 a5 00        add a0,a0,a0
+    libdis_test+0x2c:  b3 85 b5 00        add a1,a1,a1
+    libdis_test+0x30:  33 06 c6 00        add a2,a2,a2
+    libdis_test+0x34:  b3 86 d6 00        add a3,a3,a3
+    libdis_test+0x38:  33 07 e7 00        add a4,a4,a4
+    libdis_test+0x3c:  b3 87 f7 00        add a5,a5,a5
+    libdis_test+0x40:  33 08 08 01        add a6,a6,a6
+    libdis_test+0x44:  b3 88 18 01        add a7,a7,a7
+    libdis_test+0x48:  33 09 29 01        add s2,s2,s2
+    libdis_test+0x4c:  b3 89 39 01        add s3,s3,s3
+    libdis_test+0x50:  33 0a 4a 01        add s4,s4,s4
+    libdis_test+0x54:  b3 8a 5a 01        add s5,s5,s5
+    libdis_test+0x58:  33 0b 6b 01        add s6,s6,s6
+    libdis_test+0x5c:  b3 8b 7b 01        add s7,s7,s7
+    libdis_test+0x60:  33 0c 8c 01        add s8,s8,s8
+    libdis_test+0x64:  b3 8c 9c 01        add s9,s9,s9
+    libdis_test+0x68:  33 0d ad 01        add s10,s10,s10
+    libdis_test+0x6c:  b3 8d bd 01        add s11,s11,s11
+    libdis_test+0x70:  33 0e ce 01        add t3,t3,t3
+    libdis_test+0x74:  b3 8e de 01        add t4,t4,t4
+    libdis_test+0x78:  33 0f ef 01        add t5,t5,t5
+    libdis_test+0x7c:  b3 8f ff 01        add t6,t6,t6
+    libdis_test+0x80:  33 80 20 00        add x0,ra,sp
+    libdis_test+0x84:  b3 00 31 00        add ra,sp,gp
+    libdis_test+0x88:  33 81 41 00        add sp,gp,tp
+    libdis_test+0x8c:  b3 01 52 00        add gp,tp,t0
+    libdis_test+0x90:  33 82 62 00        add tp,t0,t1
+    libdis_test+0x94:  b3 02 73 00        add t0,t1,t2
+    libdis_test+0x98:  33 83 83 00        add t1,t2,s0
+    libdis_test+0x9c:  b3 03 94 00        add t2,s0,s1
+    libdis_test+0xa0:  33 84 a4 00        add s0,s1,a0
+    libdis_test+0xa4:  b3 04 b5 00        add s1,a0,a1
+    libdis_test+0xa8:  33 85 c5 00        add a0,a1,a2
+    libdis_test+0xac:  b3 05 d6 00        add a1,a2,a3
+    libdis_test+0xb0:  33 86 e6 00        add a2,a3,a4
+    libdis_test+0xb4:  b3 06 f7 00        add a3,a4,a5
+    libdis_test+0xb8:  33 87 07 01        add a4,a5,a6
+    libdis_test+0xbc:  b3 07 18 01        add a5,a6,a7
+    libdis_test+0xc0:  33 88 28 01        add a6,a7,s2
+    libdis_test+0xc4:  b3 08 39 01        add a7,s2,s3
+    libdis_test+0xc8:  33 89 49 01        add s2,s3,s4
+    libdis_test+0xcc:  b3 09 5a 01        add s3,s4,s5
+    libdis_test+0xd0:  33 8a 6a 01        add s4,s5,s6
+    libdis_test+0xd4:  b3 0a 7b 01        add s5,s6,s7
+    libdis_test+0xd8:  33 8b 8b 01        add s6,s7,s8
+    libdis_test+0xdc:  b3 0b 9c 01        add s7,s8,s9
+    libdis_test+0xe0:  33 8c ac 01        add s8,s9,s10
+    libdis_test+0xe4:  b3 0c bd 01        add s9,s10,s11
+    libdis_test+0xe8:  33 8d cd 01        add s10,s11,t3
+    libdis_test+0xec:  b3 0d de 01        add s11,t3,t4
+    libdis_test+0xf0:  33 8e ee 01        add t3,t4,t5
+    libdis_test+0xf4:  b3 0e ff 01        add t4,t5,t6
+    libdis_test+0xf8:  33 8f 0f 00        add t5,t6,x0
+    libdis_test+0xfc:  b3 0f 10 00        add t6,x0,ra
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.regs.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.regs.s
new file mode 100644
index 0000000..7ccfd71
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.regs.s
@@ -0,0 +1,90 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test that we properly name all registers in their place.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	add	x0, x0, x0
+	add	ra, ra, ra
+	add	sp, sp, sp
+	add	gp, gp, gp
+	add	tp, tp, tp
+	add	t0, t0, t0
+	add	t1, t1, t1
+	add	t2, t2, t2
+	add	s0, s0, s0
+	add	s1, s1, s1
+	add	a0, a0, a0
+	add	a1, a1, a1
+	add	a2, a2, a2
+	add	a3, a3, a3
+	add	a4, a4, a4
+	add	a5, a5, a5
+	add	a6, a6, a6
+	add	a7, a7, a7
+	add	s2, s2, s2
+	add	s3, s3, s3
+	add	s4, s4, s4
+	add	s5, s5, s5
+	add	s6, s6, s6
+	add	s7, s7, s7
+	add	s8, s8, s8
+	add	s9, s9, s9
+	add	s10, s10, s10
+	add	s11, s11, s11
+	add	t3, t3, t3
+	add	t4, t4, t4
+	add	t5, t5, t5
+	add	t6, t6, t6
+
+	add	x0, ra, sp
+	add	ra, sp, gp
+	add	sp, gp, tp
+	add	gp, tp, t0
+	add	tp, t0, t1
+	add	t0, t1, t2
+	add	t1, t2, s0
+	add	t2, s0, s1
+	add	s0, s1, a0
+	add	s1, a0, a1
+	add	a0, a1, a2
+	add	a1, a2, a3
+	add	a2, a3, a4
+	add	a3, a4, a5
+	add	a4, a5, a6
+	add	a5, a6, a7
+	add	a6, a7, s2
+	add	a7, s2, s3
+	add	s2, s3, s4
+	add	s3, s4, s5
+	add	s4, s5, s6
+	add	s5, s6, s7
+	add	s6, s7, s8
+	add	s7, s8, s9
+	add	s8, s9, s10
+	add	s9, s10, s11
+	add	s10, s11, t3
+	add	s11, t3, t4
+	add	t3, t4, t5
+	add	t4, t5, t6
+	add	t5, t6, x0
+	add	t6, x0, ra
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32a.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32a.out
new file mode 100644
index 0000000..9eb8112
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32a.out
@@ -0,0 +1,44 @@
+    libdis_test:      2f a4 04 10        lr.w s0,(s1)
+    libdis_test+0x4:  af 24 09 14        lr.w.aq s1,(s2)
+    libdis_test+0x8:  2f a9 09 12        lr.w.rl s2,(s3)
+    libdis_test+0xc:  af 29 0a 16        lr.w.aqrl s3,(s4)
+    libdis_test+0x10: 2f a4 24 19        sc.w s0,s2,(s1)
+    libdis_test+0x14: af a4 34 1d        sc.w.aq s1,s3,(s1)
+    libdis_test+0x18: 2f a9 44 1b        sc.w.rl s2,s4,(s1)
+    libdis_test+0x1c: af a9 54 1f        sc.w.aqrl s3,s5,(s1)
+    libdis_test+0x20: af a2 63 08        amoswap.w t0,t1,(t2)
+    libdis_test+0x24: 2f 23 7e 0c        amoswap.w.aq t1,t2,(t3)
+    libdis_test+0x28: af a3 ce 0b        amoswap.w.rl t2,t3,(t4)
+    libdis_test+0x2c: 2f 2e df 0f        amoswap.w.aqrl t3,t4,(t5)
+    libdis_test+0x30: af a2 63 00        amoadd.w t0,t1,(t2)
+    libdis_test+0x34: 2f 23 7e 04        amoadd.w.aq t1,t2,(t3)
+    libdis_test+0x38: af a3 ce 03        amoadd.w.rl t2,t3,(t4)
+    libdis_test+0x3c: 2f 2e df 07        amoadd.w.aqrl t3,t4,(t5)
+    libdis_test+0x40: af a2 63 20        amoxor.w t0,t1,(t2)
+    libdis_test+0x44: 2f 23 7e 24        amoxor.w.aq t1,t2,(t3)
+    libdis_test+0x48: af a3 ce 23        amoxor.w.rl t2,t3,(t4)
+    libdis_test+0x4c: 2f 2e df 27        amoxor.w.aqrl t3,t4,(t5)
+    libdis_test+0x50: af a2 63 60        amoand.w t0,t1,(t2)
+    libdis_test+0x54: 2f 23 7e 64        amoand.w.aq t1,t2,(t3)
+    libdis_test+0x58: af a3 ce 63        amoand.w.rl t2,t3,(t4)
+    libdis_test+0x5c: 2f 2e df 67        amoand.w.aqrl t3,t4,(t5)
+    libdis_test+0x60: af a2 63 40        amoor.w t0,t1,(t2)
+    libdis_test+0x64: 2f 23 7e 44        amoor.w.aq t1,t2,(t3)
+    libdis_test+0x68: af a3 ce 43        amoor.w.rl t2,t3,(t4)
+    libdis_test+0x6c: 2f 2e df 47        amoor.w.aqrl t3,t4,(t5)
+    libdis_test+0x70: af a2 63 80        amomin.w t0,t1,(t2)
+    libdis_test+0x74: 2f 23 7e 84        amomin.w.aq t1,t2,(t3)
+    libdis_test+0x78: af a3 ce 83        amomin.w.rl t2,t3,(t4)
+    libdis_test+0x7c: 2f 2e df 87        amomin.w.aqrl t3,t4,(t5)
+    libdis_test+0x80: af a2 63 a0        amomax.w t0,t1,(t2)
+    libdis_test+0x84: 2f 23 7e a4        amomax.w.aq t1,t2,(t3)
+    libdis_test+0x88: af a3 ce a3        amomax.w.rl t2,t3,(t4)
+    libdis_test+0x8c: 2f 2e df a7        amomax.w.aqrl t3,t4,(t5)
+    libdis_test+0x90: af a2 63 c0        amominu.w t0,t1,(t2)
+    libdis_test+0x94: 2f 23 7e c4        amominu.w.aq t1,t2,(t3)
+    libdis_test+0x98: af a3 ce c3        amominu.w.rl t2,t3,(t4)
+    libdis_test+0x9c: 2f 2e df c7        amominu.w.aqrl t3,t4,(t5)
+    libdis_test+0xa0: af a2 63 e0        amomaxu.w t0,t1,(t2)
+    libdis_test+0xa4: 2f 23 7e e4        amomaxu.w.aq t1,t2,(t3)
+    libdis_test+0xa8: af a3 ce e3        amomaxu.w.rl t2,t3,(t4)
+    libdis_test+0xac: 2f 2e df e7        amomaxu.w.aqrl t3,t4,(t5)
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32a.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32a.s
new file mode 100644
index 0000000..147319d
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32a.s
@@ -0,0 +1,70 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV32A instructions. Instructions are ordered per the
+ * ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	lr.w		s0, (s1)
+	lr.w.aq		s1, (s2)
+	lr.w.rl		s2, (s3)
+	lr.w.aqrl	s3, (s4)
+	sc.w		s0, s2, (s1)
+	sc.w.aq		s1, s3, (s1)
+	sc.w.rl		s2, s4, (s1)
+	sc.w.aqrl	s3, s5, (s1)
+	amoswap.w	t0, t1, (t2)
+	amoswap.w.aq	t1, t2, (t3)
+	amoswap.w.rl	t2, t3, (t4)
+	amoswap.w.aqrl	t3, t4, (t5)
+	amoadd.w	t0, t1, (t2)
+	amoadd.w.aq	t1, t2, (t3)
+	amoadd.w.rl	t2, t3, (t4)
+	amoadd.w.aqrl	t3, t4, (t5)
+	amoxor.w	t0, t1, (t2)
+	amoxor.w.aq	t1, t2, (t3)
+	amoxor.w.rl	t2, t3, (t4)
+	amoxor.w.aqrl	t3, t4, (t5)
+	amoand.w	t0, t1, (t2)
+	amoand.w.aq	t1, t2, (t3)
+	amoand.w.rl	t2, t3, (t4)
+	amoand.w.aqrl	t3, t4, (t5)
+	amoor.w		t0, t1, (t2)
+	amoor.w.aq	t1, t2, (t3)
+	amoor.w.rl	t2, t3, (t4)
+	amoor.w.aqrl	t3, t4, (t5)
+	amomin.w	t0, t1, (t2)
+	amomin.w.aq	t1, t2, (t3)
+	amomin.w.rl	t2, t3, (t4)
+	amomin.w.aqrl	t3, t4, (t5)
+	amomax.w	t0, t1, (t2)
+	amomax.w.aq	t1, t2, (t3)
+	amomax.w.rl	t2, t3, (t4)
+	amomax.w.aqrl	t3, t4, (t5)
+	amominu.w	t0, t1, (t2)
+	amominu.w.aq	t1, t2, (t3)
+	amominu.w.rl	t2, t3, (t4)
+	amominu.w.aqrl	t3, t4, (t5)
+	amomaxu.w	t0, t1, (t2)
+	amomaxu.w.aq	t1, t2, (t3)
+	amomaxu.w.rl	t2, t3, (t4)
+	amomaxu.w.aqrl	t3, t4, (t5)
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32d.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32d.out
new file mode 100644
index 0000000..bef10b7
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32d.out
@@ -0,0 +1,90 @@
+    libdis_test:       87 30 09 00        fld ft1,0x0(s2)
+    libdis_test+0x4:   87 30 c9 ff        fld ft1,-0x4(s2)
+    libdis_test+0x8:   87 30 29 04        fld ft1,0x42(s2)
+    libdis_test+0xc:   27 30 19 00        fsd ft1,0x0(s2)
+    libdis_test+0x10:  27 3e 19 fe        fsd ft1,-0x4(s2)
+    libdis_test+0x14:  27 31 19 04        fsd ft1,0x42(s2)
+    libdis_test+0x18:  c3 70 31 22        fmadd.d ft1,ft2,ft3,ft4
+    libdis_test+0x1c:  c3 00 31 22        fmadd.d ft1,ft2,ft3,ft4,rne
+    libdis_test+0x20:  c3 10 31 22        fmadd.d ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x24:  c3 20 31 22        fmadd.d ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x28:  c3 30 31 22        fmadd.d ft1,ft2,ft3,ft4,rup
+    libdis_test+0x2c:  c3 40 31 22        fmadd.d ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x30:  c7 70 31 22        fmsub.d ft1,ft2,ft3,ft4
+    libdis_test+0x34:  c7 00 31 22        fmsub.d ft1,ft2,ft3,ft4,rne
+    libdis_test+0x38:  c7 10 31 22        fmsub.d ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x3c:  c7 20 31 22        fmsub.d ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x40:  c7 30 31 22        fmsub.d ft1,ft2,ft3,ft4,rup
+    libdis_test+0x44:  c7 40 31 22        fmsub.d ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x48:  cb 70 31 22        fnmsub.d ft1,ft2,ft3,ft4
+    libdis_test+0x4c:  cb 00 31 22        fnmsub.d ft1,ft2,ft3,ft4,rne
+    libdis_test+0x50:  cb 10 31 22        fnmsub.d ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x54:  cb 20 31 22        fnmsub.d ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x58:  cb 30 31 22        fnmsub.d ft1,ft2,ft3,ft4,rup
+    libdis_test+0x5c:  cb 40 31 22        fnmsub.d ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x60:  cf 70 31 22        fnmadd.d ft1,ft2,ft3,ft4
+    libdis_test+0x64:  cf 00 31 22        fnmadd.d ft1,ft2,ft3,ft4,rne
+    libdis_test+0x68:  cf 10 31 22        fnmadd.d ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x6c:  cf 20 31 22        fnmadd.d ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x70:  cf 30 31 22        fnmadd.d ft1,ft2,ft3,ft4,rup
+    libdis_test+0x74:  cf 40 31 22        fnmadd.d ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x78:  53 f4 24 03        fadd.d fs0,fs1,fs2
+    libdis_test+0x7c:  d3 04 39 03        fadd.d fs1,fs2,fs3,rne
+    libdis_test+0x80:  53 99 49 03        fadd.d fs2,fs3,fs4,rtz
+    libdis_test+0x84:  d3 29 5a 03        fadd.d fs3,fs4,fs5,rdn
+    libdis_test+0x88:  53 ba 6a 03        fadd.d fs4,fs5,fs6,rup
+    libdis_test+0x8c:  d3 4a 7b 03        fadd.d fs5,fs6,fs7,rmm
+    libdis_test+0x90:  53 f4 24 0b        fsub.d fs0,fs1,fs2
+    libdis_test+0x94:  d3 04 39 0b        fsub.d fs1,fs2,fs3,rne
+    libdis_test+0x98:  53 99 49 0b        fsub.d fs2,fs3,fs4,rtz
+    libdis_test+0x9c:  d3 29 5a 0b        fsub.d fs3,fs4,fs5,rdn
+    libdis_test+0xa0:  53 ba 6a 0b        fsub.d fs4,fs5,fs6,rup
+    libdis_test+0xa4:  d3 4a 7b 0b        fsub.d fs5,fs6,fs7,rmm
+    libdis_test+0xa8:  53 f4 24 13        fmul.d fs0,fs1,fs2
+    libdis_test+0xac:  d3 04 39 13        fmul.d fs1,fs2,fs3,rne
+    libdis_test+0xb0:  53 99 49 13        fmul.d fs2,fs3,fs4,rtz
+    libdis_test+0xb4:  d3 29 5a 13        fmul.d fs3,fs4,fs5,rdn
+    libdis_test+0xb8:  53 ba 6a 13        fmul.d fs4,fs5,fs6,rup
+    libdis_test+0xbc:  d3 4a 7b 13        fmul.d fs5,fs6,fs7,rmm
+    libdis_test+0xc0:  53 f4 24 1b        fdiv.d fs0,fs1,fs2
+    libdis_test+0xc4:  d3 04 39 1b        fdiv.d fs1,fs2,fs3,rne
+    libdis_test+0xc8:  53 99 49 1b        fdiv.d fs2,fs3,fs4,rtz
+    libdis_test+0xcc:  d3 29 5a 1b        fdiv.d fs3,fs4,fs5,rdn
+    libdis_test+0xd0:  53 ba 6a 1b        fdiv.d fs4,fs5,fs6,rup
+    libdis_test+0xd4:  d3 4a 7b 1b        fdiv.d fs5,fs6,fs7,rmm
+    libdis_test+0xd8:  53 f4 04 5a        fsqrt.d fs0,fs1
+    libdis_test+0xdc:  d3 04 09 5a        fsqrt.d fs1,fs2,rne
+    libdis_test+0xe0:  53 99 09 5a        fsqrt.d fs2,fs3,rtz
+    libdis_test+0xe4:  d3 29 0a 5a        fsqrt.d fs3,fs4,rdn
+    libdis_test+0xe8:  53 ba 0a 5a        fsqrt.d fs4,fs5,rup
+    libdis_test+0xec:  d3 4a 0b 5a        fsqrt.d fs5,fs6,rmm
+    libdis_test+0xf0:  53 85 c5 22        fsgnj.d fa0,fa1,fa2
+    libdis_test+0xf4:  53 95 c5 22        fsgnjn.d fa0,fa1,fa2
+    libdis_test+0xf8:  53 a5 c5 22        fsgnjx.d fa0,fa1,fa2
+    libdis_test+0xfc:  53 85 c5 2a        fmin.d fa0,fa1,fa2
+    libdis_test+0x100: 53 95 c5 2a        fmax.d fa0,fa1,fa2
+    libdis_test+0x104: 53 f4 14 40        fcvt.s.d fs0,fs1
+    libdis_test+0x108: d3 04 19 40        fcvt.s.d fs1,fs2,rne
+    libdis_test+0x10c: 53 99 19 40        fcvt.s.d fs2,fs3,rtz
+    libdis_test+0x110: d3 29 1a 40        fcvt.s.d fs3,fs4,rdn
+    libdis_test+0x114: 53 ba 1a 40        fcvt.s.d fs4,fs5,rup
+    libdis_test+0x118: d3 4a 1b 40        fcvt.s.d fs5,fs6,rmm
+    libdis_test+0x11c: 53 85 05 42        fcvt.d.s fa0,fa1
+    libdis_test+0x120: 53 25 7e a2        feq.d a0,ft8,ft7
+    libdis_test+0x124: d3 15 7e a2        flt.d a1,ft8,ft7
+    libdis_test+0x128: 53 06 7e a2        fle.d a2,ft8,ft7
+    libdis_test+0x12c: d3 16 0e e2        fclass.d a3,ft8
+    libdis_test+0x130: d3 f2 00 c2        fcvt.w.d t0,ft1
+    libdis_test+0x134: 53 03 01 c2        fcvt.w.d t1,ft2,rne
+    libdis_test+0x138: d3 93 01 c2        fcvt.w.d t2,ft3,rtz
+    libdis_test+0x13c: 53 2e 02 c2        fcvt.w.d t3,ft4,rdn
+    libdis_test+0x140: d3 be 02 c2        fcvt.w.d t4,ft5,rup
+    libdis_test+0x144: 53 4f 03 c2        fcvt.w.d t5,ft6,rmm
+    libdis_test+0x148: d3 f2 10 c2        fcvt.wu.d t0,ft1
+    libdis_test+0x14c: 53 03 11 c2        fcvt.wu.d t1,ft2,rne
+    libdis_test+0x150: d3 93 11 c2        fcvt.wu.d t2,ft3,rtz
+    libdis_test+0x154: 53 2e 12 c2        fcvt.wu.d t3,ft4,rdn
+    libdis_test+0x158: d3 be 12 c2        fcvt.wu.d t4,ft5,rup
+    libdis_test+0x15c: 53 4f 13 c2        fcvt.wu.d t5,ft6,rmm
+    libdis_test+0x160: d3 80 03 d2        fcvt.d.w ft1,t2
+    libdis_test+0x164: d3 80 13 d2        fcvt.d.wu ft1,t2
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32d.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32d.s
new file mode 100644
index 0000000..9cbb040
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32d.s
@@ -0,0 +1,132 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV32D instructions. Instructions are ordered per
+ * the ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	fld		ft1, (s2)
+	fld		ft1, -0x4(s2)
+	fld		ft1, 0x42(s2)
+	fsd		ft1, (s2)
+	fsd		ft1, -0x4(s2)
+	fsd		ft1, 0x42(s2)
+
+	fmadd.d		ft1, ft2, ft3, ft4
+	fmadd.d		ft1, ft2, ft3, ft4, rne
+	fmadd.d		ft1, ft2, ft3, ft4, rtz
+	fmadd.d		ft1, ft2, ft3, ft4, rdn
+	fmadd.d		ft1, ft2, ft3, ft4, rup
+	fmadd.d		ft1, ft2, ft3, ft4, rmm
+
+	fmsub.d		ft1, ft2, ft3, ft4
+	fmsub.d		ft1, ft2, ft3, ft4, rne
+	fmsub.d		ft1, ft2, ft3, ft4, rtz
+	fmsub.d		ft1, ft2, ft3, ft4, rdn
+	fmsub.d		ft1, ft2, ft3, ft4, rup
+	fmsub.d		ft1, ft2, ft3, ft4, rmm
+
+	fnmsub.d	ft1, ft2, ft3, ft4
+	fnmsub.d	ft1, ft2, ft3, ft4, rne
+	fnmsub.d	ft1, ft2, ft3, ft4, rtz
+	fnmsub.d	ft1, ft2, ft3, ft4, rdn
+	fnmsub.d	ft1, ft2, ft3, ft4, rup
+	fnmsub.d	ft1, ft2, ft3, ft4, rmm
+
+	fnmadd.d	ft1, ft2, ft3, ft4
+	fnmadd.d	ft1, ft2, ft3, ft4, rne
+	fnmadd.d	ft1, ft2, ft3, ft4, rtz
+	fnmadd.d	ft1, ft2, ft3, ft4, rdn
+	fnmadd.d	ft1, ft2, ft3, ft4, rup
+	fnmadd.d	ft1, ft2, ft3, ft4, rmm
+
+	fadd.d		fs0, fs1, fs2
+	fadd.d		fs1, fs2, fs3, rne
+	fadd.d		fs2, fs3, fs4, rtz
+	fadd.d		fs3, fs4, fs5, rdn
+	fadd.d		fs4, fs5, fs6, rup
+	fadd.d		fs5, fs6, fs7, rmm
+
+	fsub.d		fs0, fs1, fs2
+	fsub.d		fs1, fs2, fs3, rne
+	fsub.d		fs2, fs3, fs4, rtz
+	fsub.d		fs3, fs4, fs5, rdn
+	fsub.d		fs4, fs5, fs6, rup
+	fsub.d		fs5, fs6, fs7, rmm
+
+	fmul.d		fs0, fs1, fs2
+	fmul.d		fs1, fs2, fs3, rne
+	fmul.d		fs2, fs3, fs4, rtz
+	fmul.d		fs3, fs4, fs5, rdn
+	fmul.d		fs4, fs5, fs6, rup
+	fmul.d		fs5, fs6, fs7, rmm
+
+	fdiv.d		fs0, fs1, fs2
+	fdiv.d		fs1, fs2, fs3, rne
+	fdiv.d		fs2, fs3, fs4, rtz
+	fdiv.d		fs3, fs4, fs5, rdn
+	fdiv.d		fs4, fs5, fs6, rup
+	fdiv.d		fs5, fs6, fs7, rmm
+
+	fsqrt.d		fs0, fs1
+	fsqrt.d		fs1, fs2, rne
+	fsqrt.d		fs2, fs3, rtz
+	fsqrt.d		fs3, fs4, rdn
+	fsqrt.d		fs4, fs5, rup
+	fsqrt.d		fs5, fs6, rmm
+
+	fsgnj.d		fa0, fa1, fa2
+	fsgnjn.d	fa0, fa1, fa2
+	fsgnjx.d	fa0, fa1, fa2
+	fmin.d		fa0, fa1, fa2
+	fmax.d		fa0, fa1, fa2
+
+	fcvt.s.d	fs0, fs1
+	fcvt.s.d	fs1, fs2, rne
+	fcvt.s.d	fs2, fs3, rtz
+	fcvt.s.d	fs3, fs4, rdn
+	fcvt.s.d	fs4, fs5, rup
+	fcvt.s.d	fs5, fs6, rmm
+
+	fcvt.d.s	fa0, fa1
+
+	feq.d		a0, ft8, ft7
+	flt.d		a1, ft8, ft7
+	fle.d		a2, ft8, ft7
+	fclass.d	a3, ft8
+
+	fcvt.w.d	t0, ft1
+	fcvt.w.d	t1, ft2, rne
+	fcvt.w.d	t2, ft3, rtz
+	fcvt.w.d	t3, ft4, rdn
+	fcvt.w.d	t4, ft5, rup
+	fcvt.w.d	t5, ft6, rmm
+
+	fcvt.wu.d	t0, ft1
+	fcvt.wu.d	t1, ft2, rne
+	fcvt.wu.d	t2, ft3, rtz
+	fcvt.wu.d	t3, ft4, rdn
+	fcvt.wu.d	t4, ft5, rup
+	fcvt.wu.d	t5, ft6, rmm
+
+	fcvt.d.w	ft1, t2
+	fcvt.d.wu	ft1, t2
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32f.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32f.out
new file mode 100644
index 0000000..15264cf
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32f.out
@@ -0,0 +1,95 @@
+    libdis_test:       87 20 09 00        flw ft1,0x0(s2)
+    libdis_test+0x4:   87 20 c9 ff        flw ft1,-0x4(s2)
+    libdis_test+0x8:   87 20 29 04        flw ft1,0x42(s2)
+    libdis_test+0xc:   27 20 19 00        fsw ft1,0x0(s2)
+    libdis_test+0x10:  27 2e 19 fe        fsw ft1,-0x4(s2)
+    libdis_test+0x14:  27 21 19 04        fsw ft1,0x42(s2)
+    libdis_test+0x18:  c3 70 31 20        fmadd.s ft1,ft2,ft3,ft4
+    libdis_test+0x1c:  c3 00 31 20        fmadd.s ft1,ft2,ft3,ft4,rne
+    libdis_test+0x20:  c3 10 31 20        fmadd.s ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x24:  c3 20 31 20        fmadd.s ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x28:  c3 30 31 20        fmadd.s ft1,ft2,ft3,ft4,rup
+    libdis_test+0x2c:  c3 40 31 20        fmadd.s ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x30:  c7 70 31 20        fmsub.s ft1,ft2,ft3,ft4
+    libdis_test+0x34:  c7 00 31 20        fmsub.s ft1,ft2,ft3,ft4,rne
+    libdis_test+0x38:  c7 10 31 20        fmsub.s ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x3c:  c7 20 31 20        fmsub.s ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x40:  c7 30 31 20        fmsub.s ft1,ft2,ft3,ft4,rup
+    libdis_test+0x44:  c7 40 31 20        fmsub.s ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x48:  cb 70 31 20        fnmsub.s ft1,ft2,ft3,ft4
+    libdis_test+0x4c:  cb 00 31 20        fnmsub.s ft1,ft2,ft3,ft4,rne
+    libdis_test+0x50:  cb 10 31 20        fnmsub.s ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x54:  cb 20 31 20        fnmsub.s ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x58:  cb 30 31 20        fnmsub.s ft1,ft2,ft3,ft4,rup
+    libdis_test+0x5c:  cb 40 31 20        fnmsub.s ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x60:  cf 70 31 20        fnmadd.s ft1,ft2,ft3,ft4
+    libdis_test+0x64:  cf 00 31 20        fnmadd.s ft1,ft2,ft3,ft4,rne
+    libdis_test+0x68:  cf 10 31 20        fnmadd.s ft1,ft2,ft3,ft4,rtz
+    libdis_test+0x6c:  cf 20 31 20        fnmadd.s ft1,ft2,ft3,ft4,rdn
+    libdis_test+0x70:  cf 30 31 20        fnmadd.s ft1,ft2,ft3,ft4,rup
+    libdis_test+0x74:  cf 40 31 20        fnmadd.s ft1,ft2,ft3,ft4,rmm
+    libdis_test+0x78:  53 f4 24 01        fadd.s fs0,fs1,fs2
+    libdis_test+0x7c:  d3 04 39 01        fadd.s fs1,fs2,fs3,rne
+    libdis_test+0x80:  53 99 49 01        fadd.s fs2,fs3,fs4,rtz
+    libdis_test+0x84:  d3 29 5a 01        fadd.s fs3,fs4,fs5,rdn
+    libdis_test+0x88:  53 ba 6a 01        fadd.s fs4,fs5,fs6,rup
+    libdis_test+0x8c:  d3 4a 7b 01        fadd.s fs5,fs6,fs7,rmm
+    libdis_test+0x90:  53 f4 24 09        fsub.s fs0,fs1,fs2
+    libdis_test+0x94:  d3 04 39 09        fsub.s fs1,fs2,fs3,rne
+    libdis_test+0x98:  53 99 49 09        fsub.s fs2,fs3,fs4,rtz
+    libdis_test+0x9c:  d3 29 5a 09        fsub.s fs3,fs4,fs5,rdn
+    libdis_test+0xa0:  53 ba 6a 09        fsub.s fs4,fs5,fs6,rup
+    libdis_test+0xa4:  d3 4a 7b 09        fsub.s fs5,fs6,fs7,rmm
+    libdis_test+0xa8:  53 f4 24 11        fmul.s fs0,fs1,fs2
+    libdis_test+0xac:  d3 04 39 11        fmul.s fs1,fs2,fs3,rne
+    libdis_test+0xb0:  53 99 49 11        fmul.s fs2,fs3,fs4,rtz
+    libdis_test+0xb4:  d3 29 5a 11        fmul.s fs3,fs4,fs5,rdn
+    libdis_test+0xb8:  53 ba 6a 11        fmul.s fs4,fs5,fs6,rup
+    libdis_test+0xbc:  d3 4a 7b 11        fmul.s fs5,fs6,fs7,rmm
+    libdis_test+0xc0:  53 f4 24 19        fdiv.s fs0,fs1,fs2
+    libdis_test+0xc4:  d3 04 39 19        fdiv.s fs1,fs2,fs3,rne
+    libdis_test+0xc8:  53 99 49 19        fdiv.s fs2,fs3,fs4,rtz
+    libdis_test+0xcc:  d3 29 5a 19        fdiv.s fs3,fs4,fs5,rdn
+    libdis_test+0xd0:  53 ba 6a 19        fdiv.s fs4,fs5,fs6,rup
+    libdis_test+0xd4:  d3 4a 7b 19        fdiv.s fs5,fs6,fs7,rmm
+    libdis_test+0xd8:  53 f4 04 58        fsqrt.s fs0,fs1
+    libdis_test+0xdc:  d3 04 09 58        fsqrt.s fs1,fs2,rne
+    libdis_test+0xe0:  53 99 09 58        fsqrt.s fs2,fs3,rtz
+    libdis_test+0xe4:  d3 29 0a 58        fsqrt.s fs3,fs4,rdn
+    libdis_test+0xe8:  53 ba 0a 58        fsqrt.s fs4,fs5,rup
+    libdis_test+0xec:  d3 4a 0b 58        fsqrt.s fs5,fs6,rmm
+    libdis_test+0xf0:  53 85 c5 20        fsgnj.s fa0,fa1,fa2
+    libdis_test+0xf4:  53 95 c5 20        fsgnjn.s fa0,fa1,fa2
+    libdis_test+0xf8:  53 a5 c5 20        fsgnjx.s fa0,fa1,fa2
+    libdis_test+0xfc:  53 85 c5 28        fmin.s fa0,fa1,fa2
+    libdis_test+0x100: 53 95 c5 28        fmax.s fa0,fa1,fa2
+    libdis_test+0x104: d3 f2 00 c0        fcvt.w.s t0,ft1
+    libdis_test+0x108: 53 03 01 c0        fcvt.w.s t1,ft2,rne
+    libdis_test+0x10c: d3 93 01 c0        fcvt.w.s t2,ft3,rtz
+    libdis_test+0x110: 53 2e 02 c0        fcvt.w.s t3,ft4,rdn
+    libdis_test+0x114: d3 be 02 c0        fcvt.w.s t4,ft5,rup
+    libdis_test+0x118: 53 4f 03 c0        fcvt.w.s t5,ft6,rmm
+    libdis_test+0x11c: d3 f2 10 c0        fcvt.wu.s t0,ft1
+    libdis_test+0x120: 53 03 11 c0        fcvt.wu.s t1,ft2,rne
+    libdis_test+0x124: d3 93 11 c0        fcvt.wu.s t2,ft3,rtz
+    libdis_test+0x128: 53 2e 12 c0        fcvt.wu.s t3,ft4,rdn
+    libdis_test+0x12c: d3 be 12 c0        fcvt.wu.s t4,ft5,rup
+    libdis_test+0x130: 53 4f 13 c0        fcvt.wu.s t5,ft6,rmm
+    libdis_test+0x134: d3 82 00 e0        fmv.x.w t0,ft1
+    libdis_test+0x138: 53 25 7e a0        feq.s a0,ft8,ft7
+    libdis_test+0x13c: d3 15 7e a0        flt.s a1,ft8,ft7
+    libdis_test+0x140: 53 06 7e a0        fle.s a2,ft8,ft7
+    libdis_test+0x144: d3 16 0e e0        fclass.s a3,ft8
+    libdis_test+0x148: d3 f0 03 d0        fcvt.s.w ft1,t2
+    libdis_test+0x14c: 53 01 0e d0        fcvt.s.w ft2,t3,rne
+    libdis_test+0x150: d3 91 0e d0        fcvt.s.w ft3,t4,rtz
+    libdis_test+0x154: 53 22 0f d0        fcvt.s.w ft4,t5,rdn
+    libdis_test+0x158: d3 b2 0f d0        fcvt.s.w ft5,t6,rup
+    libdis_test+0x15c: 53 c3 0f d0        fcvt.s.w ft6,t6,rmm
+    libdis_test+0x160: d3 f0 13 d0        fcvt.s.wu ft1,t2
+    libdis_test+0x164: 53 01 1e d0        fcvt.s.wu ft2,t3,rne
+    libdis_test+0x168: d3 91 1e d0        fcvt.s.wu ft3,t4,rtz
+    libdis_test+0x16c: 53 22 1f d0        fcvt.s.wu ft4,t5,rdn
+    libdis_test+0x170: d3 b2 1f d0        fcvt.s.wu ft5,t6,rup
+    libdis_test+0x174: 53 c3 1f d0        fcvt.s.wu ft6,t6,rmm
+    libdis_test+0x178: 53 0d 0d f0        fmv.w.x fs10,s10
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32f.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32f.s
new file mode 100644
index 0000000..cc3dfd2
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32f.s
@@ -0,0 +1,137 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV32F instructions. Instructions are ordered per
+ * the ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	flw		ft1, (s2)
+	flw		ft1, -0x4(s2)
+	flw		ft1, 0x42(s2)
+	fsw		ft1, (s2)
+	fsw		ft1, -0x4(s2)
+	fsw		ft1, 0x42(s2)
+
+	fmadd.s		ft1, ft2, ft3, ft4
+	fmadd.s		ft1, ft2, ft3, ft4, rne
+	fmadd.s		ft1, ft2, ft3, ft4, rtz
+	fmadd.s		ft1, ft2, ft3, ft4, rdn
+	fmadd.s		ft1, ft2, ft3, ft4, rup
+	fmadd.s		ft1, ft2, ft3, ft4, rmm
+
+	fmsub.s		ft1, ft2, ft3, ft4
+	fmsub.s		ft1, ft2, ft3, ft4, rne
+	fmsub.s		ft1, ft2, ft3, ft4, rtz
+	fmsub.s		ft1, ft2, ft3, ft4, rdn
+	fmsub.s		ft1, ft2, ft3, ft4, rup
+	fmsub.s		ft1, ft2, ft3, ft4, rmm
+
+	fnmsub.s	ft1, ft2, ft3, ft4
+	fnmsub.s	ft1, ft2, ft3, ft4, rne
+	fnmsub.s	ft1, ft2, ft3, ft4, rtz
+	fnmsub.s	ft1, ft2, ft3, ft4, rdn
+	fnmsub.s	ft1, ft2, ft3, ft4, rup
+	fnmsub.s	ft1, ft2, ft3, ft4, rmm
+
+	fnmadd.s	ft1, ft2, ft3, ft4
+	fnmadd.s	ft1, ft2, ft3, ft4, rne
+	fnmadd.s	ft1, ft2, ft3, ft4, rtz
+	fnmadd.s	ft1, ft2, ft3, ft4, rdn
+	fnmadd.s	ft1, ft2, ft3, ft4, rup
+	fnmadd.s	ft1, ft2, ft3, ft4, rmm
+
+	fadd.s		fs0, fs1, fs2
+	fadd.s		fs1, fs2, fs3, rne
+	fadd.s		fs2, fs3, fs4, rtz
+	fadd.s		fs3, fs4, fs5, rdn
+	fadd.s		fs4, fs5, fs6, rup
+	fadd.s		fs5, fs6, fs7, rmm
+
+	fsub.s		fs0, fs1, fs2
+	fsub.s		fs1, fs2, fs3, rne
+	fsub.s		fs2, fs3, fs4, rtz
+	fsub.s		fs3, fs4, fs5, rdn
+	fsub.s		fs4, fs5, fs6, rup
+	fsub.s		fs5, fs6, fs7, rmm
+
+	fmul.s		fs0, fs1, fs2
+	fmul.s		fs1, fs2, fs3, rne
+	fmul.s		fs2, fs3, fs4, rtz
+	fmul.s		fs3, fs4, fs5, rdn
+	fmul.s		fs4, fs5, fs6, rup
+	fmul.s		fs5, fs6, fs7, rmm
+
+	fdiv.s		fs0, fs1, fs2
+	fdiv.s		fs1, fs2, fs3, rne
+	fdiv.s		fs2, fs3, fs4, rtz
+	fdiv.s		fs3, fs4, fs5, rdn
+	fdiv.s		fs4, fs5, fs6, rup
+	fdiv.s		fs5, fs6, fs7, rmm
+
+	fsqrt.s		fs0, fs1
+	fsqrt.s		fs1, fs2, rne
+	fsqrt.s		fs2, fs3, rtz
+	fsqrt.s		fs3, fs4, rdn
+	fsqrt.s		fs4, fs5, rup
+	fsqrt.s		fs5, fs6, rmm
+
+	fsgnj.s		fa0, fa1, fa2
+	fsgnjn.s	fa0, fa1, fa2
+	fsgnjx.s	fa0, fa1, fa2
+	fmin.s		fa0, fa1, fa2
+	fmax.s		fa0, fa1, fa2
+
+	fcvt.w.s	t0, ft1
+	fcvt.w.s	t1, ft2, rne
+	fcvt.w.s	t2, ft3, rtz
+	fcvt.w.s	t3, ft4, rdn
+	fcvt.w.s	t4, ft5, rup
+	fcvt.w.s	t5, ft6, rmm
+
+	fcvt.wu.s	t0, ft1
+	fcvt.wu.s	t1, ft2, rne
+	fcvt.wu.s	t2, ft3, rtz
+	fcvt.wu.s	t3, ft4, rdn
+	fcvt.wu.s	t4, ft5, rup
+	fcvt.wu.s	t5, ft6, rmm
+
+	fmv.x.w		t0, ft1
+	feq.s		a0, ft8, ft7
+	flt.s		a1, ft8, ft7
+	fle.s		a2, ft8, ft7
+	fclass.s	a3, ft8
+
+	fcvt.s.w	ft1, t2
+	fcvt.s.w	ft2, t3, rne
+	fcvt.s.w	ft3, t4, rtz
+	fcvt.s.w	ft4, t5, rdn
+	fcvt.s.w	ft5, t6, rup
+	fcvt.s.w	ft6, t6, rmm
+
+	fcvt.s.wu	ft1, t2
+	fcvt.s.wu	ft2, t3, rne
+	fcvt.s.wu	ft3, t4, rtz
+	fcvt.s.wu	ft4, t5, rdn
+	fcvt.s.wu	ft5, t6, rup
+	fcvt.s.wu	ft6, t6, rmm
+
+	fmv.w.x		fs10, s10
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32i.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32i.out
new file mode 100644
index 0000000..833a04c
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32i.out
@@ -0,0 +1,60 @@
+    libdis_test:      b7 00 00 00        lui ra,0x0
+    libdis_test+0x4:  b7 30 02 00        lui ra,0x23
+    libdis_test+0x8:  b7 f0 ff ff        lui ra,0xfffff
+    libdis_test+0xc:  97 00 00 00        auipc ra,0x0
+    libdis_test+0x10: 97 30 02 00        auipc ra,0x23
+    libdis_test+0x14: 97 f0 ff ff        auipc ra,0xfffff
+    libdis_test+0x18: 03 84 f4 7f        lb s0,0x7ff(s1)
+    libdis_test+0x1c: 83 84 04 00        lb s1,0x0(s1)
+    libdis_test+0x20: 03 89 04 80        lb s2,-0x800(s1)
+    libdis_test+0x24: 83 99 f4 7f        lh s3,0x7ff(s1)
+    libdis_test+0x28: 03 9a 04 00        lh s4,0x0(s1)
+    libdis_test+0x2c: 83 9a 04 80        lh s5,-0x800(s1)
+    libdis_test+0x30: 03 ab f4 7f        lw s6,0x7ff(s1)
+    libdis_test+0x34: 83 ab 04 00        lw s7,0x0(s1)
+    libdis_test+0x38: 03 ac 04 80        lw s8,-0x800(s1)
+    libdis_test+0x3c: 83 cb f4 7f        lbu s7,0x7ff(s1)
+    libdis_test+0x40: 03 cb 04 00        lbu s6,0x0(s1)
+    libdis_test+0x44: 83 ca 04 80        lbu s5,-0x800(s1)
+    libdis_test+0x48: 03 da f4 7f        lhu s4,0x7ff(s1)
+    libdis_test+0x4c: 83 d9 04 00        lhu s3,0x0(s1)
+    libdis_test+0x50: 03 d9 04 80        lhu s2,-0x800(s1)
+    libdis_test+0x54: a3 0f 53 7e        sb t0,0x7ff(t1)
+    libdis_test+0x58: 23 80 63 00        sb t1,0x0(t2)
+    libdis_test+0x5c: 23 00 7e 80        sb t2,-0x800(t3)
+    libdis_test+0x60: a3 1f c3 7f        sh t3,0x7ff(t1)
+    libdis_test+0x64: 23 90 d3 01        sh t4,0x0(t2)
+    libdis_test+0x68: 23 10 ee 81        sh t5,-0x800(t3)
+    libdis_test+0x6c: a3 2f d3 7f        sw t4,0x7ff(t1)
+    libdis_test+0x70: 23 a0 c3 01        sw t3,0x0(t2)
+    libdis_test+0x74: 23 20 7e 80        sw t2,-0x800(t3)
+    libdis_test+0x78: 93 80 42 00        addi ra,t0,0x4
+    libdis_test+0x7c: 93 80 c2 ff        addi ra,t0,-0x4
+    libdis_test+0x80: 93 a0 42 00        slti ra,t0,0x4
+    libdis_test+0x84: 93 a0 c2 ff        slti ra,t0,-0x4
+    libdis_test+0x88: 93 b0 42 00        sltiu ra,t0,0x4
+    libdis_test+0x8c: 93 b0 c2 ff        sltiu ra,t0,-0x4
+    libdis_test+0x90: 93 c0 42 00        xori ra,t0,0x4
+    libdis_test+0x94: 93 c0 c2 ff        xori ra,t0,-0x4
+    libdis_test+0x98: 93 e0 42 00        ori ra,t0,0x4
+    libdis_test+0x9c: 93 e0 c2 ff        ori ra,t0,-0x4
+    libdis_test+0xa0: 93 f0 42 00        andi ra,t0,0x4
+    libdis_test+0xa4: 93 f0 c2 ff        andi ra,t0,-0x4
+    libdis_test+0xa8: 93 1e 2f 01        slli t4,t5,0x12
+    libdis_test+0xac: 93 5e 3f 01        srli t4,t5,0x13
+    libdis_test+0xb0: 93 5e 4f 41        srai t4,t5,0x14
+    libdis_test+0xb4: 33 84 24 01        add s0,s1,s2
+    libdis_test+0xb8: b3 04 39 41        sub s1,s2,s3
+    libdis_test+0xbc: b3 19 5a 01        sll s3,s4,s5
+    libdis_test+0xc0: 33 aa 6a 01        slt s4,s5,s6
+    libdis_test+0xc4: 33 b5 15 00        sltu a0,a1,ra
+    libdis_test+0xc8: b3 4a 7b 01        xor s5,s6,s7
+    libdis_test+0xcc: 33 db 8b 01        srl s6,s7,s8
+    libdis_test+0xd0: b3 5b 9c 41        sra s7,s8,s9
+    libdis_test+0xd4: 33 ec ac 01        or s8,s9,s10
+    libdis_test+0xd8: b3 7c bd 01        and s9,s10,s11
+    libdis_test+0xdc: 0f 00 f0 0f        fence
+    libdis_test+0xe0: 0f 00 a0 05        fence ow, ir
+    libdis_test+0xe4: 0f 00 50 0a        fence ir, ow
+    libdis_test+0xe8: 0f 00 f0 0e        fence ior, iorw
+    libdis_test+0xec: 0f 10 00 00        fence.i
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32i.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32i.s
new file mode 100644
index 0000000..98938cf
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32i.s
@@ -0,0 +1,91 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV32I instructions. Instructions are ordered per
+ * the ISA manual. Supervisor and CSR instructions are elsewhere.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	lui	ra, 0x00
+	lui	ra, 0x23
+	lui	ra, 0xfffff
+	auipc	ra, 0x00
+	auipc	ra, 0x23
+	auipc	ra, 0xfffff
+	/*
+	 * Branches are not tested at this time as they basially always end up
+	 * wanting to create which ends up not really lending itself to
+	 * automated testing here. 
+	 */
+	lb	s0, 0x7ff(s1)
+	lb	s1, (s1)
+	lb	s2, -0x800(s1)
+	lh	s3, 0x7ff(s1)
+	lh	s4, (s1)
+	lh	s5, -0x800(s1)
+	lw	s6, 0x7ff(s1)
+	lw	s7, (s1)
+	lw	s8, -0x800(s1)
+	lbu	s7, 0x7ff(s1)
+	lbu	s6, (s1)
+	lbu	s5, -0x800(s1)
+	lhu	s4, 0x7ff(s1)
+	lhu	s3, (s1)
+	lhu	s2, -0x800(s1)
+	sb	t0, 0x7ff(t1)
+	sb	t1, (t2)
+	sb	t2, -0x800(t3)
+	sh	t3, 0x7ff(t1)
+	sh	t4, (t2)
+	sh	t5, -0x800(t3)
+	sw	t4, 0x7ff(t1)
+	sw	t3, (t2)
+	sw	t2, -0x800(t3)
+	addi	ra, t0, 0x4
+	addi	ra, t0, -0x4
+	slti	ra, t0, 0x4
+	slti	ra, t0, -0x4
+	sltiu	ra, t0, 0x4
+	sltiu	ra, t0, -0x4
+	xori	ra, t0, 0x4
+	xori	ra, t0, -0x4
+	ori	ra, t0, 0x4
+	ori	ra, t0, -0x4
+	andi	ra, t0, 0x4
+	andi	ra, t0, -0x4
+	slli	t4, t5, 0x12
+	srli	t4, t5, 0x13
+	srai	t4, t5, 0x14
+	add	s0, s1, s2
+	sub	s1, s2, s3
+	sll	s3, s4, s5
+	slt	s4, s5, s6
+	sltu	a0, a1, ra
+	xor	s5, s6, s7
+	srl	s6, s7, s8
+	sra	s7, s8, s9
+	or	s8, s9, s10
+	and	s9, s10, s11
+	fence
+	fence	ow, ir
+	fence	ir, ow
+	fence	ior, iorw
+	fence.i
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32m.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32m.out
new file mode 100644
index 0000000..87aa4e5
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32m.out
@@ -0,0 +1,8 @@
+    libdis_test:      33 84 24 03        mul s0,s1,s2
+    libdis_test+0x4:  b3 14 39 03        mulh s1,s2,s3
+    libdis_test+0x8:  33 a9 49 03        mulhsu s2,s3,s4
+    libdis_test+0xc:  b3 39 5a 03        mulhu s3,s4,s5
+    libdis_test+0x10: 33 ca 6a 03        div s4,s5,s6
+    libdis_test+0x14: b3 5a 7b 03        divu s5,s6,s7
+    libdis_test+0x18: 33 eb 8b 03        rem s6,s7,s8
+    libdis_test+0x1c: b3 7b 9c 03        remu s7,s8,s9
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32m.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32m.s
new file mode 100644
index 0000000..241fd5a
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.rv32m.s
@@ -0,0 +1,34 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of the RV32M instructions. Instructions are ordered per the
+ * ISA manual.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	mul	s0, s1, s2
+	mulh	s1, s2, s3
+	mulhsu	s2, s3, s4
+	mulhu	s3, s4, s5
+	div	s4, s5, s6
+	divu	s5, s6, s7
+	rem	s6, s7, s8
+	remu	s7, s8, s9
+.size libdis_test, [.-libdis_test]
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.supervisor.out b/usr/src/test/util-tests/tests/dis/risc-v/tst.supervisor.out
new file mode 100644
index 0000000..26299cc
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.supervisor.out
@@ -0,0 +1,7 @@
+    libdis_test:      73 00 00 00        ecall
+    libdis_test+0x4:  73 00 10 00        ebreak
+    libdis_test+0x8:  73 00 20 00        uret
+    libdis_test+0xc:  73 00 20 10        sret
+    libdis_test+0x10: 73 00 20 30        mret
+    libdis_test+0x14: 73 00 50 10        wfi
+    libdis_test+0x18: 73 80 62 12        sfence.vma t0,t1
diff --git a/usr/src/test/util-tests/tests/dis/risc-v/tst.supervisor.s b/usr/src/test/util-tests/tests/dis/risc-v/tst.supervisor.s
new file mode 100644
index 0000000..883a086
--- /dev/null
+++ b/usr/src/test/util-tests/tests/dis/risc-v/tst.supervisor.s
@@ -0,0 +1,32 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source.  A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2018, Joyent, Inc.
+ */
+
+/*
+ * Test our disassembly of supervisor instructions.
+ */
+
+.text
+.align 16
+.globl libdis_test
+.type libdis_test, @function
+libdis_test:
+	ecall
+	ebreak
+	uret
+	sret
+	mret
+	wfi
+	sfence.vma	t0, t1
+.size libdis_test, [.-libdis_test]