summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJerry Jelinek <jerry.jelinek@joyent.com>2020-03-30 11:59:04 +0000
committerJerry Jelinek <jerry.jelinek@joyent.com>2020-03-30 11:59:04 +0000
commit380d528f676476b9d6662f0edea853a36789f58b (patch)
tree5cb0437ff0b585ab3d6f3ad8aedf67f220464bb2
parentd8cab3215b93aa7d16090428ff303d6ff92263f7 (diff)
parent8c16a0e6d0b3d6a8b804825076383c61979302ec (diff)
downloadillumos-joyent-380d528f676476b9d6662f0edea853a36789f58b.tar.gz
[illumos-gate merge]
commit 8c16a0e6d0b3d6a8b804825076383c61979302ec 12404 audioemu10k: variable may be used uninitialized commit d52aae2365749461c362fde5a4c1a26a620cfbd3 12310 Add demangle(1) command commit a61ed2ce7a86a4d6428f2a83eb4739fae945447e 12258 Need native CCID driver commit ae6d4bc342613e6a5dc7b84b03ecdb0cc9cf7d26 12444 Intel v1 chip topo needs rank information Conflicts: usr/src/uts/common/sys/usb/clients/ccid/uccid.h usr/src/uts/common/sys/usb/clients/ccid/ccid.h usr/src/uts/common/io/usb/clients/ccid/ccid.c usr/src/uts/common/Makefile.files usr/src/test/os-tests/tests/uccid/yk-readonly.c usr/src/test/os-tests/tests/uccid/notxn-poll.c usr/src/test/os-tests/tests/uccid/modify.c usr/src/test/os-tests/tests/Makefile usr/src/man/man7d/ccid.7d usr/src/man/man1m/ccidadm.1m usr/src/lib/libcmdutils/common/nicenum.c usr/src/lib/cfgadm_plugins/ccid/common/cfga_ccid.c usr/src/common/ccid/atr.c usr/src/cmd/devfsadm/usb_link.c usr/src/cmd/ccidadm/ccidadm.c usr/src/cmd/ccidadm/Makefile
-rw-r--r--manifest9
-rw-r--r--usr/src/cmd/Makefile1
-rw-r--r--usr/src/cmd/ccidadm/Makefile7
-rw-r--r--usr/src/cmd/ccidadm/ccidadm.c2
-rw-r--r--usr/src/cmd/demangle/Makefile40
-rw-r--r--usr/src/cmd/demangle/demangle.c211
-rw-r--r--usr/src/cmd/devfsadm/usb_link.c4
-rw-r--r--usr/src/common/ccid/atr.c1
-rw-r--r--usr/src/lib/cfgadm_plugins/ccid/common/cfga_ccid.c7
-rw-r--r--usr/src/lib/fm/topo/modules/i86pc/chip/chip_intel.c206
-rw-r--r--usr/src/lib/libcmdutils/common/nicenum.c10
-rw-r--r--usr/src/lib/libdemangle/common/demangle-sys.h3
-rw-r--r--usr/src/lib/libdemangle/common/demangle.c40
-rw-r--r--usr/src/lib/libdemangle/common/mapfile-vers2
-rw-r--r--usr/src/man/man1/Makefile2
-rw-r--r--usr/src/man/man1/demangle.1119
-rw-r--r--usr/src/man/man1m/ccidadm.1m90
-rw-r--r--usr/src/man/man7d/ccid.7d142
-rw-r--r--usr/src/pkg/manifests/developer-object-file.mf3
-rw-r--r--usr/src/pkg/manifests/driver-misc-ccid.mf57
-rw-r--r--usr/src/pkg/manifests/system-library-libpcsc.mf32
-rw-r--r--usr/src/pkg/manifests/system-test-ostest.mf17
-rw-r--r--usr/src/test/os-tests/runfiles/default.run8
-rw-r--r--usr/src/test/os-tests/tests/uccid/modify.c28
-rw-r--r--usr/src/test/os-tests/tests/uccid/notxn-poll.c8
-rw-r--r--usr/src/test/os-tests/tests/uccid/yk-readonly.c26
-rw-r--r--usr/src/uts/common/io/audio/drv/audioemu10k/audioemu10k.c5
-rw-r--r--usr/src/uts/common/io/usb/clients/ccid/ccid.c153
-rw-r--r--usr/src/uts/common/sys/usb/clients/ccid/ccid.h18
-rw-r--r--usr/src/uts/common/sys/usb/clients/ccid/uccid.h8
30 files changed, 1084 insertions, 175 deletions
diff --git a/manifest b/manifest
index fd66326864..412059e65a 100644
--- a/manifest
+++ b/manifest
@@ -2534,6 +2534,7 @@ f usr/bin/date 0555 root bin
f usr/bin/dc 0555 root bin
f usr/bin/dd 0555 root bin
h usr/bin/decrypt=usr/lib/isaexec
+f usr/bin/demangle 0555 root bin
f usr/bin/deroff 0555 root bin
f usr/bin/devattr 0555 root bin
f usr/bin/devfree 0555 root bin
@@ -4788,6 +4789,9 @@ d usr/include/sys/usb 0755 root bin
d usr/include/sys/usb/clients 0755 root bin
d usr/include/sys/usb/clients/audio 0755 root bin
f usr/include/sys/usb/clients/audio/usb_audio.h 0644 root bin
+d usr/include/sys/usb/clients/ccid 0755 root bin
+f usr/include/sys/usb/clients/ccid/ccid.h 0644 root bin
+f usr/include/sys/usb/clients/ccid/uccid.h 0644 root bin
d usr/include/sys/usb/clients/hid 0755 root bin
f usr/include/sys/usb/clients/hid/hid.h 0644 root bin
d usr/include/sys/usb/clients/mass_storage 0755 root bin
@@ -4932,6 +4936,8 @@ f usr/include/wchar.h 0644 root bin
f usr/include/wchar_impl.h 0644 root bin
f usr/include/wctype.h 0644 root bin
f usr/include/widec.h 0644 root bin
+f usr/include/winscard.h 0644 root bin
+f usr/include/wintypes.h 0644 root bin
f usr/include/wordexp.h 0644 root bin
f usr/include/xlocale.h 0644 root bin
f usr/include/xti.h 0644 root bin
@@ -5292,6 +5298,7 @@ f usr/lib/amd64/libpanel.so.1 0755 root bin
s usr/lib/amd64/libpanel.so=libpanel.so.1
f usr/lib/amd64/libpcidb.so.1 0755 root bin
f usr/lib/amd64/libpcsc.so.1 0755 root bin
+s usr/lib/amd64/libpcsc.so=libpcsc.so.1
f usr/lib/amd64/libpctx.so.1 0755 root bin
s usr/lib/amd64/libpctx.so=libpctx.so.1
f usr/lib/amd64/libpicl.so.1 0755 root bin
@@ -6808,6 +6815,7 @@ f usr/lib/libpanel.so.1 0755 root bin
s usr/lib/libpanel.so=libpanel.so.1
f usr/lib/libpcidb.so.1 0755 root bin
f usr/lib/libpcsc.so.1 0755 root bin
+s usr/lib/libpcsc.so=libpcsc.so.1
f usr/lib/libpctx.so.1 0755 root bin
s usr/lib/libpctx.so=libpctx.so.1
f usr/lib/libpicl.so.1 0755 root bin
@@ -11949,6 +11957,7 @@ f usr/share/man/man1/date.1 0444 root bin
f usr/share/man/man1/dc.1 0444 root bin
f usr/share/man/man1/deallocate.1 0444 root bin
s usr/share/man/man1/decrypt.1=encrypt.1
+f usr/share/man/man1/demangle.1 0444 root bin
f usr/share/man/man1/deroff.1 0444 root bin
f usr/share/man/man1/dhcpinfo.1 0444 root bin
f usr/share/man/man1/diff.1 0444 root bin
diff --git a/usr/src/cmd/Makefile b/usr/src/cmd/Makefile
index 7a410a3a49..dd035124e9 100644
--- a/usr/src/cmd/Makefile
+++ b/usr/src/cmd/Makefile
@@ -119,6 +119,7 @@ COMMON_SUBDIRS= \
date \
dc \
dd \
+ demangle \
deroff \
devfsadm \
syseventd \
diff --git a/usr/src/cmd/ccidadm/Makefile b/usr/src/cmd/ccidadm/Makefile
index de9761ff9d..d1d9221c80 100644
--- a/usr/src/cmd/ccidadm/Makefile
+++ b/usr/src/cmd/ccidadm/Makefile
@@ -18,15 +18,12 @@ PROG= ccidadm
include ../Makefile.cmd
include ../Makefile.ctf
-ROOTCMDDIR = $(ROOTLIB)/ccid
CFLAGS += $(CCVERBOSE)
LDLIBS += -lofmt -lcmdutils
SRCS = ccidadm.c atr.c
OBJS = $(SRCS:%.c=%.o)
CPPFLAGS += -I$(SRC)/common/ccid
-ROOTCCIDFILES = $(PROG:%=$(ROOTCMDDIR)/%)
-
.KEEP_STATE:
$(PROG): $(OBJS)
@@ -43,9 +40,9 @@ $(PROG): $(OBJS)
all: $(PROG)
-install: all $(ROOTCMD)
+install: all $(ROOTUSRSBINPROG)
clean:
- $(RM) $(OBJS)
+ $(RM) $(OBJS) $(PROG)
include ../Makefile.targ
diff --git a/usr/src/cmd/ccidadm/ccidadm.c b/usr/src/cmd/ccidadm/ccidadm.c
index 1d3c2bcbfc..6309ecfcc8 100644
--- a/usr/src/cmd/ccidadm/ccidadm.c
+++ b/usr/src/cmd/ccidadm/ccidadm.c
@@ -220,7 +220,7 @@ static boolean_t
ccidadm_list_slot_usable_str(uccid_cmd_status_t *ucs, char *buf,
uint_t buflen)
{
- char *un = "";
+ const char *un = "";
ccid_class_features_t feat;
uint_t prot = CCID_CLASS_F_SHORT_APDU_XCHG | CCID_CLASS_F_EXT_APDU_XCHG;
uint_t param = CCID_CLASS_F_AUTO_PARAM_NEG | CCID_CLASS_F_AUTO_PPS;
diff --git a/usr/src/cmd/demangle/Makefile b/usr/src/cmd/demangle/Makefile
new file mode 100644
index 0000000000..8366ac85f3
--- /dev/null
+++ b/usr/src/cmd/demangle/Makefile
@@ -0,0 +1,40 @@
+#
+# 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 2020 Joyent, Inc.
+#
+
+PROG= demangle
+OBJS= demangle.o
+SRCS= $(OBJS:%.o=%.c)
+
+include $(SRC)/cmd/Makefile.cmd
+include $(SRC)/cmd/Makefile.ctf
+
+CSTD= $(CSTD_GNU99)
+
+LDLIBS += -ldemangle-sys -lcustr
+
+.KEEP_STATE:
+
+all: $(PROG)
+
+$(PROG): $(OBJS)
+ $(LINK.c) $(OBJS) -o $@ $(LDLIBS)
+ $(POST_PROCESS)
+
+clean:
+ $(RM) $(OBJS)
+
+install: all $(ROOTPROG)
+
+include $(SRC)/cmd/Makefile.targ
diff --git a/usr/src/cmd/demangle/demangle.c b/usr/src/cmd/demangle/demangle.c
new file mode 100644
index 0000000000..33a68edc9e
--- /dev/null
+++ b/usr/src/cmd/demangle/demangle.c
@@ -0,0 +1,211 @@
+/*
+ * 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 2020 Joyent, Inc.
+ */
+
+#include <ctype.h>
+#include <demangle-sys.h>
+#include <err.h>
+#include <errno.h>
+#include <libcustr.h>
+#include <locale.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+#define _(x) gettext(x)
+
+locale_t c_locale;
+
+static int do_symbols(sysdem_lang_t, int, char * const *);
+static int do_input(sysdem_lang_t, FILE *restrict, FILE *restrict);
+static int do_demangle(const char *, sysdem_lang_t, FILE *);
+static void appendc(custr_t *, char);
+static void xputc(int, FILE *);
+
+static void
+usage(void)
+{
+ (void) fprintf(stderr, _("Usage: %s [-l lang] [sym...]\n"),
+ getprogname());
+ exit(2);
+}
+
+int
+main(int argc, char * const *argv)
+{
+ sysdem_lang_t lang = SYSDEM_LANG_AUTO;
+ int c;
+ int ret;
+
+ (void) setlocale(LC_ALL, "");
+
+#if !defined(TEXT_DOMAIN)
+#define TEXT_DOMAIN "SYS_TEST"
+#endif
+ (void) textdomain(TEXT_DOMAIN);
+
+ /*
+ * For detecting symbol boundaries, we want to use the C locale
+ * definitions for use in isalnum_l().
+ */
+ if ((c_locale = newlocale(LC_CTYPE_MASK, "C", NULL)) == NULL)
+ err(EXIT_FAILURE, _("failed to construct C locale"));
+
+ while ((c = getopt(argc, argv, "hl:")) != -1) {
+ switch (c) {
+ case 'l':
+ if (sysdem_parse_lang(optarg, &lang))
+ break;
+
+ errx(EXIT_FAILURE, _("Unsupported language '%s'\n"),
+ optarg);
+ case 'h':
+ case '?':
+ usage();
+ }
+ }
+
+ argc -= optind;
+ argv += optind;
+
+ if (argc > 0)
+ ret = do_symbols(lang, argc, argv);
+ else
+ ret = do_input(lang, stdin, stdout);
+
+ return ((ret < 0) ? EXIT_FAILURE : EXIT_SUCCESS);
+}
+
+static int
+do_symbols(sysdem_lang_t lang, int argc, char * const *argv)
+{
+ int ret = 0;
+
+ for (int i = 0; i < argc; i++) {
+ if (do_demangle(argv[i], lang, stdout) < 0)
+ ret = -1;
+ else
+ xputc('\n', stdout);
+ }
+
+ return (ret);
+}
+
+static int
+do_input(sysdem_lang_t lang, FILE *restrict in, FILE *restrict out)
+{
+ custr_t *word = NULL;
+ int c;
+ int ret = 0;
+ boolean_t in_symbol = B_FALSE;
+
+ if (custr_alloc(&word) != 0)
+ err(EXIT_FAILURE, _("failed to allocate memory"));
+
+ while ((c = fgetc(in)) != EOF) {
+ if (in_symbol) {
+ /*
+ * All currently supported mangling formats only use
+ * alphanumeric characters, '.', '_', or '$' in
+ * mangled names. Once we've seen the potential start
+ * of a symbol ('_'), we accumulate subsequent
+ * charaters into 'word'. If we encounter a character
+ * that is not a part of that set ([A-Za-z0-9._$]), we
+ * treat it as a delimiter, we stop accumulating
+ * characters into word, and we attempt to demangle the
+ * accumulated string in 'word' by calling
+ * demangle_custr().
+ *
+ * Similar utilities like c++filt behave in a similar
+ * fashion when reading from stdin to allow for
+ * demangling of symbols embedded in surrounding text.
+ */
+ if (isalnum_l(c, c_locale) || c == '.' || c == '_' ||
+ c == '$') {
+ appendc(word, c);
+ continue;
+ }
+
+ /*
+ * Hit a symbol boundary, attempt to demangle what
+ * we've accumulated in word and reset word.
+ */
+ if (do_demangle(custr_cstr(word), lang, out) < 0)
+ ret = -1;
+
+ custr_reset(word);
+ in_symbol = B_FALSE;
+ }
+
+ if (c != '_') {
+ xputc(c, out);
+ } else {
+ in_symbol = B_TRUE;
+ appendc(word, c);
+ }
+ }
+
+ if (ferror(in))
+ err(EXIT_FAILURE, _("error reading input"));
+
+ /*
+ * If we were accumulating characters for a symbol and hit EOF,
+ * attempt to demangle what we accumulated.
+ */
+ if (custr_len(word) > 0 && do_demangle(custr_cstr(word), lang, out) < 0)
+ ret = -1;
+
+ custr_free(word);
+ return (ret);
+}
+
+/*
+ * Attempt to demangle 'sym' as a symbol for 'lang' and write the result
+ * to 'out'. If 'sym' could not be demangled as 'lang' symbol, the original
+ * string is output instead.
+ *
+ * If an error other than 'not a mangled symbol' is encountered (e.g. ENOMEM),
+ * a warning is sent to stderr and -1 is returned. Otherwise, 0 is returned
+ * (including when 'sym' is merely not a mangled symbol of 'lang').
+ */
+static int
+do_demangle(const char *sym, sysdem_lang_t lang, FILE *out)
+{
+ char *demangled = sysdemangle(sym, lang, NULL);
+
+ if (demangled == NULL && errno != EINVAL) {
+ warn(_("error while demangling '%s'"), sym);
+ return (-1);
+ }
+
+ if (fprintf(out, "%s", (demangled != NULL) ? demangled : sym) < 0)
+ err(EXIT_FAILURE, _("failed to write to output"));
+
+ free(demangled);
+ return (0);
+}
+
+static void
+appendc(custr_t *cus, char c)
+{
+ if (custr_appendc(cus, c) == 0)
+ return;
+ err(EXIT_FAILURE, _("failed to save character from input"));
+}
+
+static void
+xputc(int c, FILE *out)
+{
+ if (fputc(c, out) < 0)
+ err(EXIT_FAILURE, _("failed to write output"));
+}
diff --git a/usr/src/cmd/devfsadm/usb_link.c b/usr/src/cmd/devfsadm/usb_link.c
index 80996a1773..b233f85daf 100644
--- a/usr/src/cmd/devfsadm/usb_link.c
+++ b/usr/src/cmd/devfsadm/usb_link.c
@@ -316,8 +316,8 @@ usb_process(di_minor_t minor, di_node_t node)
return (DEVFSADM_CONTINUE);
}
- if (strcmp(di_minor_nodetype(minor), DDI_NT_CCID_ATTACHMENT_POINT)
- == 0) {
+ if (strcmp(di_minor_nodetype(minor), DDI_NT_CCID_ATTACHMENT_POINT) ==
+ 0) {
ccid_create_link(p_path, minor_nm, node, minor);
free(l_path);
free(p_path);
diff --git a/usr/src/common/ccid/atr.c b/usr/src/common/ccid/atr.c
index db83c91ceb..d43aa585c5 100644
--- a/usr/src/common/ccid/atr.c
+++ b/usr/src/common/ccid/atr.c
@@ -20,7 +20,6 @@
#include "atr.h"
#include <sys/debug.h>
-#include <sys/limits.h>
#include <sys/sysmacros.h>
#ifdef _KERNEL
diff --git a/usr/src/lib/cfgadm_plugins/ccid/common/cfga_ccid.c b/usr/src/lib/cfgadm_plugins/ccid/common/cfga_ccid.c
index 4ce28c2aec..3a44580306 100644
--- a/usr/src/lib/cfgadm_plugins/ccid/common/cfga_ccid.c
+++ b/usr/src/lib/cfgadm_plugins/ccid/common/cfga_ccid.c
@@ -376,10 +376,9 @@ cfga_list_ext(const char *ap, struct cfga_list_data **ap_list, int *nlist,
}
/*
- * XXX We should probably have a way to indicate that there's an error
- * when the ICC is basically foobar'd. We should also allow the status
- * ioctl to know that the slot is resetting or something else is going
- * on I guess.
+ * We should probably have a way to indicate that there's an error when
+ * the ICC is basically foobar'd. We should also allow the status ioctl
+ * to know that the slot is resetting or something else is going on.
*/
if ((ucs.ucs_class.ccd_dwFeatures &
(CCID_CLASS_F_SHORT_APDU_XCHG | CCID_CLASS_F_EXT_APDU_XCHG)) == 0) {
diff --git a/usr/src/lib/fm/topo/modules/i86pc/chip/chip_intel.c b/usr/src/lib/fm/topo/modules/i86pc/chip/chip_intel.c
index 4c5da1e8cb..df6e2b6f95 100644
--- a/usr/src/lib/fm/topo/modules/i86pc/chip/chip_intel.c
+++ b/usr/src/lib/fm/topo/modules/i86pc/chip/chip_intel.c
@@ -73,6 +73,8 @@
#define DIMM_HDRL "hdrl-enabled"
#define DIMM_HDRL_PARITY "hdrl-parity"
#define DIMM_3DRANK "3d-subranks"
+#define RANK_STATUS "dimm-rank-status"
+#define RANK_SIZE "dimm-rank-size"
static const topo_pgroup_info_t dimm_channel_pgroup =
{ PGNAME(CHAN), TOPO_STABILITY_PRIVATE, TOPO_STABILITY_PRIVATE, 1 };
@@ -156,7 +158,7 @@ mc_add_ranks(topo_mod_t *mod, tnode_t *dnode, nvlist_t *auth, int dimm,
(void) topo_node_fru_set(rnode, NULL, 0, &err);
if (topo_method_register(mod, rnode, rank_methods) < 0)
- whinge(mod, &err, "rank_create: "
+ whinge(mod, &err, "mc_add_ranks: "
"topo_method_register failed");
if (! is_xpv() && topo_method_register(mod, rnode,
@@ -455,6 +457,102 @@ mc_nb_create(topo_mod_t *mod, uint16_t chip_smbid, tnode_t *pnode,
}
static int
+mc_rank_create_v1(topo_mod_t *mod, tnode_t *pnode, nvlist_t *auth,
+ nvlist_t *dimm_nvl, uint64_t rsize, uint32_t id)
+{
+ nvlist_t *fmri;
+ tnode_t *rank;
+ int err;
+ boolean_t *disabled;
+ uint_t ndisabled;
+ const char *status;
+
+ fmri = topo_mod_hcfmri(mod, pnode, FM_HC_SCHEME_VERSION, RANK, id,
+ NULL, auth, NULL, NULL, NULL);
+ if (fmri == NULL) {
+ whinge(mod, NULL, "mc_rank_create_v1: topo_mod_hcfmri "
+ "failed\n");
+ return (-1);
+ }
+
+ if ((rank = topo_node_bind(mod, pnode, RANK, id, fmri)) == NULL) {
+ whinge(mod, NULL, "mc_rank_create_v1: node bind failed for "
+ "DIMM\n");
+ nvlist_free(fmri);
+ return (-1);
+ }
+
+ if (topo_method_register(mod, rank, rank_methods) < 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: topo_method_register "
+ "failed for rank_methods: %d", topo_mod_errno(mod));
+ }
+
+ if (!is_xpv() && topo_method_register(mod, rank,
+ ntv_page_retire_methods) != 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: topo_method_register "
+ "failed for page retire: %d", topo_mod_errno(mod));
+ }
+
+ if (topo_node_asru_set(rank, fmri, TOPO_ASRU_COMPUTE, &err) != 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: failed to set asru: %d",
+ err);
+ nvlist_free(fmri);
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ if (topo_node_fru_set(rank, NULL, 0, &err) != 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: fru set failed: "
+ "%d\n", err);
+ nvlist_free(fmri);
+ return (topo_mod_seterrno(mod, err));
+ }
+ nvlist_free(fmri);
+
+ if (topo_pgroup_create(rank, &rank_pgroup, &err) != 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: failed to create "
+ "property group: %d\n", err);
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ /*
+ * The traditional northbridge driver broke down each rank into the
+ * interleave targets that led to it. At this time, the imc driver (the
+ * only v1 provider) does not supply that information and therefore we
+ * cannot set that. Instead we just set basic properties on this, the
+ * size of the rank and whether or not it is disabled.
+ */
+ if (rsize != 0 && topo_prop_set_uint64(rank, PGNAME(RANK), RANK_SIZE,
+ TOPO_PROP_IMMUTABLE, rsize, &err) != 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: failed to set %s "
+ "property: %d", RANK_SIZE, err);
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ if (nvlist_lookup_boolean_array(dimm_nvl, MCINTEL_NVLIST_V1_DIMM_RDIS,
+ &disabled, &ndisabled) != 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: Couldn't find disabled "
+ "ranks array");
+ return (topo_mod_seterrno(mod, EMOD_UNKNOWN));
+ }
+
+ if (id >= ndisabled) {
+ whinge(mod, NULL, "mc_rank_create_v1: Found rank %u with id "
+ "larger than supported by hardware", id);
+ return (topo_mod_seterrno(mod, EMOD_UNKNOWN));
+ }
+
+ status = disabled[id] ? "disabled" : "enabled";
+ if (topo_prop_set_string(rank, PGNAME(RANK), RANK_STATUS,
+ TOPO_PROP_IMMUTABLE, status, &err) != 0) {
+ whinge(mod, NULL, "mc_rank_create_v1: failed to set %s "
+ "property: %d", RANK_STATUS, err);
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ return (0);
+}
+
+static int
mc_dimm_create_v1(topo_mod_t *mod, tnode_t *pnode, nvlist_t *auth,
nvlist_t *dimm_nvl, uint_t id)
{
@@ -462,8 +560,8 @@ mc_dimm_create_v1(topo_mod_t *mod, tnode_t *pnode, nvlist_t *auth,
tnode_t *dimm;
nvlist_t *fmri;
boolean_t present;
- uint64_t size, density;
- uint32_t cols, rows, width, ranks, banks;
+ uint64_t size, density, rsize;
+ uint32_t cols, rows, width, ranks, banks, i;
/*
* First, figure out if this DIMM is present. If not, we don't bother
@@ -510,8 +608,10 @@ mc_dimm_create_v1(topo_mod_t *mod, tnode_t *pnode, nvlist_t *auth,
&size) == 0) {
char buf[64];
const char *suffix;
+ uint64_t tsize;
ret |= topo_prop_set_uint64(dimm, PGNAME(DIMM), DIMM_SIZE,
TOPO_PROP_IMMUTABLE, size, &err);
+ tsize = size;
/*
* We must manually cons up a dimm-size property which is the
@@ -520,68 +620,115 @@ mc_dimm_create_v1(topo_mod_t *mod, tnode_t *pnode, nvlist_t *auth,
* controller drivers did this in the driver, but we instead opt
* to do so in user land.
*/
- if (size >= (1ULL << 40)) {
- size /= (1ULL << 40);
+ if (tsize >= (1ULL << 40)) {
+ tsize /= (1ULL << 40);
suffix = "T";
- } else if (size >= (1ULL << 30)) {
- size /= (1ULL << 30);
+ } else if (tsize >= (1ULL << 30)) {
+ tsize /= (1ULL << 30);
suffix = "G";
- } else if (size >= (1ULL << 20)) {
- size /= (1ULL << 20);
+ } else if (tsize >= (1ULL << 20)) {
+ tsize /= (1ULL << 20);
suffix = "M";
} else {
suffix = NULL;
}
if (suffix != NULL) {
- if (snprintf(buf, sizeof (buf), "%"PRIu64"%s", size,
+ if (snprintf(buf, sizeof (buf), "%"PRIu64"%s", tsize,
suffix) >= sizeof (buf)) {
whinge(mod, NULL, "failed to construct DIMM "
"size due to buffer overflow");
return (topo_mod_seterrno(mod, EMOD_UNKNOWN));
}
- ret |= topo_prop_set_string(dimm, PGNAME(DIMM),
+ ret = topo_prop_set_string(dimm, PGNAME(DIMM),
DIMM_STRING_SIZE, TOPO_PROP_IMMUTABLE, buf, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
}
+ } else {
+ size = 0;
}
if (nvlist_lookup_uint32(dimm_nvl, MCINTEL_NVLIST_V1_DIMM_NCOLS,
&cols) == 0) {
- ret |= topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_COL,
+ ret = topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_COL,
TOPO_PROP_IMMUTABLE, cols, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
}
if (nvlist_lookup_uint32(dimm_nvl, MCINTEL_NVLIST_V1_DIMM_NROWS,
&rows) == 0) {
- ret |= topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_ROW,
+ ret = topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_ROW,
TOPO_PROP_IMMUTABLE, rows, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
}
if (nvlist_lookup_uint64(dimm_nvl, MCINTEL_NVLIST_V1_DIMM_DENSITY,
&density) == 0) {
- ret |= topo_prop_set_uint64(dimm, PGNAME(DIMM), DIMM_DENSITY,
+ ret = topo_prop_set_uint64(dimm, PGNAME(DIMM), DIMM_DENSITY,
TOPO_PROP_IMMUTABLE, density, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
}
if (nvlist_lookup_uint32(dimm_nvl, MCINTEL_NVLIST_V1_DIMM_WIDTH,
&width) == 0) {
- ret |= topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_WIDTH,
+ ret = topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_WIDTH,
TOPO_PROP_IMMUTABLE, width, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
}
if (nvlist_lookup_uint32(dimm_nvl, MCINTEL_NVLIST_V1_DIMM_BANKS,
&banks) == 0) {
- ret |= topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_BANKS,
+ ret = topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_BANKS,
TOPO_PROP_IMMUTABLE, banks, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
+ } else {
+ banks = 0;
}
if (nvlist_lookup_uint32(dimm_nvl, MCINTEL_NVLIST_V1_DIMM_RANKS,
&ranks) == 0) {
- ret |= topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_RANKS,
+ ret = topo_prop_set_uint32(dimm, PGNAME(DIMM), DIMM_RANKS,
TOPO_PROP_IMMUTABLE, ranks, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
+ }
+
+ if (ret != 0) {
+ return (-1);
+ }
+
+ if (topo_node_range_create(mod, dimm, RANK, 0, ranks - 1) < 0) {
+ whinge(mod, NULL, "mc_dimm_create_v1: rank node range "
+ "create failed\n");
+ return (-1);
+ }
+
+ rsize = 0;
+ if (size != 0 && banks != 0) {
+ rsize = size / banks;
}
- return (ret != 0 ? -1 : 0);
+ for (i = 0; i < ranks; i++) {
+ if (mc_rank_create_v1(mod, dimm, auth, dimm_nvl, rsize, i) !=
+ 0) {
+ return (-1);
+ }
+ }
+
+ return (0);
}
static int
@@ -657,12 +804,12 @@ mc_imc_create_v1(topo_mod_t *mod, tnode_t *pnode, const char *name,
uint_t nchans, i;
if (mkrsrc(mod, pnode, name, id, auth, &fmri) != 0) {
- whinge(mod, NULL, "mc_nb_create_v1: mkrsrc failed\n");
+ whinge(mod, NULL, "mc_imc_create_v1: mkrsrc failed\n");
return (-1);
}
if ((mcnode = topo_node_bind(mod, pnode, name, id, fmri)) == NULL) {
- whinge(mod, NULL, "mc_nb_create_v1: node bind failed"
+ whinge(mod, NULL, "mc_imc_create_v1: node bind failed"
" for memory-controller\n");
nvlist_free(fmri);
return (-1);
@@ -670,13 +817,13 @@ mc_imc_create_v1(topo_mod_t *mod, tnode_t *pnode, const char *name,
nvlist_free(fmri);
if (topo_node_fru_set(mcnode, NULL, 0, &err) != 0) {
- whinge(mod, NULL, "mc_nb_create_v1: fru set failed: "
+ whinge(mod, NULL, "mc_imc_create_v1: fru set failed: "
"%d\n", err);
return (topo_mod_seterrno(mod, err));
}
if (topo_pgroup_create(mcnode, &mc_pgroup, &err) != 0) {
- whinge(mod, NULL, "mc_nb_create_v1: failed to create "
+ whinge(mod, NULL, "mc_imc_create_v1: failed to create "
"property group: %d\n", err);
return (topo_mod_seterrno(mod, err));
}
@@ -689,14 +836,20 @@ mc_imc_create_v1(topo_mod_t *mod, tnode_t *pnode, const char *name,
if (nvlist_lookup_boolean_value(mc_nvl, MCINTEL_NVLIST_V1_MC_ECC,
&ecc) == 0) {
const char *pval = ecc ? "enabled" : "disabled";
- ret |= topo_prop_set_string(mcnode, PGNAME(MCT), MC_PROP_ECC,
+ ret = topo_prop_set_string(mcnode, PGNAME(MCT), MC_PROP_ECC,
TOPO_PROP_IMMUTABLE, pval, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
}
if (nvlist_lookup_string(mc_nvl, MCINTEL_NVLIST_V1_MC_POLICY,
&page) == 0) {
- ret |= topo_prop_set_string(mcnode, PGNAME(MCT), MC_PROP_POLICY,
+ ret = topo_prop_set_string(mcnode, PGNAME(MCT), MC_PROP_POLICY,
TOPO_PROP_IMMUTABLE, page, &err);
+ if (ret != 0) {
+ return (topo_mod_seterrno(mod, err));
+ }
}
if (nvlist_lookup_string(mc_nvl, MCINTEL_NVLIST_V1_MC_CHAN_MODE,
@@ -704,9 +857,6 @@ mc_imc_create_v1(topo_mod_t *mod, tnode_t *pnode, const char *name,
cmode = NULL;
}
- if (ret != 0)
- return (-1);
-
if (nvlist_lookup_nvlist_array(mc_nvl, MCINTEL_NVLIST_V1_MC_CHANNELS,
&channels, &nchans) != 0) {
whinge(mod, NULL, "mc_imc_create_v1: missing channels entry");
@@ -746,7 +896,7 @@ mc_nb_create_v1(topo_mod_t *mod, tnode_t *pnode, const char *name,
if (topo_node_range_create(mod, pnode, name, 0, nmc - 1) < 0) {
whinge(mod, NULL,
- "mc_nb_create: node range create failed\n");
+ "mc_nb_create_v1: node range create failed\n");
return (-1);
}
diff --git a/usr/src/lib/libcmdutils/common/nicenum.c b/usr/src/lib/libcmdutils/common/nicenum.c
index 9b9a8fcd5e..a9161c422c 100644
--- a/usr/src/lib/libcmdutils/common/nicenum.c
+++ b/usr/src/lib/libcmdutils/common/nicenum.c
@@ -45,13 +45,11 @@ nicenum_scale(uint64_t n, size_t units, char *buf, size_t buflen,
uint64_t divisor = 1;
int index = 0;
int rc = 0;
- int spclen = 0;
- char *spc = "";
+ const char *spc = "";
char u;
if (flags & NN_UNIT_SPACE) {
spc = " ";
- spclen = 1;
}
if (units == 0)
@@ -92,7 +90,7 @@ nicenum_scale(uint64_t n, size_t units, char *buf, size_t buflen,
u = " KMGTPE"[index];
if (index == 0) {
- rc = snprintf(buf, buflen, "%llu", n);
+ rc = snprintf(buf, buflen, "%llu%s", n, spc);
} else if (n % divisor == 0) {
/*
* If this is an even multiple of the base, always display
@@ -102,7 +100,7 @@ nicenum_scale(uint64_t n, size_t units, char *buf, size_t buflen,
} else {
/*
* We want to choose a precision that reflects the best choice
- * for fitting in 5 characters. This can get rather tricky
+ * for fitting in the buffer. This can get rather tricky
* when we have numbers that are very close to an order of
* magnitude. For example, when displaying 10239 (which is
* really 9.999K), we want only a single place of precision
@@ -113,7 +111,7 @@ nicenum_scale(uint64_t n, size_t units, char *buf, size_t buflen,
int i;
for (i = 2; i >= 0; i--) {
if ((rc = snprintf(buf, buflen, "%.*f%s%c", i,
- (double)n / divisor, spc, u)) <= 5 + spclen)
+ (double)n / divisor, spc, u)) <= (buflen - 1))
break;
}
}
diff --git a/usr/src/lib/libdemangle/common/demangle-sys.h b/usr/src/lib/libdemangle/common/demangle-sys.h
index 05776ee5ee..3452d39667 100644
--- a/usr/src/lib/libdemangle/common/demangle-sys.h
+++ b/usr/src/lib/libdemangle/common/demangle-sys.h
@@ -11,7 +11,7 @@
/*
* Copyright 2017 Jason King
- * Copyright 2018, Joyent, Inc.
+ * Copyright 2019 Joyent, Inc.
*/
#ifndef _DEMANGLE_SYS_H
@@ -34,6 +34,7 @@ typedef struct sysdem_alloc_s {
void (*free)(void *, size_t);
} sysdem_ops_t;
+boolean_t sysdem_parse_lang(const char *, sysdem_lang_t *);
char *sysdemangle(const char *, sysdem_lang_t, sysdem_ops_t *);
#ifdef __cplusplus
diff --git a/usr/src/lib/libdemangle/common/demangle.c b/usr/src/lib/libdemangle/common/demangle.c
index 4f8e9ad678..b6db356416 100644
--- a/usr/src/lib/libdemangle/common/demangle.c
+++ b/usr/src/lib/libdemangle/common/demangle.c
@@ -21,6 +21,7 @@
#include <pthread.h>
#include <sys/ctype.h>
#include <sys/debug.h>
+#include <sys/sysmacros.h>
#include <stdarg.h>
#include "demangle-sys.h"
#include "demangle_int.h"
@@ -31,19 +32,40 @@ static pthread_once_t debug_once = PTHREAD_ONCE_INIT;
volatile boolean_t demangle_debug;
FILE *debugf = stderr;
+static struct {
+ const char *str;
+ sysdem_lang_t lang;
+} lang_tbl[] = {
+ { "auto", SYSDEM_LANG_AUTO },
+ { "c++", SYSDEM_LANG_CPP },
+ { "rust", SYSDEM_LANG_RUST },
+};
+
static const char *
langstr(sysdem_lang_t lang)
{
- switch (lang) {
- case SYSDEM_LANG_AUTO:
- return ("auto");
- case SYSDEM_LANG_CPP:
- return ("c++");
- case SYSDEM_LANG_RUST:
- return ("rust");
- default:
- return ("invalid");
+ size_t i;
+
+ for (i = 0; i < ARRAY_SIZE(lang_tbl); i++) {
+ if (lang == lang_tbl[i].lang)
+ return (lang_tbl[i].str);
}
+ return ("invalid");
+}
+
+boolean_t
+sysdem_parse_lang(const char *str, sysdem_lang_t *langp)
+{
+ size_t i;
+
+ for (i = 0; i < ARRAY_SIZE(lang_tbl); i++) {
+ if (strcmp(str, lang_tbl[i].str) == 0) {
+ *langp = lang_tbl[i].lang;
+ return (B_TRUE);
+ }
+ }
+
+ return (B_FALSE);
}
static sysdem_lang_t
diff --git a/usr/src/lib/libdemangle/common/mapfile-vers b/usr/src/lib/libdemangle/common/mapfile-vers
index 48c11ef0d7..2207547185 100644
--- a/usr/src/lib/libdemangle/common/mapfile-vers
+++ b/usr/src/lib/libdemangle/common/mapfile-vers
@@ -11,6 +11,7 @@
#
# Copyright 2017 Jason King
+# Copyright 2019 Joyent, Inc.
#
#
@@ -30,6 +31,7 @@ $mapfile_version 2
SYMBOL_VERSION ILLUMOSprivate {
global:
+ sysdem_parse_lang;
sysdemangle;
local:
*;
diff --git a/usr/src/man/man1/Makefile b/usr/src/man/man1/Makefile
index d7904100eb..c80c00d8ed 100644
--- a/usr/src/man/man1/Makefile
+++ b/usr/src/man/man1/Makefile
@@ -14,6 +14,7 @@
# Copyright 2018 Nexenta Systems, Inc.
# Copyright 2014 Garrett D'Amore <garrett@damore.org>
# Copyright 2019 OmniOS Community Edition (OmniOSce) Association.
+# Copyright 2020 Joyent, Inc.
#
include $(SRC)/Makefile.master
@@ -95,6 +96,7 @@ MANFILES= acctcom.1 \
date.1 \
dc.1 \
deallocate.1 \
+ demangle.1 \
deroff.1 \
dhcpinfo.1 \
diff.1 \
diff --git a/usr/src/man/man1/demangle.1 b/usr/src/man/man1/demangle.1
new file mode 100644
index 0000000000..ca2dbef35a
--- /dev/null
+++ b/usr/src/man/man1/demangle.1
@@ -0,0 +1,119 @@
+.\" The contents of this file are subject to the terms of the
+.\" Common Development and Distribution License (the "License").
+.\" You may not use this file except in compliance with the License.
+.\"
+.\" You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+.\" or http://www.opensolaris.org/os/licensing.
+.\" See the License for the specific language governing permissions
+.\" and limitations under the License.
+.\"
+.\" When distributing Covered Code, include this CDDL HEADER in each
+.\" file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+.\" If applicable, add the following below this CDDL HEADER, with the
+.\" fields enclosed by brackets "[]" replaced with your own identifying
+.\" information: Portions Copyright [yyyy] [name of copyright owner]
+.\"
+.\" Copyright 2020 Joyent, Inc.
+.\"
+.Dd March 3, 2020
+.Dt DEMANGLE 1
+.Os
+.Sh NAME
+.Nm demangle
+.Nd demangle symbols
+.Sh SYNOPSIS
+.Nm
+.Oo
+.Fl l
+.Ar lang
+.Oc
+.Op Ar symbol Ns ...
+.Sh DESCRIPTION
+The
+.Nm
+utility attempts to detect mangled symbols and transform them back into a
+more human friendly version of the symbol.
+.Pp
+Some languages allow the same identifier to refer to multiple things
+(functions, variables, etc\&.) where some additional context such as
+parameter types, return types, etc\&. are used to disambiguate between the
+symbols sharing the same name.
+When compiling such languages into an executable form, most binary formats
+do not allow for duplicate symbol names or provide a way to disambiguate
+between duplicate names.
+.Pp
+To solve this problem, many languages will use the additional context from
+the source code to transform the symbol name into a unique name.
+This process is called name mangling.
+While the resulting name is predictable, the mangled names are often difficult
+for humans to interpret.
+.Pp
+The
+.Nm
+utility can be invoked in one of two ways.
+In the first method,
+.Ar symbol
+is demangled and the result is written to standard out, one line per input
+.Ar symbol .
+If any input
+.Ar symbol
+cannot be demangled, the original value of
+.Ar symbol
+is output unchanged.
+In the second method,
+.Nm
+reads standard in, and whenever it encounters a potential symbol, it will
+attempt to replace the symbol in stdandard out with the demangled version.
+If the symbol cannot be demangled, it is output unchanged.
+.Pp
+For either method, if an error other than attempting to demangle an non-mangled
+symbol (e.g. out of memory), that error will be written to standard error.
+.Sh OPTIONS
+.Bl -tag -width Fl
+.It Fl l Ar lang
+Treat all potential symbols as symbols from
+.Ar lang .
+By default,
+.Nm
+will attempt to detect the language and demangle symbols for all supported
+languages.
+Current supported values of
+.Ar lang
+are:
+.Bl -tag -width rust -offset indent
+.It c++
+The C++ mangling format defined by the Itanium ABI.
+While the mangling format was originally defined for the Itanium processor, g++
+and clang use this format for all their supported platforms (including x86 and
+SPARC).
+.It rust
+The legacy rust mangling format.
+.It auto
+Attempt to detect the language automatically (default).
+.El
+.El
+.Sh EXIT STATUS
+.Ex -std
+.Sh EXAMPLES
+.Sy Example 1
+Demangle symbols given as command line arguments.
+.Bd -literal
+% demangle '_ZGVN9__gnu_cxx16bitmap_allocatorIwE13_S_mem_blocksE'
+guard variable for __gnu_cxx::bitmap_allocator<wchar_t>::_S_mem_blocks
+%
+.Ed
+.Pp
+.Sy Example 2
+Demangle symbols from the output of another command.
+.Bd -literal
+% grep slice rust.c | head -1
+ T("__ZN4core5slice89_$LT$impl$u20$core..iter..traits..IntoIterator$u20$for$u20$$RF$$u27$a$u20$$u5b$T$u5d$$GT$9into_iter17h450e234d27262170E",
+% grep slice rust.c | head -1 | demangle
+ T("core::slice::<impl core::iter::traits::IntoIterator for &'a [T]>::into_iter::h450e234d27262170",
+%
+.Ed
+.Sh INTERFACE STABILITY
+The command line options are
+.Sy Uncommitted .
+The output format is
+.Sy Not-an-Interface .
diff --git a/usr/src/man/man1m/ccidadm.1m b/usr/src/man/man1m/ccidadm.1m
index 686db8cb46..d1a09e25cf 100644
--- a/usr/src/man/man1m/ccidadm.1m
+++ b/usr/src/man/man1m/ccidadm.1m
@@ -18,14 +18,14 @@
.Nm ccidadm
.Nd CCID administration utility
.Sh SYNOPSIS
-.Nm /usr/lib/ccid/ccidadm
-.Ar list
-.Nm /usr/lib/ccid/ccidadm
-.Ar atr
+.Nm
+.Cm list
+.Nm
+.Cm atr
.Op Fl pvx
.Op Ar device
-.Nm /usr/lib/ccid/ccidadm
-.Ar reader
+.Nm
+.Cm reader
.Op Ar device
.Sh DESCRIPTION
The
@@ -48,7 +48,8 @@ Any command
.Nm
understands.
See section
-.Sx COMMANDS .
+.Sx COMMANDS
+for more information.
.It Ar device
Specifies a CCID reader or a slot, either as absolute path to the device node
or in a short-hand form.
@@ -85,11 +86,11 @@ in the system.
A human-readable summary of the ATR data is printed when no flags are given.
The following options can be used to alter the output of the
.Cm atr
-command::
+command:
.Bl -tag -width Ds
.It Fl v
Verbose output, the individual bytes of the ATR are printed and decoded
-bit-by-bit in a human-readable form.
+in a human-readable form.
Additionally the historic data in the ATR is printed as a hexadecimal dump.
.It Fl x
The complete ATR is printed as a hexadecimal dump.
@@ -105,7 +106,75 @@ If no device is given, the command will print the capabilities of all attached
CCID readers.
.El
.Sh EXIT STATUS
-.Ex -std
+The
+.Nm
+utility exits 0 on success, 1 on any error opening or accessing the device, and
+2 if no command or an unknown command are given.
+.Sh EXAMPLES
+.Bl -tag -width ""
+.It Sy Example 1: List all CCID devices
+.Bd -literal
+# ccidadm list
+PRODUCT DEVICE CARD STATE TRANSPORT SUPPORTED
+Yubikey 4 OTP+U2F+CCID ccid0/slot0 activated APDU (T=1) supported
+Yubikey 4 OTP+U2F+CCID ccid1/slot0 unactivated APDU supported
+Smart Card Reader USB ccid2/slot0 missing TPDU unsupported
+Smart Card Reader USB ccid3/slot0 unactivated TPDU unsupported
+.Ed
+.It Sy Example 2: Get the ATR of a Yubikey
+.Bd -literal
+# ccidadm atr ccid0/slot0
+ATR for ccid0/slot0 (18 bytes):
+ICC supports protocol(s): T=1
+Card protocol is negotiable; starts with default T=1 parameters
+Reader will run ICC at ICC's Di/Fi values
+T=1 properties that would be negotiated:
+ + Fi/Fmax Index: 1 (Fi 372/Fmax 5 MHz)
+ + Di Index: 3 (Di 4)
+ + Checksum: LRC
+ + Extra Guardtime: 0
+ + BWI: 1
+ + CWI: 5
+ + Clock Stop: 0 (disallowed)
+ + IFSC: 254
+ + CCID Supports NAD: no
+.Ed
+.It Sy Example 2: Get capabilities of a Smart Card Reader
+.Bd -literal
+# ccidadm reader ccid3
+Reader ccid3, CCID class v1.0 device:
+ Product: Smart Card Reader USB
+ Serial: <unknown>
+ Slots Present: 1
+ Maximum Busy Slots: 1
+ Supported Voltages:
+ + 5.0 V
+ + 3.0 V
+ + 1.8 V
+ Supported Protocols:
+ + T=0
+ + T=1
+ Default Clock: 3.69 MHz
+ Maximum Clock: 3.69 MHz
+ Supported Clock Rates: 1
+ Default Data Rate: 9.92 Kbps
+ Maximum Data Rate: 318 Kbps
+ Supported Data Rates: 19
+ Maximum IFSD (T=1 only): 254
+ Synchronous Protocols Supported:
+ + 2-Wire Support
+ + 3-Wire Support
+ + I2C Support
+ Device Features:
+ + Automatic ICC clock frequency change
+ + Automatic baud rate change
+ + Automatic PPS made by CCID
+ + CCID can set ICC in clock stop mode
+ + NAD value other than zero accepted
+ + TPDU support
+ Maximum Message Length: 271 bytes
+.Ed
+.El
.Sh INTERFACE STABILITY
The command line interface of
.Nm
@@ -117,4 +186,5 @@ is
.Sy Not-an-Interface
and may change any time.
.Sh SEE ALSO
+.Xr cfgadm 1M ,
.Xr ccid 7D
diff --git a/usr/src/man/man7d/ccid.7d b/usr/src/man/man7d/ccid.7d
index 86ada626e9..f5158b0d0d 100644
--- a/usr/src/man/man7d/ccid.7d
+++ b/usr/src/man/man7d/ccid.7d
@@ -110,7 +110,7 @@ When a program is finished, it must explicitly end the transaction,
which may have the side effect of resetting the ICC.
If a program with an open transaction crashes or closes the file
descriptor without taking other actions, then the transaction will be
-automatically closed.
+automatically closed and the ICC will be reset.
Without a transaction open, it will still be possible to issue ioctls
that obtain the status of the slot and the reader.
.Pp
@@ -159,13 +159,6 @@ The card has been removed from the slot.
An hardware error has occurred, or the CCID reader has been disconnected.
.El
.Pp
-If
-.Xr poll 2
-is called while no transaction is active, none of these events will ever occur
-and
-.Xr poll 2
-may block indefinitely if no timeout is given.
-.Pp
One important note is that readers with multiple slots often still only
allow I/O a single command to be outstanding across all of the slots in
the system.
@@ -214,7 +207,7 @@ status information.
.Pp
To perform general I/O to the card, a program must be in the context of
a transaction as discussed in the
-.Sx I/O model
+.Sx I/O Model
section.
To open a transaction, a program must issue the
.Dv UCCID_CMD_TXN_BEGIN
@@ -288,7 +281,7 @@ the fields of which have the following meanings:
.Bl -tag -width Fa
.It Fa uint32_t ucs_version
Indicates the current version of the structure.
-Should be set to
+This should be set to
.Dv UCCID_CURRENT_VERSION .
.It Fa uint32_t ucs_status
This value is ignored when issuing the command.
@@ -342,7 +335,7 @@ for the TPDU T=1 protocol.
.It Fa ccid_params_t ucs_params
The CCID parameters available on the card.
.El
-.Ss UCCID_CMD_TXN_BEGIN
+.Ss Ic UCCID_CMD_TXN_BEGIN
This command is used to begin a transaction.
The command will block until exclusive access is available to the
caller.
@@ -356,7 +349,7 @@ with the following members:
.Bl -tag -width Fa
.It Fa uint32_t ucs_version
Indicates the current version of the structure.
-Should be set to
+This should be set to
.Dv UCCID_CURRENT_VERSION .
.It Fa uint32_t uct_flags
Flags that impact the behavior of the command.
@@ -370,7 +363,7 @@ immediately.
.Pp
If an unknown flag is specified, an error will be returned.
.El
-.Ss UCCID_CMD_TXN_END
+.Ss Ic UCCID_CMD_TXN_END
The
.Dv UCCID_CMD_TXN_END
command is used to end a transaction and relinquish exclusive access
@@ -382,7 +375,7 @@ with the following members:
.Bl -tag -width Fa
.It Fa uint32_t uct_version
Indicates the current version of the structure.
-Should be set to
+This should be set to
.Dv UCCID_CURRENT_VERSION .
.It Fa uint32_t uct_flags
.Bl -tag -width Dv
@@ -399,7 +392,7 @@ time.
If the device is closed without ending a transaction first, then the ICC
will be reset.
.El
-.Ss UCCID_CMD_ICC_MODIFY
+.Ss Ic UCCID_CMD_ICC_MODIFY
This command can be used to change the state of an ICC, if present.
.Pp
The command uses the structure
@@ -408,7 +401,7 @@ with the following members:
.Bl -tag -width Fa
.It Fa uint32_t uci_version
Indicates the current version of the structure.
-Should be set to
+This should be set to
.Dv UCCID_CURRENT_VERSION .
.It Fa uint32_t uci_action
The action to be taken on the ICC.
@@ -422,7 +415,7 @@ Power off the ICC.
Perform a warm reset of the ICC.
.El
.El
-.Ss FIONREAD
+.Ss Ic FIONREAD
This command returns the size in bytes of a command response available
for reading with
.Xr read 2 .
@@ -432,11 +425,116 @@ pointed to by the argument.
.Sh SYSTEM CALLS
This section lists the different system calls that may be issued to a
CCID device.
-.Ss open
-.Ss close
-.Ss write
-.Ss read
-.Ss poll
+.Ss Xr open 2
+.Nm
+slot device nodes can be opened using
+.Xr open 2 .
+Non-blocking operation can be selected by using the
+.Dv O_NONBLOCK
+flag when opening the device node.
+A device node opened for read-only operations will not allow creating
+transactions or doing I/O, but it will allow the ICC/reader status to
+be queried.
+.Ss Xr close 2
+When no longer needed by a program, a device node can be closed with
+.Xr close 2 .
+If a transaction is still active when a device node is closed, the transaction
+will be ended automatically and the ICC will be reset.
+Any unread data is discarded.
+.Ss Xr ioctl 2
+The
+.Xr ioctl 2
+system call can be used to start or end a transaction, query the reply size for
+.Xr read 2 ,
+query the ICC and CCID reader status, or change the state of an ICC in a reader.
+See section
+.Sx IOCTLS
+for details.
+.Ss Xr write 2
+Within an active transaction the
+.Xr write 2
+system call can be used to transfer an APDU (application protocol data unit) to
+an ICC, one single complete APDU at a time.
+Partial writes or writing more than one APDU at a time are not supported.
+The data returned by the ICC must be consumed by a subsequent
+.Xr read 2
+call before
+.Xr write 2
+can be called again within the same transaction.
+.Pp
+The following errors for
+.Xr write 2
+have specific meaning in
+.Nm :
+.Bl -tag -width Dv
+.It Dv E2BIG
+The number of bytes to write is larger than the maximum APDU length supported by
+.Nm ,
+currently defined as 261 bytes.
+.It Dv EACCES
+The device is opened read-only, or no transaction is active.
+.It Dv EBUSY
+There is unread data from a previous call to
+.Xr write 2 .
+.It Dv ENOTSUP
+The reader and/or ICC is unsupported for I/O.
+.It Dv ENXIO
+The ICC is inactive and can't be used for I/O.
+.It Dv ENODEV
+The CCID reader has been disconnected.
+.El
+.Ss Xr read 2
+Within an active transaction the
+.Xr read 2
+system call is used to read the reply from an ICC following sending an APDU with
+.Xr write 2 .
+The whole reply needs to be read with a single call to
+.Xr read 2 .
+The size of the reply can be queried before reading by issuing the
+.Dv FIONREAD
+ioctl.
+See section
+.Sx IOCTLS
+for details.
+.Pp
+The following errors for
+.Xr read 2
+have specific meaning in
+.Nm :
+.Bl -tag -width Dv
+.It Dv EACCES
+No transaction is active.
+.It Dv EBUSY
+Another thread is already blocked in
+.Xr read 2
+waiting for data.
+.It Dv EOVERFLOW
+The buffer size is too small to fit the reply.
+.It Dv ENODATA
+No
+.Xr write 2
+was issued before and consequently there is no reply to be read.
+.It Dv ENODEV
+The CCID reader has been disconnected.
+.El
+.Ss Xr poll 2
+Within an active transaction the
+.Xr poll 2
+system call is used to wait for status changes on a device node.
+See section
+.Sx I/O model
+for details.
+.Pp
+The following errors for
+.Xr poll 2
+have specific meaning in
+.Nm :
+.Bl -tag -width Dv
+.It Dv EACCES
+No transaction is active.
+.It Dv ENODEV
+The CCID reader has been disconnected.
+.El
.Sh SEE ALSO
.Xr ccidadm 1M ,
.Xr cfgadm 1M ,
diff --git a/usr/src/pkg/manifests/developer-object-file.mf b/usr/src/pkg/manifests/developer-object-file.mf
index 5519e67d93..21d064fb9f 100644
--- a/usr/src/pkg/manifests/developer-object-file.mf
+++ b/usr/src/pkg/manifests/developer-object-file.mf
@@ -22,6 +22,7 @@
#
# Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
# Copyright 2019 OmniOS Community Edition (OmniOSce) Association.
+# Copyright 2020 Joyent, Inc.
#
set name=pkg.fmri value=pkg:/developer/object-file@$(PKGVERS)
@@ -53,6 +54,7 @@ file path=usr/bin/$(ARCH64)/mcs mode=0555
file path=usr/bin/$(ARCH64)/nm mode=0555
file path=usr/bin/$(ARCH64)/size mode=0555
file path=usr/bin/ar mode=0555
+file path=usr/bin/demangle mode=0555
file path=usr/bin/dis mode=0555
file path=usr/bin/dump mode=0555
file path=usr/bin/elfdump mode=0555
@@ -95,6 +97,7 @@ file path=usr/share/lib/ccs/ncform
file path=usr/share/lib/ccs/nrform
file path=usr/share/lib/ccs/yaccpar
file path=usr/share/man/man1/ar.1
+file path=usr/share/man/man1/demangle.1
file path=usr/share/man/man1/dis.1
file path=usr/share/man/man1/dump.1
file path=usr/share/man/man1/elfdump.1
diff --git a/usr/src/pkg/manifests/driver-misc-ccid.mf b/usr/src/pkg/manifests/driver-misc-ccid.mf
new file mode 100644
index 0000000000..e0d1ca0155
--- /dev/null
+++ b/usr/src/pkg/manifests/driver-misc-ccid.mf
@@ -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 2019, Joyent Inc.
+#
+
+#
+# The default for payload-bearing actions in this package is to appear in the
+# global zone only. See the include file for greater detail, as well as
+# information about overriding the defaults.
+#
+set name=pkg.fmri value=pkg:/driver/misc/ccid@$(PKGVERS)
+set name=pkg.description \
+ value="Driver for USB Chip Card Interface Devices (CCID)"
+set name=pkg.summary value="CCID driver"
+set name=info.classification \
+ value=org.opensolaris.category.2008:System/Hardware
+set name=variant.arch value=i386
+dir path=kernel group=sys variant.opensolaris.zone=global
+dir path=kernel/drv group=sys variant.opensolaris.zone=global
+dir path=kernel/drv/$(ARCH64) group=sys variant.opensolaris.zone=global
+dir path=usr group=sys
+dir path=usr/include
+dir path=usr/include/sys
+dir path=usr/include/sys/usb
+dir path=usr/include/sys/usb/clients
+dir path=usr/include/sys/usb/clients/ccid
+dir path=usr/lib/cfgadm variant.opensolaris.zone=global
+dir path=usr/lib/cfgadm/$(ARCH64) variant.opensolaris.zone=global
+dir path=usr/sbin variant.opensolaris.zone=global
+dir path=usr/share
+dir path=usr/share/man
+dir path=usr/share/man/man1m variant.opensolaris.zone=global
+dir path=usr/share/man/man7d
+driver name=ccid alias=usbif,classb class=misc perms="* 0600 root sys"
+file path=kernel/drv/$(ARCH64)/ccid group=sys variant.opensolaris.zone=global
+file path=usr/include/sys/usb/clients/ccid/ccid.h
+file path=usr/include/sys/usb/clients/ccid/uccid.h
+file path=usr/lib/cfgadm/$(ARCH64)/ccid.so.1 variant.opensolaris.zone=global
+file path=usr/lib/cfgadm/ccid.so.1 variant.opensolaris.zone=global
+file path=usr/sbin/ccidadm mode=0555 variant.opensolaris.zone=global
+file path=usr/share/man/man1m/ccidadm.1m variant.opensolaris.zone=global
+file path=usr/share/man/man7d/ccid.7d
+license lic_CDDL license=lic_CDDL
+link path=usr/lib/cfgadm/$(ARCH64)/ccid.so target=./ccid.so.1 \
+ variant.opensolaris.zone=global
+link path=usr/lib/cfgadm/ccid.so target=./ccid.so.1 \
+ variant.opensolaris.zone=global
diff --git a/usr/src/pkg/manifests/system-library-libpcsc.mf b/usr/src/pkg/manifests/system-library-libpcsc.mf
new file mode 100644
index 0000000000..fbf60f6595
--- /dev/null
+++ b/usr/src/pkg/manifests/system-library-libpcsc.mf
@@ -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 2019, Joyent Inc.
+#
+
+set name=pkg.fmri value=pkg:/system/library/libpcsc@$(PKGVERS)
+set name=pkg.description \
+ value="PC/SC compatible library for Smart Card access"
+set name=info.classification \
+ value=org.opensolaris.category.2008:System/Libraries
+set name=variant.arch value=$(ARCH)
+dir path=usr group=sys
+dir path=usr/include
+dir path=usr/lib
+dir path=usr/lib/$(ARCH64)
+file path=usr/include/winscard.h
+file path=usr/include/wintypes.h
+file path=usr/lib/$(ARCH64)/libpcsc.so.1
+file path=usr/lib/libpcsc.so.1
+link path=usr/lib/$(ARCH64)/libpcsc.so target=./libpcsc.so.1
+link path=usr/lib/libpcsc.so target=./libpcsc.so.1
+depend fmri=driver/misc/ccid type=require
diff --git a/usr/src/pkg/manifests/system-test-ostest.mf b/usr/src/pkg/manifests/system-test-ostest.mf
index dbaabe6dcd..6e20cc2b8e 100644
--- a/usr/src/pkg/manifests/system-test-ostest.mf
+++ b/usr/src/pkg/manifests/system-test-ostest.mf
@@ -35,6 +35,7 @@ dir path=opt/os-tests/tests/secflags
dir path=opt/os-tests/tests/sigqueue
dir path=opt/os-tests/tests/sockfs
dir path=opt/os-tests/tests/stress
+dir path=opt/os-tests/tests/uccid
file path=opt/os-tests/README mode=0444
file path=opt/os-tests/bin/ostest mode=0555
file path=opt/os-tests/runfiles/default.run mode=0444
@@ -85,6 +86,22 @@ file path=opt/os-tests/tests/sockfs/nosignal mode=0555
file path=opt/os-tests/tests/sockfs/sockpair mode=0555
file path=opt/os-tests/tests/spoof-ras mode=0555
file path=opt/os-tests/tests/stress/dladm-kstat mode=0555
+file path=opt/os-tests/tests/uccid/atrparse mode=0555
+file path=opt/os-tests/tests/uccid/excl-badread mode=0555
+file path=opt/os-tests/tests/uccid/excl-basic mode=0555
+file path=opt/os-tests/tests/uccid/excl-close mode=0555
+file path=opt/os-tests/tests/uccid/excl-loop mode=0555
+file path=opt/os-tests/tests/uccid/excl-nonblock mode=0555
+file path=opt/os-tests/tests/uccid/excl-reset mode=0555
+file path=opt/os-tests/tests/uccid/modify mode=0555
+file path=opt/os-tests/tests/uccid/notxn-poll mode=0555
+file path=opt/os-tests/tests/uccid/pollin mode=0555
+file path=opt/os-tests/tests/uccid/pollout mode=0555
+file path=opt/os-tests/tests/uccid/status mode=0555
+file path=opt/os-tests/tests/uccid/txn-pollerr mode=0555
+file path=opt/os-tests/tests/uccid/yk mode=0555
+file path=opt/os-tests/tests/uccid/yk-poll mode=0555
+file path=opt/os-tests/tests/uccid/yk-readonly mode=0555
file path=opt/os-tests/tests/writev.32 mode=0555
file path=opt/os-tests/tests/writev.64 mode=0555
license cr_Sun license=cr_Sun
diff --git a/usr/src/test/os-tests/runfiles/default.run b/usr/src/test/os-tests/runfiles/default.run
index 4db81dc30e..2313f65f7b 100644
--- a/usr/src/test/os-tests/runfiles/default.run
+++ b/usr/src/test/os-tests/runfiles/default.run
@@ -104,3 +104,11 @@ tests = ['atrparse']
[/opt/os-tests/tests/imc_test]
arch = i86pc
+
+#
+# Except atrparse all tests require special hardware (CCID YubiKey) to run,
+# hence they aren't included in the default runfile.
+#
+[/opt/os-tests/tests/uccid]
+arch = i86pc
+tests = ['atrparse']
diff --git a/usr/src/test/os-tests/tests/uccid/modify.c b/usr/src/test/os-tests/tests/uccid/modify.c
index 1ac44f3ba4..137c461701 100644
--- a/usr/src/test/os-tests/tests/uccid/modify.c
+++ b/usr/src/test/os-tests/tests/uccid/modify.c
@@ -53,14 +53,36 @@ main(int argc, char *argv[])
err(EXIT_FAILURE, "failed to open %s", argv[1]);
}
- /* try power off the card outside of a transaction */
+ /* power off the card outside of a transaction */
bzero(&uci, sizeof (uci));
uci.uci_version = UCCID_CURRENT_VERSION;
uci.uci_action = UCCID_ICC_POWER_OFF;
ret = ioctl(fd, UCCID_CMD_ICC_MODIFY, &uci);
- VERIFY3S(ret, ==, -1);
- VERIFY3S(errno, ==, EACCES);
+ VERIFY3S(ret, ==, 0);
+
+ /* make sure the card is inactive now */
+ bzero(&ucs, sizeof (ucs));
+ ucs.ucs_version = UCCID_CURRENT_VERSION;
+ ret = ioctl(fd, UCCID_CMD_STATUS, &ucs);
+ VERIFY3S(ret, ==, 0);
+ VERIFY3U(ucs.ucs_status & UCCID_STATUS_F_CARD_ACTIVE, ==, 0);
+
+ /* power on the card outside of a transaction */
+ bzero(&uci, sizeof (uci));
+ uci.uci_version = UCCID_CURRENT_VERSION;
+ uci.uci_action = UCCID_ICC_POWER_ON;
+ ret = ioctl(fd, UCCID_CMD_ICC_MODIFY, &uci);
+ VERIFY3S(ret, ==, 0);
+
+ /* make sure the card is active again */
+ bzero(&ucs, sizeof (ucs));
+ ucs.ucs_version = UCCID_CURRENT_VERSION;
+ ret = ioctl(fd, UCCID_CMD_STATUS, &ucs);
+ VERIFY3S(ret, ==, 0);
+ VERIFY3U(ucs.ucs_status & UCCID_STATUS_F_CARD_ACTIVE, !=, 0);
+
+ /* enter transaction */
bzero(&begin, sizeof (begin));
begin.uct_version = UCCID_CURRENT_VERSION;
if (ioctl(fd, UCCID_CMD_TXN_BEGIN, &begin) != 0) {
diff --git a/usr/src/test/os-tests/tests/uccid/notxn-poll.c b/usr/src/test/os-tests/tests/uccid/notxn-poll.c
index b45f06b218..3a756b5fbc 100644
--- a/usr/src/test/os-tests/tests/uccid/notxn-poll.c
+++ b/usr/src/test/os-tests/tests/uccid/notxn-poll.c
@@ -14,8 +14,8 @@
*/
/*
- * Verify that trying to poll without a transaction / excl access works but
- * returns no events.
+ * Verify that trying to poll without a transaction / excl access fails
+ * with EACCES.
*/
#include <err.h>
@@ -50,8 +50,8 @@ main(int argc, char *argv[])
pfds[0].revents = 0;
ret = poll(pfds, 1, 0);
- VERIFY3S(ret, ==, 0);
- VERIFY3S(pfds[0].revents, ==, 0);
+ VERIFY3S(ret, ==, -1);
+ VERIFY3S(errno, ==, EACCES);
return (0);
}
diff --git a/usr/src/test/os-tests/tests/uccid/yk-readonly.c b/usr/src/test/os-tests/tests/uccid/yk-readonly.c
index dfe7390ea1..1f5d503891 100644
--- a/usr/src/test/os-tests/tests/uccid/yk-readonly.c
+++ b/usr/src/test/os-tests/tests/uccid/yk-readonly.c
@@ -54,31 +54,47 @@ main(int argc, char *argv[])
bzero(&begin, sizeof (begin));
begin.uct_version = UCCID_CURRENT_VERSION;
if (ioctl(fd, UCCID_CMD_TXN_BEGIN, &begin) == 0) {
- err(EXIT_FAILURE, "didn't fail to issue begin ioctl");
+ errx(EXIT_FAILURE, "didn't fail to issue begin ioctl");
}
if ((ret = write(fd, yk_req, sizeof (yk_req))) != -1) {
- err(EXIT_FAILURE, "didn't fail to write data");
+ errx(EXIT_FAILURE, "didn't fail to write data");
+ }
+
+ if (errno != EBADF) {
+ err(EXIT_FAILURE, "wrong errno for failed write, "
+ "expected EBADF");
}
if ((ret = read(fd, buf, sizeof (buf))) != -1) {
- err(EXIT_FAILURE, "didn't fail to read data");
+ errx(EXIT_FAILURE, "didn't fail to read data");
+ }
+
+ if (errno != EACCES) {
+ err(EXIT_FAILURE, "wrong errno for failed read, "
+ "expected EACCES");
}
+ /* get card status */
bzero(&ucs, sizeof (ucs));
ucs.ucs_version = UCCID_CURRENT_VERSION;
if ((ret = ioctl(fd, UCCID_CMD_STATUS, &ucs)) != 0) {
err(EXIT_FAILURE, "failed to get status");
}
- /* try power off the card outside of a transaction */
+
+ /* try to power off the card while opened read-only */
bzero(&uci, sizeof (uci));
uci.uci_version = UCCID_CURRENT_VERSION;
uci.uci_action = UCCID_ICC_POWER_OFF;
if ((ret = ioctl(fd, UCCID_CMD_ICC_MODIFY, &uci)) == 0) {
- err(EXIT_FAILURE, "didn't fail to power off ICC");
+ errx(EXIT_FAILURE, "didn't fail to power off ICC");
}
+ if (errno != EBADF) {
+ err(EXIT_FAILURE, "wrong errno for failed write, "
+ "expected EBADF");
+ }
return (0);
}
diff --git a/usr/src/uts/common/io/audio/drv/audioemu10k/audioemu10k.c b/usr/src/uts/common/io/audio/drv/audioemu10k/audioemu10k.c
index caf47337ae..c114dcea61 100644
--- a/usr/src/uts/common/io/audio/drv/audioemu10k/audioemu10k.c
+++ b/usr/src/uts/common/io/audio/drv/audioemu10k/audioemu10k.c
@@ -827,6 +827,11 @@ emu10k_reset_rec(emu10k_portc_t *portc)
case 65536:
sz = 31;
break;
+ default:
+ /*
+ * Can't really reach here, but this keeps the compiler quiet.
+ */
+ return;
}
emu10k_write_reg(devc, ADCBA, 0, portc->buf_paddr);
emu10k_write_reg(devc, ADCBS, 0, sz);
diff --git a/usr/src/uts/common/io/usb/clients/ccid/ccid.c b/usr/src/uts/common/io/usb/clients/ccid/ccid.c
index 22578d4a1c..61003875d4 100644
--- a/usr/src/uts/common/io/usb/clients/ccid/ccid.c
+++ b/usr/src/uts/common/io/usb/clients/ccid/ccid.c
@@ -138,7 +138,10 @@
* Readers provide four different modes for us to be able to transmit data to
* and from the card. These are:
*
- * 1. Character Mode 2. TPDU Mode 3. Short APDU Mode 4. Extended APDU Mode
+ * 1. Character Mode
+ * 2. TPDU Mode
+ * 3. Short APDU Mode
+ * 4. Extended APDU Mode
*
* Readers either support mode 1, mode 2, mode 3, or mode 3 and 4. All readers
* that support extended APDUs support short APDUs. At this time, we do not
@@ -916,8 +919,8 @@ ccid_slot_excl_req(ccid_slot_t *slot, ccid_minor_t *cmp, boolean_t nosleep)
list_insert_tail(&slot->cs_excl_waiters, cmp);
while (slot->cs_excl_minor != NULL ||
(slot->cs_flags & CCID_SLOT_F_NOEXCL_MASK) != 0) {
- if (cv_wait_sig(&cmp->cm_excl_cv, &slot->cs_ccid->ccid_mutex)
- == 0) {
+ if (cv_wait_sig(&cmp->cm_excl_cv, &slot->cs_ccid->ccid_mutex) ==
+ 0) {
/*
* Remove ourselves from the list and try to signal the
* next thread.
@@ -1043,13 +1046,14 @@ static uint8_t
ccid_command_resp_param2(ccid_command_t *cc)
{
const ccid_header_t *cch;
+ uint8_t val;
VERIFY3P(cc, !=, NULL);
VERIFY3P(cc->cc_response, !=, NULL);
cch = (ccid_header_t *)cc->cc_response->b_rptr;
-
- return (cch->ch_param2);
+ bcopy(&cch->ch_param2, &val, sizeof (val));
+ return (val);
}
/*
@@ -1073,7 +1077,7 @@ ccid_command_complete(ccid_command_t *cc)
ccid_slot_t *slot;
slot = &ccid->ccid_slots[cc->cc_slot];
- ASSERT(slot->cs_icc.icc_complete != NULL);
+ ASSERT3P(slot->cs_icc.icc_complete, !=, NULL);
slot->cs_icc.icc_complete(ccid, slot, cc);
} else {
list_insert_tail(&ccid->ccid_complete_queue, cc);
@@ -1169,8 +1173,6 @@ ccid_reply_bulk_cb(usb_pipe_handle_t ph, usb_bulk_req_t *ubrp)
return;
}
- slot = &ccid->ccid_slots[cc->cc_slot];
-
if (mlen >= sizeof (ccid_header_t)) {
bcopy(ubrp->bulk_data->b_rptr, &cch, sizeof (cch));
header_valid = B_TRUE;
@@ -1209,6 +1211,8 @@ ccid_reply_bulk_cb(usb_pipe_handle_t ph, usb_bulk_req_t *ubrp)
return;
}
+ slot = &ccid->ccid_slots[cc->cc_slot];
+
/*
* If the sequence or slot number don't match the head of the list or
* the response type is unexpected for this command then we should be
@@ -1949,14 +1953,18 @@ ccid_hw_error(ccid_t *ccid, ccid_intr_hwerr_t *hwerr)
ccid_slot_t *slot;
/* Make sure the slot number is within range. */
- if (hwerr->cih_slot >= ccid->ccid_nslots)
+ if (hwerr->cih_slot >= ccid->ccid_nslots) {
+ ccid->ccid_stats.cst_intr_inval++;
return;
+ }
slot = &ccid->ccid_slots[hwerr->cih_slot];
/* The only error condition defined by the spec is overcurrent. */
- if (hwerr->cih_code != CCID_INTR_HWERR_OVERCURRENT)
+ if (hwerr->cih_code != CCID_INTR_HWERR_OVERCURRENT) {
+ ccid->ccid_stats.cst_intr_inval++;
return;
+ }
/*
* The worker thread will take care of this situation.
@@ -2263,10 +2271,7 @@ ccid_slot_power_on(ccid_t *ccid, ccid_slot_t *slot, ccid_class_voltage_t volts,
VERIFY(MUTEX_HELD(&ccid->ccid_mutex));
mutex_exit(&ccid->ccid_mutex);
- if ((ret = ccid_command_power_on(ccid, slot, volts, atr))
- != 0) {
- freemsg(*atr);
-
+ if ((ret = ccid_command_power_on(ccid, slot, volts, atr)) != 0) {
/*
* If we got ENXIO, then we know that there is no ICC
* present. This could happen for a number of reasons.
@@ -2370,8 +2375,8 @@ ccid_slot_inserted(ccid_t *ccid, ccid_slot_t *slot)
* the moment we do.
*/
if ((ccid->ccid_class.ccd_dwFeatures &
- (CCID_CLASS_F_AUTO_ICC_ACTIVATE | CCID_CLASS_F_AUTO_ICC_VOLTAGE))
- == 0) {
+ (CCID_CLASS_F_AUTO_ICC_ACTIVATE | CCID_CLASS_F_AUTO_ICC_VOLTAGE)) ==
+ 0) {
/* Skip auto-voltage */
cvolt++;
}
@@ -2380,13 +2385,15 @@ ccid_slot_inserted(ccid_t *ccid, ccid_slot_t *slot)
int ret;
if (volts[cvolt] != CCID_CLASS_VOLT_AUTO &&
- (ccid->ccid_class.ccd_bVoltageSupport & volts[cvolt])
- == 0) {
+ (ccid->ccid_class.ccd_bVoltageSupport & volts[cvolt]) ==
+ 0) {
continue;
}
- if ((ret = ccid_slot_power_on(ccid, slot, volts[cvolt], &atr))
- != 0) {
+ ret = ccid_slot_power_on(ccid, slot, volts[cvolt], &atr);
+ if (ret != 0) {
+ freemsg(atr);
+ atr = NULL;
continue;
}
@@ -2531,8 +2538,8 @@ ccid_worker(void *arg)
ccid_slot_removed(ccid, slot, B_TRUE);
} else {
(void) ccid_slot_inserted(ccid, slot);
- if ((slot->cs_flags & CCID_SLOT_F_ACTIVE)
- != 0) {
+ if ((slot->cs_flags & CCID_SLOT_F_ACTIVE) !=
+ 0) {
ccid_slot_excl_maybe_signal(slot);
}
}
@@ -3718,8 +3725,8 @@ ccid_read(dev_t dev, struct uio *uiop, cred_t *credp)
* a lot of the surrounding logic and fits with the current consumer
* model.
*/
- if ((slot->cs_io.ci_flags & (CCID_IO_F_IN_PROGRESS | CCID_IO_F_DONE))
- == 0) {
+ if ((slot->cs_io.ci_flags & (CCID_IO_F_IN_PROGRESS | CCID_IO_F_DONE)) ==
+ 0) {
mutex_exit(&ccid->ccid_mutex);
return (ENODATA);
}
@@ -3791,8 +3798,8 @@ ccid_read(dev_t dev, struct uio *uiop, cred_t *credp)
if (mlen > uiop->uio_resid) {
ret = EOVERFLOW;
} else {
- if ((ret = ccid_read_copyout(uiop, slot->cs_io.ci_data))
- == 0) {
+ ret = ccid_read_copyout(uiop, slot->cs_io.ci_data);
+ if (ret == 0) {
done = B_TRUE;
}
}
@@ -3935,7 +3942,7 @@ ccid_ioctl_status(ccid_slot_t *slot, intptr_t arg, int mode)
if (ddi_copyin((void *)arg, &ucs, sizeof (ucs), mode & FKIOCTL) != 0)
return (EFAULT);
- if (ucs.ucs_version != UCCID_CURRENT_VERSION)
+ if (ucs.ucs_version != UCCID_VERSION_ONE)
return (EINVAL);
ucs.ucs_status = 0;
@@ -3943,6 +3950,11 @@ ccid_ioctl_status(ccid_slot_t *slot, intptr_t arg, int mode)
ucs.ucs_slot = slot->cs_slotno;
mutex_enter(&slot->cs_ccid->ccid_mutex);
+ if ((slot->cs_ccid->ccid_flags & CCID_F_DISCONNECTED) != 0) {
+ mutex_exit(&slot->cs_ccid->ccid_mutex);
+ return (ENODEV);
+ }
+
if ((slot->cs_flags & CCID_SLOT_F_PRESENT) != 0)
ucs.ucs_status |= UCCID_STATUS_F_CARD_PRESENT;
if ((slot->cs_flags & CCID_SLOT_F_ACTIVE) != 0)
@@ -3998,7 +4010,7 @@ ccid_ioctl_txn_begin(ccid_slot_t *slot, ccid_minor_t *cmp, intptr_t arg,
if (ddi_copyin((void *)arg, &uct, sizeof (uct), mode & FKIOCTL) != 0)
return (EFAULT);
- if (uct.uct_version != UCCID_CURRENT_VERSION)
+ if (uct.uct_version != UCCID_VERSION_ONE)
return (EINVAL);
if ((uct.uct_flags & ~UCCID_TXN_DONT_BLOCK) != 0)
@@ -4006,9 +4018,14 @@ ccid_ioctl_txn_begin(ccid_slot_t *slot, ccid_minor_t *cmp, intptr_t arg,
nowait = (uct.uct_flags & UCCID_TXN_DONT_BLOCK) != 0;
mutex_enter(&slot->cs_ccid->ccid_mutex);
+ if ((slot->cs_ccid->ccid_flags & CCID_F_DISCONNECTED) != 0) {
+ mutex_exit(&slot->cs_ccid->ccid_mutex);
+ return (ENODEV);
+ }
+
if ((cmp->cm_flags & CCID_MINOR_F_WRITABLE) == 0) {
mutex_exit(&slot->cs_ccid->ccid_mutex);
- return (EACCES);
+ return (EBADF);
}
ret = ccid_slot_excl_req(slot, cmp, nowait);
@@ -4026,11 +4043,16 @@ ccid_ioctl_txn_end(ccid_slot_t *slot, ccid_minor_t *cmp, intptr_t arg, int mode)
return (EFAULT);
}
- if (uct.uct_version != UCCID_CURRENT_VERSION) {
+ if (uct.uct_version != UCCID_VERSION_ONE) {
return (EINVAL);
}
mutex_enter(&slot->cs_ccid->ccid_mutex);
+ if ((slot->cs_ccid->ccid_flags & CCID_F_DISCONNECTED) != 0) {
+ mutex_exit(&slot->cs_ccid->ccid_mutex);
+ return (ENODEV);
+ }
+
if (slot->cs_excl_minor != cmp) {
mutex_exit(&slot->cs_ccid->ccid_mutex);
return (EINVAL);
@@ -4065,12 +4087,21 @@ ccid_ioctl_fionread(ccid_slot_t *slot, ccid_minor_t *cmp, intptr_t arg,
int data;
mutex_enter(&slot->cs_ccid->ccid_mutex);
- if ((cmp->cm_flags & (CCID_MINOR_F_WRITABLE | CCID_MINOR_F_HAS_EXCL)) ==
- (CCID_MINOR_F_WRITABLE | CCID_MINOR_F_HAS_EXCL)) {
+ if ((slot->cs_ccid->ccid_flags & CCID_F_DISCONNECTED) != 0) {
+ mutex_exit(&slot->cs_ccid->ccid_mutex);
+ return (ENODEV);
+ }
+
+ if ((cmp->cm_flags & CCID_MINOR_F_HAS_EXCL) == 0) {
mutex_exit(&slot->cs_ccid->ccid_mutex);
return (EACCES);
}
+ if ((cmp->cm_flags & CCID_MINOR_F_WRITABLE) == 0) {
+ mutex_exit(&slot->cs_ccid->ccid_mutex);
+ return (EBADF);
+ }
+
if ((slot->cs_io.ci_flags & CCID_IO_F_DONE) != 0) {
mutex_exit(&slot->cs_ccid->ccid_mutex);
return (ENODATA);
@@ -4090,8 +4121,8 @@ ccid_ioctl_fionread(ccid_slot_t *slot, ccid_minor_t *cmp, intptr_t arg,
data = MIN(s, INT_MAX);
}
- if (ddi_copyout(&data, (void *)arg, sizeof (data), mode & FKIOCTL)
- != 0) {
+ if (ddi_copyout(&data, (void *)arg, sizeof (data), mode & FKIOCTL) !=
+ 0) {
mutex_exit(&slot->cs_ccid->ccid_mutex);
return (EFAULT);
}
@@ -4112,7 +4143,7 @@ ccid_ioctl_icc_modify(ccid_slot_t *slot, ccid_minor_t *cmp, intptr_t arg,
return (EFAULT);
}
- if (uci.uci_version != UCCID_CURRENT_VERSION) {
+ if (uci.uci_version != UCCID_VERSION_ONE) {
return (EINVAL);
}
@@ -4127,10 +4158,14 @@ ccid_ioctl_icc_modify(ccid_slot_t *slot, ccid_minor_t *cmp, intptr_t arg,
ccid = slot->cs_ccid;
mutex_enter(&ccid->ccid_mutex);
- if ((cmp->cm_flags & (CCID_MINOR_F_WRITABLE | CCID_MINOR_F_HAS_EXCL)) !=
- (CCID_MINOR_F_WRITABLE | CCID_MINOR_F_HAS_EXCL)) {
- mutex_exit(&ccid->ccid_mutex);
- return (EACCES);
+ if ((slot->cs_ccid->ccid_flags & CCID_F_DISCONNECTED) != 0) {
+ mutex_exit(&slot->cs_ccid->ccid_mutex);
+ return (ENODEV);
+ }
+
+ if ((cmp->cm_flags & CCID_MINOR_F_WRITABLE) == 0) {
+ mutex_exit(&slot->cs_ccid->ccid_mutex);
+ return (EBADF);
}
switch (uci.uci_action) {
@@ -4168,13 +4203,6 @@ ccid_ioctl(dev_t dev, int cmd, intptr_t arg, int mode, cred_t *credp,
cmp = idx->cmi_data.cmi_user;
slot = cmp->cm_slot;
- mutex_enter(&slot->cs_ccid->ccid_mutex);
- if ((slot->cs_ccid->ccid_flags & CCID_F_DISCONNECTED) != 0) {
- mutex_exit(&slot->cs_ccid->ccid_mutex);
- return (ENODEV);
- }
- mutex_exit(&slot->cs_ccid->ccid_mutex);
-
switch (cmd) {
case UCCID_CMD_TXN_BEGIN:
return (ccid_ioctl_txn_begin(slot, cmp, arg, mode));
@@ -4218,22 +4246,25 @@ ccid_chpoll(dev_t dev, short events, int anyyet, short *reventsp,
return (ENODEV);
}
- if ((cmp->cm_flags & CCID_MINOR_F_HAS_EXCL) != 0) {
- /*
- * If the CCID_IO_F_DONE flag is set, then we're always
- * readable. However, flags are insufficient to be writeable.
- */
- if ((slot->cs_io.ci_flags & CCID_IO_F_DONE) != 0) {
- ready |= POLLIN | POLLRDNORM;
- } else if ((slot->cs_flags & CCID_SLOT_F_ACTIVE) != 0 &&
- (slot->cs_io.ci_flags & CCID_IO_F_POLLOUT_FLAGS) == 0 &&
- slot->cs_icc.icc_tx != NULL) {
- ready |= POLLOUT;
- }
+ if (!(cmp->cm_flags & CCID_MINOR_F_HAS_EXCL) != 0) {
+ mutex_exit(&ccid->ccid_mutex);
+ return (EACCES);
+ }
- if ((slot->cs_flags & CCID_SLOT_F_PRESENT) == 0) {
- ready |= POLLHUP;
- }
+ /*
+ * If the CCID_IO_F_DONE flag is set, then we're always
+ * readable. However, flags are insufficient to be writeable.
+ */
+ if ((slot->cs_io.ci_flags & CCID_IO_F_DONE) != 0) {
+ ready |= POLLIN | POLLRDNORM;
+ } else if ((slot->cs_flags & CCID_SLOT_F_ACTIVE) != 0 &&
+ (slot->cs_io.ci_flags & CCID_IO_F_POLLOUT_FLAGS) == 0 &&
+ slot->cs_icc.icc_tx != NULL) {
+ ready |= POLLOUT;
+ }
+
+ if ((slot->cs_flags & CCID_SLOT_F_PRESENT) == 0) {
+ ready |= POLLHUP;
}
*reventsp = ready & events;
diff --git a/usr/src/uts/common/sys/usb/clients/ccid/ccid.h b/usr/src/uts/common/sys/usb/clients/ccid/ccid.h
index 0437a957ba..c5ed9ad1f2 100644
--- a/usr/src/uts/common/sys/usb/clients/ccid/ccid.h
+++ b/usr/src/uts/common/sys/usb/clients/ccid/ccid.h
@@ -175,23 +175,23 @@ typedef union ccid_params {
typedef enum ccid_intr_code {
CCID_INTR_CODE_SLOT_CHANGE = 0x50,
CCID_INTR_CODE_HW_ERROR = 0x51
-} __packed ccid_intr_code_t;
+} ccid_intr_code_t;
typedef enum ccid_intr_hwerr_code {
CCID_INTR_HWERR_OVERCURRENT = 0x01
-} __packed ccid_intr_hwerr_code_t;
+} ccid_intr_hwerr_code_t;
typedef struct ccid_intr_slot {
uint8_t cis_type;
uint8_t cis_state[];
-} __packed ccid_intr_slot_t;
+} ccid_intr_slot_t;
typedef struct ccid_intr_hwerr {
uint8_t cih_type;
uint8_t cih_slot;
uint8_t cih_seq;
uint8_t cih_code;
-} __packed ccid_intr_hwerr_t;
+} ccid_intr_hwerr_t;
/*
* Message request codes. These codes are based on CCID r1.1.0 Table 6.1-1
@@ -214,7 +214,7 @@ typedef enum ccid_request_code {
CCID_REQEUST_ABORT = 0x72, /* PC_to_RDR_Abort */
CCID_REQUEST_DATA_CLOCK = 0x73 /* PC_to_RDR_SetDataRateAnd */
/* ClockFrequency */
-} __packed ccid_request_code_t;
+} ccid_request_code_t;
/*
* Message request codes. These codes are based on CCID r1.1.0 Table 6.2-1
@@ -228,7 +228,7 @@ typedef enum ccid_response_code {
CCID_RESPONSE_ESCAPE = 0x83, /* RDR_to_PC_Escape */
CCID_RESPONSE_DATA_CLOCK = 0x84 /* RDR_to_PC_DataRateAnd */
/* ClockFrequency */
-} __packed ccid_response_code_t;
+} ccid_response_code_t;
/*
* This represents the CCID command header that is used for every request and
@@ -265,13 +265,13 @@ typedef enum {
CCID_REPLY_ICC_ACTIVE = 0,
CCID_REPLY_ICC_INACTIVE,
CCID_REPLY_ICC_MISSING
-} __packed ccid_reply_icc_status_t;
+} ccid_reply_icc_status_t;
typedef enum {
CCID_REPLY_STATUS_COMPLETE = 0,
CCID_REPLY_STATUS_FAILED,
CCID_REPLY_STATUS_MORE_TIME
-} __packed ccid_reply_command_status_t;
+} ccid_reply_command_status_t;
/*
* Errors that are defined based when commands fail. These are based on CCID
@@ -294,7 +294,7 @@ typedef enum ccid_command_err {
CCID_ERR_PIN_CANCELLED = 0xef,
CCID_ERR_CMD_SLOT_BUSY = 0xe0,
CCID_ERR_CMD_NOT_SUPPORTED = 0x00
-} __packed ccid_command_err_t;
+} ccid_command_err_t;
/*
* Maximum size of an APDU (application data unit) payload. There are both short
diff --git a/usr/src/uts/common/sys/usb/clients/ccid/uccid.h b/usr/src/uts/common/sys/usb/clients/ccid/uccid.h
index 9aee0559b6..f016df3879 100644
--- a/usr/src/uts/common/sys/usb/clients/ccid/uccid.h
+++ b/usr/src/uts/common/sys/usb/clients/ccid/uccid.h
@@ -56,7 +56,7 @@ extern "C" {
typedef struct uccid_cmd_txn_begin {
uint32_t uct_version;
uint32_t uct_flags;
-} __packed uccid_cmd_txn_begin_t;
+} uccid_cmd_txn_begin_t;
/*
* Relinquish exclusive access. Takes a uccid_cmd_txn_end_t. The callers should
@@ -72,7 +72,7 @@ typedef struct uccid_cmd_txn_begin {
typedef struct uccid_cmd_txn_end {
uint32_t uct_version;
uint32_t uct_flags;
-} __packed uccid_cmd_txn_end_t;
+} uccid_cmd_txn_end_t;
/*
* Obtain the status of the slot. Returns a filled-in uccid_cmd_status_t.
@@ -109,7 +109,7 @@ typedef struct uccid_cmd_status {
ccid_class_descr_t ucs_class;
uccid_prot_t ucs_prot;
ccid_params_t ucs_params;
-} __packed uccid_cmd_status_t;
+} uccid_cmd_status_t;
/*
* Modify the state of the ICC, if present.
@@ -123,7 +123,7 @@ typedef struct uccid_cmd_status {
typedef struct uccid_cmd_icc_modify {
uint32_t uci_version;
uint32_t uci_action;
-} __packed uccid_cmd_icc_modify_t;
+} uccid_cmd_icc_modify_t;
#ifdef __cplusplus
}