xref: /onnv-gate/usr/src/cmd/mdb/common/modules/md/dumpnamespace.c (revision 0:68f95e015346)
1*0Sstevel@tonic-gate /*
2*0Sstevel@tonic-gate  * CDDL HEADER START
3*0Sstevel@tonic-gate  *
4*0Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
5*0Sstevel@tonic-gate  * Common Development and Distribution License, Version 1.0 only
6*0Sstevel@tonic-gate  * (the "License").  You may not use this file except in compliance
7*0Sstevel@tonic-gate  * with the License.
8*0Sstevel@tonic-gate  *
9*0Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10*0Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
11*0Sstevel@tonic-gate  * See the License for the specific language governing permissions
12*0Sstevel@tonic-gate  * and limitations under the License.
13*0Sstevel@tonic-gate  *
14*0Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
15*0Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16*0Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
17*0Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
18*0Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
19*0Sstevel@tonic-gate  *
20*0Sstevel@tonic-gate  * CDDL HEADER END
21*0Sstevel@tonic-gate  */
22*0Sstevel@tonic-gate /*
23*0Sstevel@tonic-gate  * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
24*0Sstevel@tonic-gate  * Use is subject to license terms.
25*0Sstevel@tonic-gate  */
26*0Sstevel@tonic-gate 
27*0Sstevel@tonic-gate #pragma ident	"%Z%%M%	%I%	%E% SMI"
28*0Sstevel@tonic-gate 
29*0Sstevel@tonic-gate #include "mdinclude.h"
30*0Sstevel@tonic-gate #include <sys/lvm/md_names.h>
31*0Sstevel@tonic-gate 
32*0Sstevel@tonic-gate /*
33*0Sstevel@tonic-gate  * work out the offset size
34*0Sstevel@tonic-gate  */
35*0Sstevel@tonic-gate #define	MY_DID_SHR_NAMSIZ(n) \
36*0Sstevel@tonic-gate 	(((sizeof (struct did_shr_name) - 1) + \
37*0Sstevel@tonic-gate 	n + (sizeof (uint_t) - 1)) & ~(sizeof (uint_t) - 1))
38*0Sstevel@tonic-gate #define	MY_SHR_NAMSIZ(n) \
39*0Sstevel@tonic-gate 	(((sizeof (struct nm_shared_name) - 1) + \
40*0Sstevel@tonic-gate 	n + (sizeof (uint_t) - 1)) & ~(sizeof (uint_t) - 1))
41*0Sstevel@tonic-gate #define	MY_DID_NAMSIZ(n) \
42*0Sstevel@tonic-gate 	(((sizeof (struct did_min_name) - 1) + \
43*0Sstevel@tonic-gate 	n + (sizeof (uint_t) - 1)) & ~(sizeof (uint_t) - 1))
44*0Sstevel@tonic-gate #define	MY_NAMSIZ(n) \
45*0Sstevel@tonic-gate 	(((sizeof (struct nm_name) - 1) + \
46*0Sstevel@tonic-gate 	n + (sizeof (uint_t) - 1)) & ~(sizeof (uint_t) - 1))
47*0Sstevel@tonic-gate 
48*0Sstevel@tonic-gate static uintptr_t
print_did_shared_name(uintptr_t addr,int i)49*0Sstevel@tonic-gate print_did_shared_name(uintptr_t addr, int i)
50*0Sstevel@tonic-gate {
51*0Sstevel@tonic-gate 	struct did_shr_name	shn;
52*0Sstevel@tonic-gate 	uintptr_t		sn_name_addr;
53*0Sstevel@tonic-gate 	void			*sn_name;
54*0Sstevel@tonic-gate 	uintptr_t		next_addr = addr;
55*0Sstevel@tonic-gate 
56*0Sstevel@tonic-gate 	if (mdb_vread(&shn, sizeof (struct did_shr_name), addr) !=
57*0Sstevel@tonic-gate 	    sizeof (struct did_shr_name)) {
58*0Sstevel@tonic-gate 		mdb_warn("failed to read did_shr_name at %p\n", addr);
59*0Sstevel@tonic-gate 		return (NULL);
60*0Sstevel@tonic-gate 	}
61*0Sstevel@tonic-gate 	if (shn.did_size == 0)
62*0Sstevel@tonic-gate 		return (NULL);
63*0Sstevel@tonic-gate 	mdb_printf("device_id[%d] at %p\n", i, addr);
64*0Sstevel@tonic-gate 	mdb_inc_indent(2);
65*0Sstevel@tonic-gate 	mdb_printf("did_key:    %d\n", shn.did_key);
66*0Sstevel@tonic-gate 	mdb_printf("did_count:  %u\n", shn.did_count);
67*0Sstevel@tonic-gate 	mdb_printf("did_data:   0x%x \n", shn.did_data);
68*0Sstevel@tonic-gate 	mdb_printf("did_size: %u\n", shn.did_size);
69*0Sstevel@tonic-gate 	sn_name_addr = addr + ((uintptr_t)&shn.did_devid - (uintptr_t)&shn);
70*0Sstevel@tonic-gate 	if (shn.did_size > 0) {
71*0Sstevel@tonic-gate 		sn_name = mdb_alloc(shn.did_size + 1, UM_SLEEP | UM_GC);
72*0Sstevel@tonic-gate 		if (mdb_readstr((char *)sn_name, shn.did_size + 1,
73*0Sstevel@tonic-gate 		    sn_name_addr) <= 0) {
74*0Sstevel@tonic-gate 			mdb_warn("failed to read sn_name at %p\n",
75*0Sstevel@tonic-gate 			    sn_name_addr);
76*0Sstevel@tonic-gate 			return (NULL);
77*0Sstevel@tonic-gate 		}
78*0Sstevel@tonic-gate 		mdb_printf("did_devid:   %s at %p\n", (char *)sn_name,
79*0Sstevel@tonic-gate 		    sn_name_addr);
80*0Sstevel@tonic-gate 		next_addr = addr + MY_DID_SHR_NAMSIZ(shn.did_size);
81*0Sstevel@tonic-gate 	}
82*0Sstevel@tonic-gate 	mdb_dec_indent(2);
83*0Sstevel@tonic-gate 	return (next_addr);
84*0Sstevel@tonic-gate }
85*0Sstevel@tonic-gate 
86*0Sstevel@tonic-gate static uintptr_t
print_nm_shared_name(uintptr_t addr,int i)87*0Sstevel@tonic-gate print_nm_shared_name(uintptr_t addr, int i)
88*0Sstevel@tonic-gate {
89*0Sstevel@tonic-gate 	struct nm_shared_name	shn;
90*0Sstevel@tonic-gate 	uintptr_t		sn_name_addr;
91*0Sstevel@tonic-gate 	void			*sn_name;
92*0Sstevel@tonic-gate 	uintptr_t		next_addr = addr;
93*0Sstevel@tonic-gate 
94*0Sstevel@tonic-gate 	if (mdb_vread(&shn, sizeof (struct nm_shared_name), addr) !=
95*0Sstevel@tonic-gate 	    sizeof (struct nm_shared_name)) {
96*0Sstevel@tonic-gate 		mdb_warn("failed to read nm_shared_name at %p\n", addr);
97*0Sstevel@tonic-gate 		return (NULL);
98*0Sstevel@tonic-gate 	}
99*0Sstevel@tonic-gate 	if (shn.sn_namlen == 0)
100*0Sstevel@tonic-gate 		return (NULL);
101*0Sstevel@tonic-gate 	mdb_printf("sr_name[%d] at %p\n", i, addr);
102*0Sstevel@tonic-gate 	mdb_inc_indent(2);
103*0Sstevel@tonic-gate 	mdb_printf("sn_key:    %d \n", shn.sn_key);
104*0Sstevel@tonic-gate 	mdb_printf("sn_count:  %u\n", shn.sn_count);
105*0Sstevel@tonic-gate 	mdb_printf("sn_data:   0x%x \n", shn.sn_data);
106*0Sstevel@tonic-gate 	mdb_printf("sn_namlen: %u\n", shn.sn_namlen);
107*0Sstevel@tonic-gate 	sn_name_addr = addr + ((uintptr_t)&shn.sn_name - (uintptr_t)&shn);
108*0Sstevel@tonic-gate 	if (shn.sn_namlen > 0) {
109*0Sstevel@tonic-gate 		sn_name = mdb_alloc(shn.sn_namlen + 1, UM_SLEEP | UM_GC);
110*0Sstevel@tonic-gate 		if (mdb_readstr((char *)sn_name, shn.sn_namlen + 1,
111*0Sstevel@tonic-gate 		    sn_name_addr) <= 0) {
112*0Sstevel@tonic-gate 			mdb_warn("failed to read sn_name at %p\n",
113*0Sstevel@tonic-gate 			    sn_name_addr);
114*0Sstevel@tonic-gate 		}
115*0Sstevel@tonic-gate 		mdb_printf("sn_name:   %s at %p\n", (char *)sn_name,
116*0Sstevel@tonic-gate 		    sn_name_addr);
117*0Sstevel@tonic-gate 		next_addr = addr + MY_SHR_NAMSIZ(shn.sn_namlen);
118*0Sstevel@tonic-gate 	}
119*0Sstevel@tonic-gate 	mdb_dec_indent(2);
120*0Sstevel@tonic-gate 	return (next_addr);
121*0Sstevel@tonic-gate }
122*0Sstevel@tonic-gate 
123*0Sstevel@tonic-gate static uintptr_t
print_devid_name(uintptr_t addr,int i)124*0Sstevel@tonic-gate print_devid_name(uintptr_t addr, int i)
125*0Sstevel@tonic-gate {
126*0Sstevel@tonic-gate 	struct did_min_name	didmn;
127*0Sstevel@tonic-gate 	uintptr_t		did_name_addr;
128*0Sstevel@tonic-gate 	void			*min_name;
129*0Sstevel@tonic-gate 	uintptr_t		next_addr = addr;
130*0Sstevel@tonic-gate 
131*0Sstevel@tonic-gate 	if (mdb_vread(&didmn, sizeof (struct did_min_name), addr) !=
132*0Sstevel@tonic-gate 	    sizeof (struct did_min_name)) {
133*0Sstevel@tonic-gate 		mdb_warn("failed to read did_min_name at %p\n", addr);
134*0Sstevel@tonic-gate 		return (NULL);
135*0Sstevel@tonic-gate 	}
136*0Sstevel@tonic-gate 	if (didmn.min_namlen == 0)
137*0Sstevel@tonic-gate 		return (NULL);
138*0Sstevel@tonic-gate 	mdb_printf("minor_name[%d] at %p\n", i, addr);
139*0Sstevel@tonic-gate 	mdb_inc_indent(2);
140*0Sstevel@tonic-gate 	mdb_printf("min_key:    %d \n", didmn.min_key);
141*0Sstevel@tonic-gate 	mdb_printf("min_count:  %u\n", didmn.min_count);
142*0Sstevel@tonic-gate 	mdb_printf("min_devid_key:    %d \n", didmn.min_devid_key);
143*0Sstevel@tonic-gate 	mdb_printf("min_namlen: %u\n", didmn.min_namlen);
144*0Sstevel@tonic-gate 	did_name_addr = addr + ((uintptr_t)&didmn.min_name - (uintptr_t)&didmn);
145*0Sstevel@tonic-gate 	if (didmn.min_namlen > 0) {
146*0Sstevel@tonic-gate 		min_name = mdb_alloc(didmn.min_namlen + 1, UM_SLEEP | UM_GC);
147*0Sstevel@tonic-gate 		if (mdb_readstr((char *)min_name, didmn.min_namlen + 1,
148*0Sstevel@tonic-gate 		    did_name_addr) <= 0) {
149*0Sstevel@tonic-gate 			mdb_warn("failed to read min_name at %p\n",
150*0Sstevel@tonic-gate 			    did_name_addr);
151*0Sstevel@tonic-gate 		}
152*0Sstevel@tonic-gate 		mdb_printf("min_name:   %s at %p\n", (char *)min_name,
153*0Sstevel@tonic-gate 		    did_name_addr);
154*0Sstevel@tonic-gate 		next_addr = addr + MY_DID_NAMSIZ(didmn.min_namlen);
155*0Sstevel@tonic-gate 	}
156*0Sstevel@tonic-gate 	mdb_dec_indent(2);
157*0Sstevel@tonic-gate 	return (next_addr);
158*0Sstevel@tonic-gate }
159*0Sstevel@tonic-gate 
160*0Sstevel@tonic-gate static uintptr_t
print_nm_name(uintptr_t addr,int i)161*0Sstevel@tonic-gate print_nm_name(uintptr_t addr, int i)
162*0Sstevel@tonic-gate {
163*0Sstevel@tonic-gate 	struct nm_name	nm;
164*0Sstevel@tonic-gate 	uintptr_t	nm_name_addr;
165*0Sstevel@tonic-gate 	void		*n_name;
166*0Sstevel@tonic-gate 	uintptr_t	next_addr = addr;
167*0Sstevel@tonic-gate 
168*0Sstevel@tonic-gate 	if (mdb_vread(&nm, sizeof (struct nm_name), addr) !=
169*0Sstevel@tonic-gate 	    sizeof (struct nm_name)) {
170*0Sstevel@tonic-gate 		mdb_warn("failed to read nm_name at %p\n", addr);
171*0Sstevel@tonic-gate 		return (NULL);
172*0Sstevel@tonic-gate 	}
173*0Sstevel@tonic-gate 	if (nm.n_namlen == 0)
174*0Sstevel@tonic-gate 		return (NULL);
175*0Sstevel@tonic-gate 	mdb_printf("r_name[%d] at %p\n", i, addr);
176*0Sstevel@tonic-gate 	mdb_inc_indent(2);
177*0Sstevel@tonic-gate 	mdb_printf("n_key:    %d \n", nm.n_key);
178*0Sstevel@tonic-gate 	mdb_printf("n_count:  %u\n", nm.n_count);
179*0Sstevel@tonic-gate 	mdb_printf("n_minor:  %x\n", nm.n_minor);
180*0Sstevel@tonic-gate 	mdb_printf("n_drv_key:    %d \n", nm.n_drv_key);
181*0Sstevel@tonic-gate 	mdb_printf("n_dir_key:    %d \n", nm.n_dir_key);
182*0Sstevel@tonic-gate 	mdb_printf("n_namlen: %u\n", nm.n_namlen);
183*0Sstevel@tonic-gate 	nm_name_addr = addr + ((uintptr_t)&nm.n_name - (uintptr_t)&nm);
184*0Sstevel@tonic-gate 	if (nm.n_namlen > 0) {
185*0Sstevel@tonic-gate 		n_name = mdb_alloc(nm.n_namlen + 1, UM_SLEEP | UM_GC);
186*0Sstevel@tonic-gate 		if (mdb_readstr((char *)n_name, nm.n_namlen + 1,
187*0Sstevel@tonic-gate 		    nm_name_addr) <= 0) {
188*0Sstevel@tonic-gate 			mdb_warn("failed to read n_name at %p\n", nm_name_addr);
189*0Sstevel@tonic-gate 		}
190*0Sstevel@tonic-gate 		mdb_printf("n_name:   %s at %p\n", (char *)n_name,
191*0Sstevel@tonic-gate 		    nm_name_addr);
192*0Sstevel@tonic-gate 		next_addr = addr + MY_NAMSIZ(nm.n_namlen);
193*0Sstevel@tonic-gate 	}
194*0Sstevel@tonic-gate 
195*0Sstevel@tonic-gate 	mdb_dec_indent(2);
196*0Sstevel@tonic-gate 	return (next_addr);
197*0Sstevel@tonic-gate }
198*0Sstevel@tonic-gate 
199*0Sstevel@tonic-gate static uint_t
process_nmn_record_hdr(uintptr_t addr)200*0Sstevel@tonic-gate process_nmn_record_hdr(uintptr_t addr)
201*0Sstevel@tonic-gate {
202*0Sstevel@tonic-gate 	struct nm_rec_hdr	rhdr;
203*0Sstevel@tonic-gate 
204*0Sstevel@tonic-gate 	/*
205*0Sstevel@tonic-gate 	 * we read this anyway as the first part of nm_rec, devid_min_rec,
206*0Sstevel@tonic-gate 	 * nm_shr_rec, and devid_shr_rec record is a nm_rec_hdr
207*0Sstevel@tonic-gate 	 */
208*0Sstevel@tonic-gate 	if (mdb_vread(&rhdr, sizeof (struct nm_rec_hdr), addr) !=
209*0Sstevel@tonic-gate 	    sizeof (struct nm_rec_hdr)) {
210*0Sstevel@tonic-gate 		mdb_warn("failed to read nm_rec_hdr at %p\n", addr);
211*0Sstevel@tonic-gate 		return (0);
212*0Sstevel@tonic-gate 	}
213*0Sstevel@tonic-gate 
214*0Sstevel@tonic-gate 	mdb_printf("nmn_record: %p\n", addr);
215*0Sstevel@tonic-gate 	mdb_inc_indent(2);
216*0Sstevel@tonic-gate 	mdb_printf("r_revision:     %4u\n", rhdr.r_revision);
217*0Sstevel@tonic-gate 	mdb_printf("r_alloc_size:   %4u\n", rhdr.r_alloc_size);
218*0Sstevel@tonic-gate 	mdb_printf("r_used_size:    %4u\n", rhdr.r_used_size);
219*0Sstevel@tonic-gate 	mdb_printf("r_next_recid:   %4x\n", rhdr.r_next_recid);
220*0Sstevel@tonic-gate 	mdb_printf("xr_next_rec:    %4u\n", rhdr.xr_next_rec);
221*0Sstevel@tonic-gate 	mdb_printf("r_next_key:     %4d\n", rhdr.r_next_key);
222*0Sstevel@tonic-gate 	mdb_dec_indent(2);
223*0Sstevel@tonic-gate 	return (rhdr.r_used_size);
224*0Sstevel@tonic-gate }
225*0Sstevel@tonic-gate 
226*0Sstevel@tonic-gate static void
process_nmn_record(uintptr_t addr,int shared,int devid)227*0Sstevel@tonic-gate process_nmn_record(uintptr_t addr, int shared, int devid)
228*0Sstevel@tonic-gate {
229*0Sstevel@tonic-gate 	struct nm_shr_rec	srhdr;
230*0Sstevel@tonic-gate 	struct devid_shr_rec	didsrhdr;
231*0Sstevel@tonic-gate 	struct nm_rec		nm_record;
232*0Sstevel@tonic-gate 	struct devid_min_rec	devid_record;
233*0Sstevel@tonic-gate 	uintptr_t		shn_addr;
234*0Sstevel@tonic-gate 	int			i;
235*0Sstevel@tonic-gate 	uintptr_t		next_addr, start_addr;
236*0Sstevel@tonic-gate 	uint_t			used_size;
237*0Sstevel@tonic-gate 
238*0Sstevel@tonic-gate 	used_size = process_nmn_record_hdr(addr);
239*0Sstevel@tonic-gate 
240*0Sstevel@tonic-gate 	if (devid) {
241*0Sstevel@tonic-gate 		if (shared) {
242*0Sstevel@tonic-gate 			if (mdb_vread(&didsrhdr, sizeof (struct devid_shr_rec),
243*0Sstevel@tonic-gate 			    addr) != sizeof (struct devid_shr_rec)) {
244*0Sstevel@tonic-gate 				mdb_warn("failed to read devid_shr_rec at %p\n",
245*0Sstevel@tonic-gate 				    addr);
246*0Sstevel@tonic-gate 				return;
247*0Sstevel@tonic-gate 			}
248*0Sstevel@tonic-gate 		} else {
249*0Sstevel@tonic-gate 			if (mdb_vread(&devid_record,
250*0Sstevel@tonic-gate 			    sizeof (struct devid_min_rec), addr)
251*0Sstevel@tonic-gate 			    != sizeof (struct devid_min_rec)) {
252*0Sstevel@tonic-gate 				mdb_warn("failed to read devid_min_rec at %p\n",
253*0Sstevel@tonic-gate 				    addr);
254*0Sstevel@tonic-gate 				return;
255*0Sstevel@tonic-gate 			}
256*0Sstevel@tonic-gate 		}
257*0Sstevel@tonic-gate 	} else {
258*0Sstevel@tonic-gate 		if (shared) {
259*0Sstevel@tonic-gate 			if (mdb_vread(&srhdr, sizeof (struct nm_shr_rec), addr)
260*0Sstevel@tonic-gate 			    != sizeof (struct nm_shr_rec)) {
261*0Sstevel@tonic-gate 				mdb_warn("failed to read nm_shr_rec at %p\n",
262*0Sstevel@tonic-gate 				    addr);
263*0Sstevel@tonic-gate 				return;
264*0Sstevel@tonic-gate 			}
265*0Sstevel@tonic-gate 		} else {
266*0Sstevel@tonic-gate 			if (mdb_vread(&nm_record, sizeof (struct nm_rec), addr)
267*0Sstevel@tonic-gate 			    != sizeof (struct nm_rec)) {
268*0Sstevel@tonic-gate 				mdb_warn("failed to read nm_rec at %p\n", addr);
269*0Sstevel@tonic-gate 				return;
270*0Sstevel@tonic-gate 			}
271*0Sstevel@tonic-gate 		}
272*0Sstevel@tonic-gate 	}
273*0Sstevel@tonic-gate 	mdb_inc_indent(2);
274*0Sstevel@tonic-gate 	if (devid) {
275*0Sstevel@tonic-gate 		if (shared) {
276*0Sstevel@tonic-gate 			/*
277*0Sstevel@tonic-gate 			 * Do the rest of the device_id records.
278*0Sstevel@tonic-gate 			 */
279*0Sstevel@tonic-gate 			next_addr = addr + ((uintptr_t)&didsrhdr.device_id[0] -
280*0Sstevel@tonic-gate 			    (uintptr_t)&didsrhdr);
281*0Sstevel@tonic-gate 			start_addr = next_addr;
282*0Sstevel@tonic-gate 			for (i = 0; ; i++) {
283*0Sstevel@tonic-gate 				shn_addr = next_addr;
284*0Sstevel@tonic-gate 				next_addr = print_did_shared_name(shn_addr, i);
285*0Sstevel@tonic-gate 				if (next_addr == NULL) {
286*0Sstevel@tonic-gate 					mdb_dec_indent(2);
287*0Sstevel@tonic-gate 					return;
288*0Sstevel@tonic-gate 				}
289*0Sstevel@tonic-gate 				/*
290*0Sstevel@tonic-gate 				 * Causes us to print one extra record.
291*0Sstevel@tonic-gate 				 */
292*0Sstevel@tonic-gate 				if ((next_addr - start_addr > used_size) ||
293*0Sstevel@tonic-gate 				    (next_addr == shn_addr)) {
294*0Sstevel@tonic-gate 					break;
295*0Sstevel@tonic-gate 				}
296*0Sstevel@tonic-gate 			}
297*0Sstevel@tonic-gate 		} else {
298*0Sstevel@tonic-gate 			/*
299*0Sstevel@tonic-gate 			 * Now do the rest of the record.
300*0Sstevel@tonic-gate 			 */
301*0Sstevel@tonic-gate 			next_addr = addr +
302*0Sstevel@tonic-gate 			    ((uintptr_t)&devid_record.minor_name[0] -
303*0Sstevel@tonic-gate 			    (uintptr_t)&devid_record);
304*0Sstevel@tonic-gate 			start_addr = next_addr;
305*0Sstevel@tonic-gate 			for (i = 0; ; i++) {
306*0Sstevel@tonic-gate 				shn_addr = next_addr;
307*0Sstevel@tonic-gate 				next_addr = print_devid_name(shn_addr, i);
308*0Sstevel@tonic-gate 				if (next_addr == NULL) {
309*0Sstevel@tonic-gate 					mdb_dec_indent(2);
310*0Sstevel@tonic-gate 					return;
311*0Sstevel@tonic-gate 				}
312*0Sstevel@tonic-gate 				if ((next_addr - start_addr > used_size) ||
313*0Sstevel@tonic-gate 				    (next_addr == shn_addr)) {
314*0Sstevel@tonic-gate 					break;
315*0Sstevel@tonic-gate 				}
316*0Sstevel@tonic-gate 			}
317*0Sstevel@tonic-gate 		}
318*0Sstevel@tonic-gate 	} else {
319*0Sstevel@tonic-gate 		if (shared) {
320*0Sstevel@tonic-gate 			/*
321*0Sstevel@tonic-gate 			 * Now do the rest of the sr_name records.
322*0Sstevel@tonic-gate 			 */
323*0Sstevel@tonic-gate 			next_addr = addr + ((uintptr_t)&srhdr.sr_name[0] -
324*0Sstevel@tonic-gate 			    (uintptr_t)&srhdr);
325*0Sstevel@tonic-gate 			start_addr = next_addr;
326*0Sstevel@tonic-gate 			for (i = 0; ; i++) {
327*0Sstevel@tonic-gate 				shn_addr = next_addr;
328*0Sstevel@tonic-gate 				next_addr = print_nm_shared_name(shn_addr, i);
329*0Sstevel@tonic-gate 				if (next_addr == NULL) {
330*0Sstevel@tonic-gate 					mdb_dec_indent(2);
331*0Sstevel@tonic-gate 					return;
332*0Sstevel@tonic-gate 				}
333*0Sstevel@tonic-gate 				/*
334*0Sstevel@tonic-gate 				 * Causes us to print one extra record
335*0Sstevel@tonic-gate 				 */
336*0Sstevel@tonic-gate 				if ((next_addr - start_addr > used_size) ||
337*0Sstevel@tonic-gate 				    (next_addr == shn_addr)) {
338*0Sstevel@tonic-gate 					break;
339*0Sstevel@tonic-gate 				}
340*0Sstevel@tonic-gate 			}
341*0Sstevel@tonic-gate 		} else {
342*0Sstevel@tonic-gate 			/*
343*0Sstevel@tonic-gate 			 * Now do the rest of the record
344*0Sstevel@tonic-gate 			 */
345*0Sstevel@tonic-gate 			next_addr = addr + ((uintptr_t)&nm_record.r_name[0] -
346*0Sstevel@tonic-gate 			    (uintptr_t)&nm_record);
347*0Sstevel@tonic-gate 			start_addr = next_addr;
348*0Sstevel@tonic-gate 			for (i = 0; ; i++) {
349*0Sstevel@tonic-gate 				shn_addr = next_addr;
350*0Sstevel@tonic-gate 				next_addr = print_nm_name(shn_addr, i);
351*0Sstevel@tonic-gate 				if (next_addr == NULL) {
352*0Sstevel@tonic-gate 					mdb_dec_indent(2);
353*0Sstevel@tonic-gate 					return;
354*0Sstevel@tonic-gate 				}
355*0Sstevel@tonic-gate 				if ((next_addr - start_addr > used_size) ||
356*0Sstevel@tonic-gate 				    (next_addr == shn_addr)) {
357*0Sstevel@tonic-gate 					break;
358*0Sstevel@tonic-gate 				}
359*0Sstevel@tonic-gate 			}
360*0Sstevel@tonic-gate 		}
361*0Sstevel@tonic-gate 	}
362*0Sstevel@tonic-gate 	mdb_dec_indent(2);
363*0Sstevel@tonic-gate }
364*0Sstevel@tonic-gate 
365*0Sstevel@tonic-gate static void
process_nm_next_hdr(uintptr_t addr,int shared,int devid)366*0Sstevel@tonic-gate process_nm_next_hdr(uintptr_t addr, int shared, int devid)
367*0Sstevel@tonic-gate {
368*0Sstevel@tonic-gate 	uintptr_t	next = addr;
369*0Sstevel@tonic-gate 	struct nm_next_hdr	nhdr;
370*0Sstevel@tonic-gate 
371*0Sstevel@tonic-gate 	mdb_inc_indent(2);
372*0Sstevel@tonic-gate 	mdb_printf("%p\n", next);
373*0Sstevel@tonic-gate 	if (mdb_vread(&nhdr, sizeof (struct nm_next_hdr), next) !=
374*0Sstevel@tonic-gate 	    sizeof (struct nm_next_hdr)) {
375*0Sstevel@tonic-gate 		mdb_warn("failed to read nm_next_hdr at %p", next);
376*0Sstevel@tonic-gate 		return;
377*0Sstevel@tonic-gate 	}
378*0Sstevel@tonic-gate 	(void) process_nmn_record_hdr((uintptr_t)nhdr.nmn_record);
379*0Sstevel@tonic-gate 	next = (uintptr_t)nhdr.nmn_nextp;
380*0Sstevel@tonic-gate 	while (next != (uintptr_t)0) {
381*0Sstevel@tonic-gate 
382*0Sstevel@tonic-gate 		mdb_printf("\n");
383*0Sstevel@tonic-gate 		mdb_printf("nmn_nextp %p\n", nhdr.nmn_nextp);
384*0Sstevel@tonic-gate 		if (mdb_vread(&nhdr, sizeof (struct nm_next_hdr), next) !=
385*0Sstevel@tonic-gate 		    sizeof (struct nm_next_hdr)) {
386*0Sstevel@tonic-gate 			mdb_warn("failed to read nm_next_hdr at %p\n", next);
387*0Sstevel@tonic-gate 			break;
388*0Sstevel@tonic-gate 		}
389*0Sstevel@tonic-gate 		process_nmn_record((uintptr_t)nhdr.nmn_record, shared, devid);
390*0Sstevel@tonic-gate 		next = (uintptr_t)nhdr.nmn_nextp;
391*0Sstevel@tonic-gate 	}
392*0Sstevel@tonic-gate 	mdb_printf("\n");
393*0Sstevel@tonic-gate 	mdb_dec_indent(2);
394*0Sstevel@tonic-gate }
395*0Sstevel@tonic-gate /*
396*0Sstevel@tonic-gate  * Start the processing of a nominated set
397*0Sstevel@tonic-gate  */
398*0Sstevel@tonic-gate static void
process_set(int setno)399*0Sstevel@tonic-gate process_set(int setno)
400*0Sstevel@tonic-gate {
401*0Sstevel@tonic-gate 	uintptr_t	addr = (uintptr_t)mdset[setno].s_nm;
402*0Sstevel@tonic-gate 	uintptr_t	did_addr = (uintptr_t)mdset[setno].s_did_nm;
403*0Sstevel@tonic-gate 	uintptr_t	shared_addr, names_addr;
404*0Sstevel@tonic-gate 	uintptr_t	did_names_addr, did_shared_addr;
405*0Sstevel@tonic-gate 	struct nm_header_hdr	hdr, did_hdr;
406*0Sstevel@tonic-gate 
407*0Sstevel@tonic-gate 	mdb_printf("------ Name Space for setno %d ------\n", setno);
408*0Sstevel@tonic-gate 
409*0Sstevel@tonic-gate 	if (mdb_vread(&hdr, sizeof (struct nm_header_hdr), addr) !=
410*0Sstevel@tonic-gate 	    sizeof (struct nm_header_hdr)) {
411*0Sstevel@tonic-gate 		mdb_warn("failed to read nm_header_hdr at %p\n", addr);
412*0Sstevel@tonic-gate 		return;
413*0Sstevel@tonic-gate 	}
414*0Sstevel@tonic-gate 	mdb_printf("hh_header: %p  \n", hdr.hh_header);
415*0Sstevel@tonic-gate 	if (did_addr != NULL) {	/* device id's exist */
416*0Sstevel@tonic-gate 		if (mdb_vread(&did_hdr, sizeof (struct nm_header_hdr),
417*0Sstevel@tonic-gate 		    did_addr) != sizeof (struct nm_header_hdr)) {
418*0Sstevel@tonic-gate 			mdb_warn("failed to read nm_header_hdr at %p\n",
419*0Sstevel@tonic-gate 			    did_addr);
420*0Sstevel@tonic-gate 			return;
421*0Sstevel@tonic-gate 		}
422*0Sstevel@tonic-gate 		mdb_printf("did hh_header: %p \n", did_hdr.hh_header);
423*0Sstevel@tonic-gate 	did_names_addr =
424*0Sstevel@tonic-gate 	    (uintptr_t)&(((struct nm_header_hdr *)did_addr)->hh_names);
425*0Sstevel@tonic-gate 	did_shared_addr =
426*0Sstevel@tonic-gate 	    (uintptr_t)&(((struct nm_header_hdr *)did_addr)->hh_shared);
427*0Sstevel@tonic-gate 	}
428*0Sstevel@tonic-gate 
429*0Sstevel@tonic-gate 	names_addr = (uintptr_t)&(((struct nm_header_hdr *)addr)->hh_names);
430*0Sstevel@tonic-gate 	shared_addr = (uintptr_t)&(((struct nm_header_hdr *)addr)->hh_shared);
431*0Sstevel@tonic-gate 	mdb_printf("hh_names: %p \n", names_addr);
432*0Sstevel@tonic-gate 	mdb_printf("hh_shared: %p\n", shared_addr);
433*0Sstevel@tonic-gate 
434*0Sstevel@tonic-gate 	if (did_addr != NULL) {
435*0Sstevel@tonic-gate 		mdb_printf("did hh_names: %p \n", did_names_addr);
436*0Sstevel@tonic-gate 		mdb_printf("did hh_shared: %p\n", did_shared_addr);
437*0Sstevel@tonic-gate 	}
438*0Sstevel@tonic-gate 
439*0Sstevel@tonic-gate 	mdb_printf("hh_names:");
440*0Sstevel@tonic-gate 	process_nm_next_hdr(names_addr, 0, 0);
441*0Sstevel@tonic-gate 	mdb_printf("\nhh_shared:");
442*0Sstevel@tonic-gate 	process_nm_next_hdr(shared_addr, 1, 0);
443*0Sstevel@tonic-gate 
444*0Sstevel@tonic-gate 	if (did_addr != NULL) {
445*0Sstevel@tonic-gate 		mdb_printf("did hh_names:");
446*0Sstevel@tonic-gate 		process_nm_next_hdr(did_names_addr, 0, 1);
447*0Sstevel@tonic-gate 		mdb_printf("\ndid hh_shared:");
448*0Sstevel@tonic-gate 		process_nm_next_hdr(did_shared_addr, 1, 1);
449*0Sstevel@tonic-gate 	}
450*0Sstevel@tonic-gate }
451*0Sstevel@tonic-gate /*
452*0Sstevel@tonic-gate  * Dump the name space for all sets or specified set (-s option)
453*0Sstevel@tonic-gate  * usage: ::dumpnamespace [-s setname]
454*0Sstevel@tonic-gate  */
455*0Sstevel@tonic-gate /* ARGSUSED */
456*0Sstevel@tonic-gate int
dumpnamespace(uintptr_t addr,uint_t flags,int argc,const mdb_arg_t * argv)457*0Sstevel@tonic-gate dumpnamespace(uintptr_t addr, uint_t flags, int argc, const mdb_arg_t *argv)
458*0Sstevel@tonic-gate {
459*0Sstevel@tonic-gate 	char	*s_opt = NULL;
460*0Sstevel@tonic-gate 	int	j;
461*0Sstevel@tonic-gate 	int	setno;
462*0Sstevel@tonic-gate 
463*0Sstevel@tonic-gate 	if (mdb_getopts(argc, argv, 's', MDB_OPT_STR, &s_opt,
464*0Sstevel@tonic-gate 	    NULL) != argc) {
465*0Sstevel@tonic-gate 		/* left over arguments ?? */
466*0Sstevel@tonic-gate 		return (DCMD_USAGE);
467*0Sstevel@tonic-gate 	}
468*0Sstevel@tonic-gate 
469*0Sstevel@tonic-gate 	snarf_sets();
470*0Sstevel@tonic-gate 
471*0Sstevel@tonic-gate 	if (argc == 0) {
472*0Sstevel@tonic-gate 		for (j = 0; j < md_nsets; j++) {
473*0Sstevel@tonic-gate 			if (mdset[j].s_status & MD_SET_NM_LOADED) {
474*0Sstevel@tonic-gate 				process_set(j);
475*0Sstevel@tonic-gate 			}
476*0Sstevel@tonic-gate 		}
477*0Sstevel@tonic-gate 	} else {
478*0Sstevel@tonic-gate 		setno = findset(s_opt);
479*0Sstevel@tonic-gate 		if (setno == -1) {
480*0Sstevel@tonic-gate 			mdb_warn("no such set: %s\n", s_opt);
481*0Sstevel@tonic-gate 			return (DCMD_ERR);
482*0Sstevel@tonic-gate 		}
483*0Sstevel@tonic-gate 		if (mdset[setno].s_status & MD_SET_NM_LOADED) {
484*0Sstevel@tonic-gate 			process_set(setno);
485*0Sstevel@tonic-gate 		}
486*0Sstevel@tonic-gate 	}
487*0Sstevel@tonic-gate 	return (DCMD_OK);
488*0Sstevel@tonic-gate }
489