xref: /illumos-gate/usr/src/cmd/devprop/devprop.c (revision b13c8383)
1843e1988Sjohnlev /*
2843e1988Sjohnlev  * CDDL HEADER START
3843e1988Sjohnlev  *
4843e1988Sjohnlev  * The contents of this file are subject to the terms of the
5843e1988Sjohnlev  * Common Development and Distribution License (the "License").
6843e1988Sjohnlev  * You may not use this file except in compliance with the License.
7843e1988Sjohnlev  *
8843e1988Sjohnlev  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9843e1988Sjohnlev  * or http://www.opensolaris.org/os/licensing.
10843e1988Sjohnlev  * See the License for the specific language governing permissions
11843e1988Sjohnlev  * and limitations under the License.
12843e1988Sjohnlev  *
13843e1988Sjohnlev  * When distributing Covered Code, include this CDDL HEADER in each
14843e1988Sjohnlev  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15843e1988Sjohnlev  * If applicable, add the following below this CDDL HEADER, with the
16843e1988Sjohnlev  * fields enclosed by brackets "[]" replaced with your own identifying
17843e1988Sjohnlev  * information: Portions Copyright [yyyy] [name of copyright owner]
18843e1988Sjohnlev  *
19843e1988Sjohnlev  * CDDL HEADER END
20843e1988Sjohnlev  */
21843e1988Sjohnlev /*
22843e1988Sjohnlev  * Copyright 2007 Sun Microsystems, Inc.  All rights reserved.
23843e1988Sjohnlev  * Use is subject to license terms.
24*b13c8383SAlexander Eremin  * Copyright 2016 Nexenta Systems, Inc. All rights reserved.
25843e1988Sjohnlev  */
26843e1988Sjohnlev 
27843e1988Sjohnlev 
28843e1988Sjohnlev #include <stdio.h>
29843e1988Sjohnlev #include <unistd.h>
30843e1988Sjohnlev #include <strings.h>
31843e1988Sjohnlev #include <libdevinfo.h>
32843e1988Sjohnlev 
33843e1988Sjohnlev static void
usage(void)34843e1988Sjohnlev usage(void)
35843e1988Sjohnlev {
36843e1988Sjohnlev 	(void) fprintf(stderr,
37843e1988Sjohnlev 	    "Usage: devprop [-n device-path] "
38843e1988Sjohnlev 	    "[-vq] [-{b|i|l|s}] [property [...]]\n");
39843e1988Sjohnlev }
40843e1988Sjohnlev 
41843e1988Sjohnlev int
main(int argc,char * argv[])42843e1988Sjohnlev main(int argc, char *argv[])
43843e1988Sjohnlev {
44843e1988Sjohnlev 	int c;
45843e1988Sjohnlev 	boolean_t verbose = B_FALSE, quote = B_FALSE,
46843e1988Sjohnlev 	    error = B_FALSE;
47843e1988Sjohnlev 	int type = DI_PROP_TYPE_UNKNOWN;
48843e1988Sjohnlev 	char *path = "/";
49843e1988Sjohnlev 	di_node_t dn;
50843e1988Sjohnlev 	uchar_t *val_b;
51843e1988Sjohnlev 	int *val_i;
52843e1988Sjohnlev 	int64_t *val_l;
53*b13c8383SAlexander Eremin 	char *val_s, *ptr;
54843e1988Sjohnlev 	int n;
55843e1988Sjohnlev 
56843e1988Sjohnlev 	extern char *optarg;
57843e1988Sjohnlev 	extern int optind;
58843e1988Sjohnlev 
59843e1988Sjohnlev #define	BOOL(ch, var)				\
60843e1988Sjohnlev case ch:					\
61843e1988Sjohnlev 	var = B_TRUE;				\
62843e1988Sjohnlev 	break
63843e1988Sjohnlev 
64843e1988Sjohnlev #define	PER_OPT(ch, typ)			\
65843e1988Sjohnlev case ch:					\
66843e1988Sjohnlev 	if (type != DI_PROP_TYPE_UNKNOWN) {	\
67843e1988Sjohnlev 		usage();			\
68843e1988Sjohnlev 		return (1);			\
69843e1988Sjohnlev 	}					\
70843e1988Sjohnlev 	type = (typ);				\
71843e1988Sjohnlev 	break
72843e1988Sjohnlev 
73843e1988Sjohnlev 	while ((c = getopt(argc, argv, ":n:vqbils")) != -1) {
74843e1988Sjohnlev 		switch (c) {
75843e1988Sjohnlev 		case 'n':
76*b13c8383SAlexander Eremin 			if ((path = realpath(optarg, NULL)) == NULL)
77*b13c8383SAlexander Eremin 				path = optarg;
78843e1988Sjohnlev 			break;
79843e1988Sjohnlev 		case ':':
80843e1988Sjohnlev 			usage();
81843e1988Sjohnlev 			return (1);
82843e1988Sjohnlev 
83843e1988Sjohnlev 		BOOL('v', verbose);
84843e1988Sjohnlev 		BOOL('q', quote);
85843e1988Sjohnlev 		BOOL('?', error);
86843e1988Sjohnlev 
87843e1988Sjohnlev 		PER_OPT('b', DI_PROP_TYPE_BYTE);
88843e1988Sjohnlev 		PER_OPT('i', DI_PROP_TYPE_INT);
89843e1988Sjohnlev 		PER_OPT('l', DI_PROP_TYPE_INT64);
90843e1988Sjohnlev 		PER_OPT('s', DI_PROP_TYPE_STRING);
91843e1988Sjohnlev 		}
92843e1988Sjohnlev 	}
93843e1988Sjohnlev 
94843e1988Sjohnlev #undef	BOOL
95843e1988Sjohnlev #undef	PER_OPT
96843e1988Sjohnlev 
97843e1988Sjohnlev 	if (error) {
98843e1988Sjohnlev 		usage();
99843e1988Sjohnlev 		return (1);
100843e1988Sjohnlev 	}
101843e1988Sjohnlev 
102843e1988Sjohnlev 	/* default to strings */
103843e1988Sjohnlev 	if (type == DI_PROP_TYPE_UNKNOWN)
104843e1988Sjohnlev 		type = DI_PROP_TYPE_STRING;
105843e1988Sjohnlev 
106843e1988Sjohnlev 	/*
107843e1988Sjohnlev 	 * It's convenient to use the filesystem as a source of device
108843e1988Sjohnlev 	 * node paths.  In that case, the path will be prefixed with
109843e1988Sjohnlev 	 * "/devices", which we strip off here as di_init() expects
110843e1988Sjohnlev 	 * just the path to the node.
111843e1988Sjohnlev 	 */
112*b13c8383SAlexander Eremin 	if (strncmp("/devices/", path, strlen("/devices/")) == 0) {
113843e1988Sjohnlev 		path += strlen("/devices");
114843e1988Sjohnlev 
115*b13c8383SAlexander Eremin 		/* cut off minor name */
116*b13c8383SAlexander Eremin 		if ((ptr = strrchr(path, ':')) != NULL)
117*b13c8383SAlexander Eremin 			*ptr = '\0';
118*b13c8383SAlexander Eremin 	}
119*b13c8383SAlexander Eremin 
120843e1988Sjohnlev 	if ((dn = di_init(path, DINFOPROP)) == DI_NODE_NIL) {
121843e1988Sjohnlev 		perror("di_init");
122843e1988Sjohnlev 		return (1);
123843e1988Sjohnlev 	}
124843e1988Sjohnlev 
125843e1988Sjohnlev 	/* Careful with that axe, Eugene... */
126843e1988Sjohnlev #define	PER_TYPE(typ, func, val, incr, form, pv, sep)	\
127843e1988Sjohnlev case (typ):						\
128843e1988Sjohnlev 	n = func(DDI_DEV_T_ANY,				\
129843e1988Sjohnlev 	    dn, argv[optind], &(val));			\
130843e1988Sjohnlev 	while (n > 0) {					\
131843e1988Sjohnlev 		(void) printf((form), pv);		\
132843e1988Sjohnlev 		incr;					\
133843e1988Sjohnlev 		n--;					\
134843e1988Sjohnlev 		if (n > 0)				\
135843e1988Sjohnlev 			(void) printf(sep);		\
136843e1988Sjohnlev 	}						\
137843e1988Sjohnlev 	(void) printf("\n");				\
138843e1988Sjohnlev 	break
139843e1988Sjohnlev 
140843e1988Sjohnlev 	while (optind < argc) {
141843e1988Sjohnlev 		if (verbose)
142843e1988Sjohnlev 			(void) printf("%s=", argv[optind]);
143843e1988Sjohnlev 
144843e1988Sjohnlev 		switch (type) {
145843e1988Sjohnlev 		PER_TYPE(DI_PROP_TYPE_BYTE, di_prop_lookup_bytes,
146843e1988Sjohnlev 		    val_b, val_b++, "%2.2x", *val_b, ".");
147843e1988Sjohnlev 		PER_TYPE(DI_PROP_TYPE_INT, di_prop_lookup_ints,
148843e1988Sjohnlev 		    val_i, val_i++, "%8.8x", *val_i, ".");
149843e1988Sjohnlev 		PER_TYPE(DI_PROP_TYPE_INT64, di_prop_lookup_int64,
150843e1988Sjohnlev 		    val_l, val_l++, "%16.16llx", *val_l, ".");
151843e1988Sjohnlev 		PER_TYPE(DI_PROP_TYPE_STRING, di_prop_lookup_strings,
152843e1988Sjohnlev 		    val_s, val_s += strlen(val_s) + 1,
153843e1988Sjohnlev 		    (quote ? "\"%s\"" : "%s"), val_s, " + ");
154843e1988Sjohnlev 		}
155843e1988Sjohnlev 
156843e1988Sjohnlev 		optind++;
157843e1988Sjohnlev 	}
158843e1988Sjohnlev 
159843e1988Sjohnlev #undef	PER_TYPE
160843e1988Sjohnlev 
161843e1988Sjohnlev 	di_fini(dn);
162843e1988Sjohnlev 
163843e1988Sjohnlev 	return (0);
164843e1988Sjohnlev }
165