xref: /onnv-gate/usr/src/cmd/mdb/common/modules/ipp/ipp.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 2001-2002 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 <sys/time.h>
30*0Sstevel@tonic-gate #include <ipp/ipp.h>
31*0Sstevel@tonic-gate #include <ipp/ipp_impl.h>
32*0Sstevel@tonic-gate #include <mdb/mdb_modapi.h>
33*0Sstevel@tonic-gate 
34*0Sstevel@tonic-gate static uintptr_t	ipp_mod_byid;
35*0Sstevel@tonic-gate static uintptr_t	ipp_action_byid;
36*0Sstevel@tonic-gate 
37*0Sstevel@tonic-gate static int	byid_walk_init(mdb_walk_state_t *);
38*0Sstevel@tonic-gate static int	byid_walk_step(mdb_walk_state_t *);
39*0Sstevel@tonic-gate static void	byid_walk_fini(mdb_walk_state_t *);
40*0Sstevel@tonic-gate 
41*0Sstevel@tonic-gate static int	action(uintptr_t, uint_t, int, const mdb_arg_t *);
42*0Sstevel@tonic-gate static int	action_format(uintptr_t, const void *, void *);
43*0Sstevel@tonic-gate static int	action_dump(uintptr_t, ipp_action_t *, boolean_t);
44*0Sstevel@tonic-gate static int	action_summary(uintptr_t, ipp_action_t *, boolean_t);
45*0Sstevel@tonic-gate 
46*0Sstevel@tonic-gate static int	cfglock(uintptr_t, uint_t, int, const mdb_arg_t *);
47*0Sstevel@tonic-gate 
48*0Sstevel@tonic-gate static int	mod(uintptr_t, uint_t, int, const mdb_arg_t *);
49*0Sstevel@tonic-gate static int	mod_format(uintptr_t, const void *, void *);
50*0Sstevel@tonic-gate static int	mod_dump(uintptr_t, ipp_mod_t *, boolean_t);
51*0Sstevel@tonic-gate static int	mod_summary(uintptr_t, ipp_mod_t *, boolean_t);
52*0Sstevel@tonic-gate static int	cfglock(uintptr_t, uint_t, int, const mdb_arg_t *);
53*0Sstevel@tonic-gate 
54*0Sstevel@tonic-gate static int	ippops(uintptr_t, uint_t, int, const mdb_arg_t *);
55*0Sstevel@tonic-gate 
56*0Sstevel@tonic-gate static int	packet(uintptr_t, uint_t, int, const mdb_arg_t *);
57*0Sstevel@tonic-gate static void	dump_classes(uintptr_t, uint_t);
58*0Sstevel@tonic-gate static void	dump_log(uintptr_t, uint_t);
59*0Sstevel@tonic-gate static void	aid2aname(ipp_action_id_t, char *);
60*0Sstevel@tonic-gate 
61*0Sstevel@tonic-gate static int	ref_walk_init(mdb_walk_state_t *);
62*0Sstevel@tonic-gate static int	ref_walk_step(mdb_walk_state_t *);
63*0Sstevel@tonic-gate static void	ref_walk_fini(mdb_walk_state_t *);
64*0Sstevel@tonic-gate 
65*0Sstevel@tonic-gate typedef	struct afdata {
66*0Sstevel@tonic-gate 	boolean_t	af_banner;
67*0Sstevel@tonic-gate 	uint_t		af_flags;
68*0Sstevel@tonic-gate } afdata_t;
69*0Sstevel@tonic-gate 
70*0Sstevel@tonic-gate #define	AF_VERBOSE	1
71*0Sstevel@tonic-gate 
72*0Sstevel@tonic-gate typedef	struct mfdata {
73*0Sstevel@tonic-gate 	boolean_t	mf_banner;
74*0Sstevel@tonic-gate 	uint_t		mf_flags;
75*0Sstevel@tonic-gate } mfdata_t;
76*0Sstevel@tonic-gate 
77*0Sstevel@tonic-gate #define	MF_VERBOSE	1
78*0Sstevel@tonic-gate 
79*0Sstevel@tonic-gate /*
80*0Sstevel@tonic-gate  * walker. Skips entries that are NULL.
81*0Sstevel@tonic-gate  */
82*0Sstevel@tonic-gate 
83*0Sstevel@tonic-gate static int
byid_walk_init(mdb_walk_state_t * wsp)84*0Sstevel@tonic-gate byid_walk_init(
85*0Sstevel@tonic-gate 	mdb_walk_state_t *wsp)
86*0Sstevel@tonic-gate {
87*0Sstevel@tonic-gate 	uintptr_t	start;
88*0Sstevel@tonic-gate 
89*0Sstevel@tonic-gate 	if (mdb_vread(&start, sizeof (uintptr_t), wsp->walk_addr) == -1) {
90*0Sstevel@tonic-gate 		mdb_warn("failed to read from address %p", wsp->walk_addr);
91*0Sstevel@tonic-gate 		return (WALK_ERR);
92*0Sstevel@tonic-gate 	}
93*0Sstevel@tonic-gate 
94*0Sstevel@tonic-gate 	wsp->walk_addr = start;
95*0Sstevel@tonic-gate 
96*0Sstevel@tonic-gate 	return (WALK_NEXT);
97*0Sstevel@tonic-gate }
98*0Sstevel@tonic-gate 
99*0Sstevel@tonic-gate static int
byid_walk_step(mdb_walk_state_t * wsp)100*0Sstevel@tonic-gate byid_walk_step(
101*0Sstevel@tonic-gate 	mdb_walk_state_t *wsp)
102*0Sstevel@tonic-gate {
103*0Sstevel@tonic-gate 	int		status;
104*0Sstevel@tonic-gate 	void 		*ptr;
105*0Sstevel@tonic-gate 
106*0Sstevel@tonic-gate 	if (mdb_vread(&ptr, sizeof (void *), wsp->walk_addr) == -1) {
107*0Sstevel@tonic-gate 		mdb_warn("failed to read from address %p", wsp->walk_addr);
108*0Sstevel@tonic-gate 		return (WALK_ERR);
109*0Sstevel@tonic-gate 	}
110*0Sstevel@tonic-gate 
111*0Sstevel@tonic-gate 	if (ptr == (void *)-1) {
112*0Sstevel@tonic-gate 		status = WALK_DONE;
113*0Sstevel@tonic-gate 	} else if (ptr == NULL) {
114*0Sstevel@tonic-gate 		status = WALK_NEXT;
115*0Sstevel@tonic-gate 	} else {
116*0Sstevel@tonic-gate 		status = wsp->walk_callback((uintptr_t)ptr, NULL,
117*0Sstevel@tonic-gate 		    wsp->walk_cbdata);
118*0Sstevel@tonic-gate 	}
119*0Sstevel@tonic-gate 
120*0Sstevel@tonic-gate 	wsp->walk_addr += sizeof (void *);
121*0Sstevel@tonic-gate 
122*0Sstevel@tonic-gate 	return (status);
123*0Sstevel@tonic-gate }
124*0Sstevel@tonic-gate 
125*0Sstevel@tonic-gate /*ARGSUSED*/
126*0Sstevel@tonic-gate static void
byid_walk_fini(mdb_walk_state_t * wsp)127*0Sstevel@tonic-gate byid_walk_fini(
128*0Sstevel@tonic-gate 	mdb_walk_state_t *wsp)
129*0Sstevel@tonic-gate {
130*0Sstevel@tonic-gate }
131*0Sstevel@tonic-gate 
132*0Sstevel@tonic-gate 
133*0Sstevel@tonic-gate /*ARGSUSED*/
134*0Sstevel@tonic-gate static int
action(uintptr_t addr,uint_t flags,int argc,const mdb_arg_t * argv)135*0Sstevel@tonic-gate action(
136*0Sstevel@tonic-gate 	uintptr_t	addr,
137*0Sstevel@tonic-gate 	uint_t		flags,
138*0Sstevel@tonic-gate 	int		argc,
139*0Sstevel@tonic-gate 	const mdb_arg_t	*argv)
140*0Sstevel@tonic-gate {
141*0Sstevel@tonic-gate 	int		status;
142*0Sstevel@tonic-gate 	int		rc = DCMD_OK;
143*0Sstevel@tonic-gate 	afdata_t	*afp;
144*0Sstevel@tonic-gate 
145*0Sstevel@tonic-gate 	afp = mdb_zalloc(sizeof (afdata_t), UM_SLEEP);
146*0Sstevel@tonic-gate 
147*0Sstevel@tonic-gate 	if (mdb_getopts(argc, argv,
148*0Sstevel@tonic-gate 	    'v', MDB_OPT_SETBITS, AF_VERBOSE, &afp->af_flags,
149*0Sstevel@tonic-gate 	    NULL) != argc)
150*0Sstevel@tonic-gate 		return (DCMD_USAGE);
151*0Sstevel@tonic-gate 
152*0Sstevel@tonic-gate 	if ((flags & DCMD_LOOPFIRST) || !(flags & DCMD_LOOP))
153*0Sstevel@tonic-gate 		afp->af_banner = B_TRUE;
154*0Sstevel@tonic-gate 
155*0Sstevel@tonic-gate 	if (flags & DCMD_ADDRSPEC) {
156*0Sstevel@tonic-gate 		status = action_format(addr, NULL, afp);
157*0Sstevel@tonic-gate 		rc = (status == WALK_NEXT) ? DCMD_OK : DCMD_ERR;
158*0Sstevel@tonic-gate 		goto cleanup;
159*0Sstevel@tonic-gate 	}
160*0Sstevel@tonic-gate 
161*0Sstevel@tonic-gate 	if (mdb_pwalk("ipp_byid", action_format, afp,
162*0Sstevel@tonic-gate 	    ipp_action_byid) == -1) {
163*0Sstevel@tonic-gate 		mdb_warn("failed to execute ipp_byid walk");
164*0Sstevel@tonic-gate 		rc = DCMD_ERR;
165*0Sstevel@tonic-gate 	}
166*0Sstevel@tonic-gate 
167*0Sstevel@tonic-gate cleanup:
168*0Sstevel@tonic-gate 	mdb_free(afp, sizeof (afdata_t));
169*0Sstevel@tonic-gate 
170*0Sstevel@tonic-gate 	return (rc);
171*0Sstevel@tonic-gate }
172*0Sstevel@tonic-gate 
173*0Sstevel@tonic-gate /*ARGSUSED*/
174*0Sstevel@tonic-gate static int
action_format(uintptr_t addr,const void * data,void * arg)175*0Sstevel@tonic-gate action_format(
176*0Sstevel@tonic-gate 	uintptr_t	addr,
177*0Sstevel@tonic-gate 	const void	*data,
178*0Sstevel@tonic-gate 	void		*arg)
179*0Sstevel@tonic-gate {
180*0Sstevel@tonic-gate 	afdata_t	*afp = (afdata_t *)arg;
181*0Sstevel@tonic-gate 	ipp_action_t	*ap;
182*0Sstevel@tonic-gate 	int		rc;
183*0Sstevel@tonic-gate 
184*0Sstevel@tonic-gate 	ap = mdb_alloc(sizeof (ipp_action_t), UM_SLEEP);
185*0Sstevel@tonic-gate 	if (mdb_vread(ap, sizeof (ipp_action_t), addr) == -1) {
186*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_action_t at %p", addr);
187*0Sstevel@tonic-gate 		rc = WALK_ERR;
188*0Sstevel@tonic-gate 		goto done;
189*0Sstevel@tonic-gate 	}
190*0Sstevel@tonic-gate 
191*0Sstevel@tonic-gate 	if (afp->af_flags & AF_VERBOSE)
192*0Sstevel@tonic-gate 		rc = action_dump(addr, ap, afp->af_banner);
193*0Sstevel@tonic-gate 	else
194*0Sstevel@tonic-gate 		rc = action_summary(addr, ap, afp->af_banner);
195*0Sstevel@tonic-gate 
196*0Sstevel@tonic-gate 	afp->af_banner = B_FALSE;
197*0Sstevel@tonic-gate done:
198*0Sstevel@tonic-gate 	mdb_free(ap, sizeof (ipp_action_t));
199*0Sstevel@tonic-gate 	return (rc);
200*0Sstevel@tonic-gate }
201*0Sstevel@tonic-gate 
202*0Sstevel@tonic-gate /*ARGSUSED*/
203*0Sstevel@tonic-gate static int
action_dump(uintptr_t addr,ipp_action_t * ap,boolean_t banner)204*0Sstevel@tonic-gate action_dump(
205*0Sstevel@tonic-gate 	uintptr_t	addr,
206*0Sstevel@tonic-gate 	ipp_action_t	*ap,
207*0Sstevel@tonic-gate 	boolean_t	banner)
208*0Sstevel@tonic-gate {
209*0Sstevel@tonic-gate 	mdb_printf("%?p: %20s = %d\n", addr, "id", ap->ippa_id);
210*0Sstevel@tonic-gate 	if (!ap->ippa_nameless) {
211*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = %s\n", "", "name", ap->ippa_name);
212*0Sstevel@tonic-gate 	}
213*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "mod", ap->ippa_mod);
214*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "ref", ap->ippa_ref);
215*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "refby", ap->ippa_refby);
216*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "ptr", ap->ippa_ptr);
217*0Sstevel@tonic-gate 
218*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = ", "", "state");
219*0Sstevel@tonic-gate 	switch (ap->ippa_state) {
220*0Sstevel@tonic-gate 	case IPP_ASTATE_PROTO:
221*0Sstevel@tonic-gate 		mdb_printf("%s\n", "PROTO");
222*0Sstevel@tonic-gate 		break;
223*0Sstevel@tonic-gate 	case IPP_ASTATE_CONFIG_PENDING:
224*0Sstevel@tonic-gate 		mdb_printf("%s\n", "CONFIG_PENDING");
225*0Sstevel@tonic-gate 		break;
226*0Sstevel@tonic-gate 	case IPP_ASTATE_AVAILABLE:
227*0Sstevel@tonic-gate 		mdb_printf("%s\n", "AVAILABLE");
228*0Sstevel@tonic-gate 		break;
229*0Sstevel@tonic-gate 	default:
230*0Sstevel@tonic-gate 		mdb_printf("%s\n", "<unknown>");
231*0Sstevel@tonic-gate 		break;
232*0Sstevel@tonic-gate 	}
233*0Sstevel@tonic-gate 
234*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %d\n", "", "packets", ap->ippa_packets);
235*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %d\n", "", "hold_count", ap->ippa_hold_count);
236*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %s\n", "", "destruct_pending",
237*0Sstevel@tonic-gate 	    (ap->ippa_destruct_pending) ? "TRUE" : "FALSE");
238*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "lock",
239*0Sstevel@tonic-gate 	    addr + ((uintptr_t)ap->ippa_lock - (uintptr_t)ap));
240*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "config_lock",
241*0Sstevel@tonic-gate 	    addr + ((uintptr_t)ap->ippa_config_lock - (uintptr_t)ap));
242*0Sstevel@tonic-gate 	mdb_printf("\n");
243*0Sstevel@tonic-gate 
244*0Sstevel@tonic-gate 	return (WALK_NEXT);
245*0Sstevel@tonic-gate }
246*0Sstevel@tonic-gate 
247*0Sstevel@tonic-gate static int
action_summary(uintptr_t addr,ipp_action_t * ap,boolean_t banner)248*0Sstevel@tonic-gate action_summary(
249*0Sstevel@tonic-gate 	uintptr_t	addr,
250*0Sstevel@tonic-gate 	ipp_action_t	*ap,
251*0Sstevel@tonic-gate 	boolean_t	banner)
252*0Sstevel@tonic-gate {
253*0Sstevel@tonic-gate 	ipp_mod_t	*imp;
254*0Sstevel@tonic-gate 	uintptr_t	ptr;
255*0Sstevel@tonic-gate 
256*0Sstevel@tonic-gate 	if (banner)
257*0Sstevel@tonic-gate 		mdb_printf("%?s %<u>%20s %5s %20s%</u>\n",
258*0Sstevel@tonic-gate 		    "", "NAME", "ID", "MODNAME");
259*0Sstevel@tonic-gate 
260*0Sstevel@tonic-gate 	imp = mdb_alloc(sizeof (ipp_mod_t), UM_SLEEP);
261*0Sstevel@tonic-gate 	ptr = (uintptr_t)ap->ippa_mod;
262*0Sstevel@tonic-gate 	if (mdb_vread(imp, sizeof (ipp_mod_t), ptr) == -1) {
263*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_mod_t at %p", ptr);
264*0Sstevel@tonic-gate 		mdb_free(imp, sizeof (ipp_mod_t));
265*0Sstevel@tonic-gate 		return (WALK_ERR);
266*0Sstevel@tonic-gate 	}
267*0Sstevel@tonic-gate 
268*0Sstevel@tonic-gate 	mdb_printf("%?p:%20s %5d %20s\n", addr, ap->ippa_name, ap->ippa_id,
269*0Sstevel@tonic-gate 	    imp->ippm_name);
270*0Sstevel@tonic-gate 
271*0Sstevel@tonic-gate 	mdb_free(imp, sizeof (ipp_mod_t));
272*0Sstevel@tonic-gate 	return (WALK_NEXT);
273*0Sstevel@tonic-gate }
274*0Sstevel@tonic-gate 
275*0Sstevel@tonic-gate /*ARGSUSED*/
276*0Sstevel@tonic-gate static int
cfglock(uintptr_t addr,uint_t flags,int argc,const mdb_arg_t * argv)277*0Sstevel@tonic-gate cfglock(
278*0Sstevel@tonic-gate 	uintptr_t	addr,
279*0Sstevel@tonic-gate 	uint_t		flags,
280*0Sstevel@tonic-gate 	int		argc,
281*0Sstevel@tonic-gate 	const mdb_arg_t	*argv)
282*0Sstevel@tonic-gate {
283*0Sstevel@tonic-gate 	cfglock_t	*clp;
284*0Sstevel@tonic-gate 
285*0Sstevel@tonic-gate 	if ((flags & DCMD_ADDRSPEC) == 0)
286*0Sstevel@tonic-gate 		return (DCMD_ERR);
287*0Sstevel@tonic-gate 
288*0Sstevel@tonic-gate 	clp = mdb_alloc(sizeof (cfglock_t), UM_SLEEP);
289*0Sstevel@tonic-gate 	if (mdb_vread(clp, sizeof (cfglock_t), addr) == -1) {
290*0Sstevel@tonic-gate 		mdb_warn("failed to read cfglock_t at %p", addr);
291*0Sstevel@tonic-gate 		mdb_free(clp, sizeof (cfglock_t));
292*0Sstevel@tonic-gate 		return (WALK_ERR);
293*0Sstevel@tonic-gate 	}
294*0Sstevel@tonic-gate 
295*0Sstevel@tonic-gate 	mdb_printf("%?p: %20s = %p\n", addr, "owner", clp->cl_owner);
296*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %s\n", "", "reader",
297*0Sstevel@tonic-gate 	    clp->cl_reader ? "TRUE" : "FALSE");
298*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %d\n", "", "writers", clp->cl_writers);
299*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "mutex",
300*0Sstevel@tonic-gate 	    addr + ((uintptr_t)clp->cl_mutex - (uintptr_t)clp));
301*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "cv",
302*0Sstevel@tonic-gate 	    addr + ((uintptr_t)clp->cl_cv - (uintptr_t)clp));
303*0Sstevel@tonic-gate 	mdb_printf("\n");
304*0Sstevel@tonic-gate 
305*0Sstevel@tonic-gate 	mdb_free(clp, sizeof (cfglock_t));
306*0Sstevel@tonic-gate 
307*0Sstevel@tonic-gate 	return (DCMD_OK);
308*0Sstevel@tonic-gate }
309*0Sstevel@tonic-gate 
310*0Sstevel@tonic-gate /*ARGSUSED*/
311*0Sstevel@tonic-gate static int
mod(uintptr_t addr,uint_t flags,int argc,const mdb_arg_t * argv)312*0Sstevel@tonic-gate mod(
313*0Sstevel@tonic-gate 	uintptr_t	addr,
314*0Sstevel@tonic-gate 	uint_t		flags,
315*0Sstevel@tonic-gate 	int		argc,
316*0Sstevel@tonic-gate 	const mdb_arg_t	*argv)
317*0Sstevel@tonic-gate {
318*0Sstevel@tonic-gate 	int		status;
319*0Sstevel@tonic-gate 	int		rc = DCMD_OK;
320*0Sstevel@tonic-gate 	mfdata_t	*mfp;
321*0Sstevel@tonic-gate 
322*0Sstevel@tonic-gate 	mfp = mdb_zalloc(sizeof (mfdata_t), UM_SLEEP);
323*0Sstevel@tonic-gate 
324*0Sstevel@tonic-gate 	if (mdb_getopts(argc, argv,
325*0Sstevel@tonic-gate 	    'v', MDB_OPT_SETBITS, MF_VERBOSE, &mfp->mf_flags,
326*0Sstevel@tonic-gate 	    NULL) != argc)
327*0Sstevel@tonic-gate 		return (DCMD_USAGE);
328*0Sstevel@tonic-gate 
329*0Sstevel@tonic-gate 	if ((flags & DCMD_LOOPFIRST) || !(flags & DCMD_LOOP))
330*0Sstevel@tonic-gate 		mfp->mf_banner = B_TRUE;
331*0Sstevel@tonic-gate 
332*0Sstevel@tonic-gate 	if (flags & DCMD_ADDRSPEC) {
333*0Sstevel@tonic-gate 		status = mod_format(addr, NULL, mfp);
334*0Sstevel@tonic-gate 		rc = (status == WALK_NEXT) ? DCMD_OK : DCMD_ERR;
335*0Sstevel@tonic-gate 		goto cleanup;
336*0Sstevel@tonic-gate 	}
337*0Sstevel@tonic-gate 
338*0Sstevel@tonic-gate 	if (mdb_pwalk("ipp_byid", mod_format, mfp,
339*0Sstevel@tonic-gate 	    ipp_mod_byid) == -1) {
340*0Sstevel@tonic-gate 		mdb_warn("failed to execute ipp_byid walk");
341*0Sstevel@tonic-gate 		rc = DCMD_ERR;
342*0Sstevel@tonic-gate 	}
343*0Sstevel@tonic-gate 
344*0Sstevel@tonic-gate cleanup:
345*0Sstevel@tonic-gate 	mdb_free(mfp, sizeof (mfdata_t));
346*0Sstevel@tonic-gate 
347*0Sstevel@tonic-gate 	return (rc);
348*0Sstevel@tonic-gate }
349*0Sstevel@tonic-gate 
350*0Sstevel@tonic-gate /*ARGSUSED*/
351*0Sstevel@tonic-gate static int
mod_format(uintptr_t addr,const void * data,void * arg)352*0Sstevel@tonic-gate mod_format(
353*0Sstevel@tonic-gate 	uintptr_t	addr,
354*0Sstevel@tonic-gate 	const void	*data,
355*0Sstevel@tonic-gate 	void		*arg)
356*0Sstevel@tonic-gate {
357*0Sstevel@tonic-gate 	mfdata_t	*mfp = (mfdata_t *)arg;
358*0Sstevel@tonic-gate 	ipp_mod_t	*imp;
359*0Sstevel@tonic-gate 	int		rc;
360*0Sstevel@tonic-gate 
361*0Sstevel@tonic-gate 	imp = mdb_alloc(sizeof (ipp_mod_t), UM_SLEEP);
362*0Sstevel@tonic-gate 	if (mdb_vread(imp, sizeof (ipp_mod_t), addr) == -1) {
363*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_mod_t at %p", addr);
364*0Sstevel@tonic-gate 		rc = WALK_ERR;
365*0Sstevel@tonic-gate 		goto done;
366*0Sstevel@tonic-gate 	}
367*0Sstevel@tonic-gate 
368*0Sstevel@tonic-gate 	if (mfp->mf_flags & MF_VERBOSE)
369*0Sstevel@tonic-gate 		rc = mod_dump(addr, imp, mfp->mf_banner);
370*0Sstevel@tonic-gate 	else
371*0Sstevel@tonic-gate 		rc = mod_summary(addr, imp, mfp->mf_banner);
372*0Sstevel@tonic-gate 
373*0Sstevel@tonic-gate 	mfp->mf_banner = B_FALSE;
374*0Sstevel@tonic-gate done:
375*0Sstevel@tonic-gate 	mdb_free(imp, sizeof (ipp_mod_t));
376*0Sstevel@tonic-gate 	return (rc);
377*0Sstevel@tonic-gate }
378*0Sstevel@tonic-gate 
379*0Sstevel@tonic-gate /*ARGSUSED*/
380*0Sstevel@tonic-gate static int
mod_dump(uintptr_t addr,ipp_mod_t * imp,boolean_t banner)381*0Sstevel@tonic-gate mod_dump(
382*0Sstevel@tonic-gate 	uintptr_t	addr,
383*0Sstevel@tonic-gate 	ipp_mod_t	*imp,
384*0Sstevel@tonic-gate 	boolean_t	banner)
385*0Sstevel@tonic-gate {
386*0Sstevel@tonic-gate 	mdb_printf("%?p: %20s = %d\n", addr, "id", imp->ippm_id);
387*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %s\n", "", "name", imp->ippm_name);
388*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "ops", imp->ippm_ops);
389*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "action", imp->ippm_action);
390*0Sstevel@tonic-gate 
391*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = ", "", "state");
392*0Sstevel@tonic-gate 	switch (imp->ippm_state) {
393*0Sstevel@tonic-gate 	case IPP_MODSTATE_PROTO:
394*0Sstevel@tonic-gate 		mdb_printf("%s\n", "PROTO");
395*0Sstevel@tonic-gate 		break;
396*0Sstevel@tonic-gate 	case IPP_MODSTATE_AVAILABLE:
397*0Sstevel@tonic-gate 		mdb_printf("%s\n", "AVAILABLE");
398*0Sstevel@tonic-gate 		break;
399*0Sstevel@tonic-gate 	default:
400*0Sstevel@tonic-gate 		mdb_printf("%s\n", "<unknown>");
401*0Sstevel@tonic-gate 		break;
402*0Sstevel@tonic-gate 	}
403*0Sstevel@tonic-gate 
404*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %d\n", "", "hold_count", imp->ippm_hold_count);
405*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = %s\n", "", "destruct_pending",
406*0Sstevel@tonic-gate 	    (imp->ippm_destruct_pending) ? "TRUE" : "FALSE");
407*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "lock",
408*0Sstevel@tonic-gate 	    addr + ((uintptr_t)imp->ippm_lock - (uintptr_t)imp));
409*0Sstevel@tonic-gate 	mdb_printf("\n");
410*0Sstevel@tonic-gate 
411*0Sstevel@tonic-gate 	return (WALK_NEXT);
412*0Sstevel@tonic-gate }
413*0Sstevel@tonic-gate 
414*0Sstevel@tonic-gate static int
mod_summary(uintptr_t addr,ipp_mod_t * imp,boolean_t banner)415*0Sstevel@tonic-gate mod_summary(
416*0Sstevel@tonic-gate 	uintptr_t	addr,
417*0Sstevel@tonic-gate 	ipp_mod_t	*imp,
418*0Sstevel@tonic-gate 	boolean_t	banner)
419*0Sstevel@tonic-gate {
420*0Sstevel@tonic-gate 	if (banner)
421*0Sstevel@tonic-gate 		mdb_printf("%?s %<u>%20s %5s%</u>\n",
422*0Sstevel@tonic-gate 		    "", "NAME", "ID");
423*0Sstevel@tonic-gate 
424*0Sstevel@tonic-gate 	mdb_printf("%?p:%20s %5d\n", addr, imp->ippm_name, imp->ippm_id);
425*0Sstevel@tonic-gate 
426*0Sstevel@tonic-gate 	return (WALK_NEXT);
427*0Sstevel@tonic-gate }
428*0Sstevel@tonic-gate 
429*0Sstevel@tonic-gate /*ARGSUSED*/
430*0Sstevel@tonic-gate static int
ippops(uintptr_t addr,uint_t flags,int argc,const mdb_arg_t * argv)431*0Sstevel@tonic-gate ippops(
432*0Sstevel@tonic-gate 	uintptr_t	addr,
433*0Sstevel@tonic-gate 	uint_t		flags,
434*0Sstevel@tonic-gate 	int		argc,
435*0Sstevel@tonic-gate 	const mdb_arg_t	*argv)
436*0Sstevel@tonic-gate {
437*0Sstevel@tonic-gate 	ipp_ops_t	*ippo;
438*0Sstevel@tonic-gate 	GElf_Sym	sym;
439*0Sstevel@tonic-gate 	char		buf[MDB_SYM_NAMLEN];
440*0Sstevel@tonic-gate 
441*0Sstevel@tonic-gate 	if ((flags & DCMD_ADDRSPEC) == 0)
442*0Sstevel@tonic-gate 		return (DCMD_ERR);
443*0Sstevel@tonic-gate 
444*0Sstevel@tonic-gate 	ippo = mdb_alloc(sizeof (ipp_ops_t), UM_SLEEP);
445*0Sstevel@tonic-gate 	if (mdb_vread(ippo, sizeof (ipp_ops_t), addr) == -1) {
446*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_ops_t at %p", addr);
447*0Sstevel@tonic-gate 		mdb_free(ippo, sizeof (ipp_ops_t));
448*0Sstevel@tonic-gate 		return (DCMD_ERR);
449*0Sstevel@tonic-gate 	}
450*0Sstevel@tonic-gate 
451*0Sstevel@tonic-gate 	mdb_printf("%?p: %20s = %d\n", addr, "rev", ippo->ippo_rev);
452*0Sstevel@tonic-gate 
453*0Sstevel@tonic-gate 	if (mdb_lookup_by_addr((uintptr_t)ippo->ippo_action_create,
454*0Sstevel@tonic-gate 	    MDB_SYM_EXACT, buf, MDB_SYM_NAMLEN, &sym) == 0)
455*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = %s\n", "", "action_create", buf);
456*0Sstevel@tonic-gate 	else
457*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = 0x%p\n", "", "action_create",
458*0Sstevel@tonic-gate 		    ippo->ippo_action_create);
459*0Sstevel@tonic-gate 
460*0Sstevel@tonic-gate 	if (mdb_lookup_by_addr((uintptr_t)ippo->ippo_action_modify,
461*0Sstevel@tonic-gate 	    MDB_SYM_EXACT, buf, MDB_SYM_NAMLEN, &sym) == 0)
462*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = %s\n", "", "action_modify", buf);
463*0Sstevel@tonic-gate 	else
464*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = 0x%p\n", "", "action_modify",
465*0Sstevel@tonic-gate 		    ippo->ippo_action_modify);
466*0Sstevel@tonic-gate 
467*0Sstevel@tonic-gate 	if (mdb_lookup_by_addr((uintptr_t)ippo->ippo_action_destroy,
468*0Sstevel@tonic-gate 	    MDB_SYM_EXACT, buf, MDB_SYM_NAMLEN, &sym) == 0)
469*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = %s\n", "", "action_destroy", buf);
470*0Sstevel@tonic-gate 	else
471*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = 0x%p\n", "", "action_destroy",
472*0Sstevel@tonic-gate 		    ippo->ippo_action_destroy);
473*0Sstevel@tonic-gate 
474*0Sstevel@tonic-gate 	if (mdb_lookup_by_addr((uintptr_t)ippo->ippo_action_info,
475*0Sstevel@tonic-gate 	    MDB_SYM_EXACT, buf, MDB_SYM_NAMLEN, &sym) == 0)
476*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = %s\n", "", "action_info", buf);
477*0Sstevel@tonic-gate 	else
478*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = 0x%p\n", "", "action_info",
479*0Sstevel@tonic-gate 		    ippo->ippo_action_info);
480*0Sstevel@tonic-gate 
481*0Sstevel@tonic-gate 	if (mdb_lookup_by_addr((uintptr_t)ippo->ippo_action_invoke,
482*0Sstevel@tonic-gate 	    MDB_SYM_EXACT, buf, MDB_SYM_NAMLEN, &sym) == 0)
483*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = %s\n", "", "action_invoke", buf);
484*0Sstevel@tonic-gate 	else
485*0Sstevel@tonic-gate 		mdb_printf("%?s  %20s = 0x%p\n", "", "action_invoke",
486*0Sstevel@tonic-gate 		    ippo->ippo_action_invoke);
487*0Sstevel@tonic-gate 
488*0Sstevel@tonic-gate 	mdb_printf("\n");
489*0Sstevel@tonic-gate 
490*0Sstevel@tonic-gate 	mdb_free(ippo, sizeof (ipp_ops_t));
491*0Sstevel@tonic-gate 	return (DCMD_OK);
492*0Sstevel@tonic-gate }
493*0Sstevel@tonic-gate 
494*0Sstevel@tonic-gate static int
ref_walk_init(mdb_walk_state_t * wsp)495*0Sstevel@tonic-gate ref_walk_init(
496*0Sstevel@tonic-gate 	mdb_walk_state_t *wsp)
497*0Sstevel@tonic-gate {
498*0Sstevel@tonic-gate 	if (wsp->walk_addr == NULL)
499*0Sstevel@tonic-gate 		return (WALK_DONE);
500*0Sstevel@tonic-gate 
501*0Sstevel@tonic-gate 	return (WALK_NEXT);
502*0Sstevel@tonic-gate }
503*0Sstevel@tonic-gate 
504*0Sstevel@tonic-gate static int
ref_walk_step(mdb_walk_state_t * wsp)505*0Sstevel@tonic-gate ref_walk_step(
506*0Sstevel@tonic-gate 	mdb_walk_state_t *wsp)
507*0Sstevel@tonic-gate {
508*0Sstevel@tonic-gate 	ipp_ref_t	*rp;
509*0Sstevel@tonic-gate 	int		status;
510*0Sstevel@tonic-gate 
511*0Sstevel@tonic-gate 	if (wsp->walk_addr == NULL)
512*0Sstevel@tonic-gate 		return (WALK_DONE);
513*0Sstevel@tonic-gate 
514*0Sstevel@tonic-gate 	rp = mdb_alloc(sizeof (ipp_ref_t), UM_SLEEP);
515*0Sstevel@tonic-gate 
516*0Sstevel@tonic-gate 	if (mdb_vread(rp, sizeof (ipp_ref_t), wsp->walk_addr) == -1) {
517*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_ref_t at %p", wsp->walk_addr);
518*0Sstevel@tonic-gate 		mdb_free(rp, sizeof (ipp_ref_t));
519*0Sstevel@tonic-gate 		return (WALK_ERR);
520*0Sstevel@tonic-gate 	}
521*0Sstevel@tonic-gate 
522*0Sstevel@tonic-gate 	status = wsp->walk_callback((uintptr_t)rp->ippr_ptr, NULL,
523*0Sstevel@tonic-gate 	    wsp->walk_cbdata);
524*0Sstevel@tonic-gate 
525*0Sstevel@tonic-gate 	wsp->walk_addr = (uintptr_t)(rp->ippr_nextp);
526*0Sstevel@tonic-gate 
527*0Sstevel@tonic-gate 	mdb_free(rp, sizeof (ipp_ref_t));
528*0Sstevel@tonic-gate 	return (status);
529*0Sstevel@tonic-gate }
530*0Sstevel@tonic-gate 
531*0Sstevel@tonic-gate /*ARGSUSED*/
532*0Sstevel@tonic-gate static void
ref_walk_fini(mdb_walk_state_t * wsp)533*0Sstevel@tonic-gate ref_walk_fini(
534*0Sstevel@tonic-gate 	mdb_walk_state_t *wsp)
535*0Sstevel@tonic-gate {
536*0Sstevel@tonic-gate }
537*0Sstevel@tonic-gate 
538*0Sstevel@tonic-gate /*ARGSUSED*/
539*0Sstevel@tonic-gate static int
packet(uintptr_t addr,uint_t flags,int argc,const mdb_arg_t * argv)540*0Sstevel@tonic-gate packet(
541*0Sstevel@tonic-gate 	uintptr_t	addr,
542*0Sstevel@tonic-gate 	uint_t		flags,
543*0Sstevel@tonic-gate 	int		argc,
544*0Sstevel@tonic-gate 	const mdb_arg_t	*argv)
545*0Sstevel@tonic-gate {
546*0Sstevel@tonic-gate 	ipp_packet_t	*pp;
547*0Sstevel@tonic-gate 
548*0Sstevel@tonic-gate 	if ((flags & DCMD_ADDRSPEC) == 0)
549*0Sstevel@tonic-gate 		return (DCMD_ERR);
550*0Sstevel@tonic-gate 
551*0Sstevel@tonic-gate 	pp = mdb_alloc(sizeof (ipp_packet_t), UM_SLEEP);
552*0Sstevel@tonic-gate 	if (mdb_vread(pp, sizeof (ipp_packet_t), addr) == -1) {
553*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_packet_t at %p", addr);
554*0Sstevel@tonic-gate 		mdb_free(pp, sizeof (ipp_packet_t));
555*0Sstevel@tonic-gate 		return (DCMD_ERR);
556*0Sstevel@tonic-gate 	}
557*0Sstevel@tonic-gate 
558*0Sstevel@tonic-gate 	mdb_printf("%?p: %20s = 0x%p\n", addr, "data", pp->ippp_data);
559*0Sstevel@tonic-gate 	mdb_printf("%?s  %20s = 0x%p\n", "", "private", pp->ippp_private);
560*0Sstevel@tonic-gate 	dump_classes((uintptr_t)pp->ippp_class_array, pp->ippp_class_windex);
561*0Sstevel@tonic-gate 	dump_log((uintptr_t)pp->ippp_log, pp->ippp_log_windex);
562*0Sstevel@tonic-gate 
563*0Sstevel@tonic-gate 	mdb_free(pp, sizeof (ipp_packet_t));
564*0Sstevel@tonic-gate 	return (DCMD_OK);
565*0Sstevel@tonic-gate }
566*0Sstevel@tonic-gate 
567*0Sstevel@tonic-gate static void
dump_classes(uintptr_t ptr,uint_t nelt)568*0Sstevel@tonic-gate dump_classes(
569*0Sstevel@tonic-gate 	uintptr_t	ptr,
570*0Sstevel@tonic-gate 	uint_t		nelt)
571*0Sstevel@tonic-gate {
572*0Sstevel@tonic-gate 	ipp_class_t	*array;
573*0Sstevel@tonic-gate 	ipp_class_t	*cp;
574*0Sstevel@tonic-gate 	uint_t		i;
575*0Sstevel@tonic-gate 	boolean_t	first_time = B_TRUE;
576*0Sstevel@tonic-gate 	char		buf[MAXNAMELEN];
577*0Sstevel@tonic-gate 
578*0Sstevel@tonic-gate 	array = mdb_alloc(sizeof (ipp_class_t) * nelt, UM_SLEEP);
579*0Sstevel@tonic-gate 	if (mdb_vread(array, sizeof (ipp_class_t) * nelt, ptr) == -1) {
580*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_class_t array at %p", ptr);
581*0Sstevel@tonic-gate 		return;
582*0Sstevel@tonic-gate 	}
583*0Sstevel@tonic-gate 
584*0Sstevel@tonic-gate 	for (i = 0; i < nelt; i++) {
585*0Sstevel@tonic-gate 		if (first_time) {
586*0Sstevel@tonic-gate 			mdb_printf("%20s  %?s   %<u>%15s %15s%</u>\n", "",
587*0Sstevel@tonic-gate 			    "classes", "NAME", "ACTION");
588*0Sstevel@tonic-gate 			first_time = B_FALSE;
589*0Sstevel@tonic-gate 		}
590*0Sstevel@tonic-gate 
591*0Sstevel@tonic-gate 		cp = &(array[i]);
592*0Sstevel@tonic-gate 		aid2aname(cp->ippc_aid, buf);
593*0Sstevel@tonic-gate 		mdb_printf("%20s  %?p:  %15s %15s%\n", "",
594*0Sstevel@tonic-gate 		    ptr + (i * sizeof (ipp_class_t)), cp->ippc_name, buf);
595*0Sstevel@tonic-gate 	}
596*0Sstevel@tonic-gate 
597*0Sstevel@tonic-gate 	mdb_free(cp, sizeof (ipp_class_t) * nelt);
598*0Sstevel@tonic-gate }
599*0Sstevel@tonic-gate 
600*0Sstevel@tonic-gate static void
dump_log(uintptr_t ptr,uint_t nelt)601*0Sstevel@tonic-gate dump_log(
602*0Sstevel@tonic-gate 	uintptr_t	ptr,
603*0Sstevel@tonic-gate 	uint_t		nelt)
604*0Sstevel@tonic-gate {
605*0Sstevel@tonic-gate 	ipp_log_t	*array;
606*0Sstevel@tonic-gate 	ipp_log_t	*lp;
607*0Sstevel@tonic-gate 	uint_t		i;
608*0Sstevel@tonic-gate 	boolean_t	first_time = B_TRUE;
609*0Sstevel@tonic-gate 	char		buf[MAXNAMELEN];
610*0Sstevel@tonic-gate 
611*0Sstevel@tonic-gate 	array = mdb_alloc(sizeof (ipp_log_t) * nelt, UM_SLEEP);
612*0Sstevel@tonic-gate 	if (mdb_vread(array, sizeof (ipp_log_t) * nelt, ptr) == -1) {
613*0Sstevel@tonic-gate 		mdb_warn("failed to read ipp_log_t array at %p", ptr);
614*0Sstevel@tonic-gate 		return;
615*0Sstevel@tonic-gate 	}
616*0Sstevel@tonic-gate 
617*0Sstevel@tonic-gate 	for (i = 0; i < nelt; i++) {
618*0Sstevel@tonic-gate 		if (first_time) {
619*0Sstevel@tonic-gate 			mdb_printf("%20s  %?s   %<u>%15s %15s%</u>\n", "",
620*0Sstevel@tonic-gate 			    "log", "CLASS NAME", "ACTION");
621*0Sstevel@tonic-gate 			first_time = B_FALSE;
622*0Sstevel@tonic-gate 		}
623*0Sstevel@tonic-gate 
624*0Sstevel@tonic-gate 		lp = &(array[i]);
625*0Sstevel@tonic-gate 		aid2aname(lp->ippl_aid, buf);
626*0Sstevel@tonic-gate 		mdb_printf("%20s  %?p:  %15s %15s\n", "",
627*0Sstevel@tonic-gate 		    ptr + (i * sizeof (ipp_class_t)), lp->ippl_name, buf);
628*0Sstevel@tonic-gate 	}
629*0Sstevel@tonic-gate 
630*0Sstevel@tonic-gate 	mdb_free(lp, sizeof (ipp_log_t) * nelt);
631*0Sstevel@tonic-gate }
632*0Sstevel@tonic-gate 
633*0Sstevel@tonic-gate static void
aid2aname(ipp_action_id_t aid,char * buf)634*0Sstevel@tonic-gate aid2aname(
635*0Sstevel@tonic-gate 	ipp_action_id_t	aid,
636*0Sstevel@tonic-gate 	char		*buf)
637*0Sstevel@tonic-gate {
638*0Sstevel@tonic-gate 	uintptr_t	addr;
639*0Sstevel@tonic-gate 	uintptr_t	ptr;
640*0Sstevel@tonic-gate 	ipp_action_t	*ap;
641*0Sstevel@tonic-gate 
642*0Sstevel@tonic-gate 	switch (aid) {
643*0Sstevel@tonic-gate 	case IPP_ACTION_INVAL:
644*0Sstevel@tonic-gate 		strcpy(buf, "invalid");
645*0Sstevel@tonic-gate 		break;
646*0Sstevel@tonic-gate 	case IPP_ACTION_CONT:
647*0Sstevel@tonic-gate 		strcpy(buf, "continue");
648*0Sstevel@tonic-gate 		break;
649*0Sstevel@tonic-gate 	case IPP_ACTION_DEFER:
650*0Sstevel@tonic-gate 		strcpy(buf, "defer");
651*0Sstevel@tonic-gate 		break;
652*0Sstevel@tonic-gate 	case IPP_ACTION_DROP:
653*0Sstevel@tonic-gate 		strcpy(buf, "drop");
654*0Sstevel@tonic-gate 		break;
655*0Sstevel@tonic-gate 	default:
656*0Sstevel@tonic-gate 		if (mdb_vread(&addr, sizeof (uintptr_t),
657*0Sstevel@tonic-gate 		    ipp_action_byid) == -1) {
658*0Sstevel@tonic-gate 			mdb_warn("failed to read from address %p",
659*0Sstevel@tonic-gate 			    ipp_action_byid);
660*0Sstevel@tonic-gate 			strcpy(buf, "???");
661*0Sstevel@tonic-gate 			break;
662*0Sstevel@tonic-gate 		}
663*0Sstevel@tonic-gate 
664*0Sstevel@tonic-gate 		addr += ((int32_t)aid * sizeof (void *));
665*0Sstevel@tonic-gate 		if (mdb_vread(&ptr, sizeof (uintptr_t), addr) == -1) {
666*0Sstevel@tonic-gate 			mdb_warn("failed to read from address %p", addr);
667*0Sstevel@tonic-gate 			strcpy(buf, "???");
668*0Sstevel@tonic-gate 			break;
669*0Sstevel@tonic-gate 		}
670*0Sstevel@tonic-gate 
671*0Sstevel@tonic-gate 		ap = mdb_alloc(sizeof (ipp_action_t), UM_SLEEP);
672*0Sstevel@tonic-gate 		if (mdb_vread(ap, sizeof (ipp_action_t), ptr) == -1) {
673*0Sstevel@tonic-gate 			mdb_warn("failed to read ipp_action_t at %p", ptr);
674*0Sstevel@tonic-gate 			mdb_free(ap, sizeof (ipp_action_t));
675*0Sstevel@tonic-gate 			strcpy(buf, "???");
676*0Sstevel@tonic-gate 			break;
677*0Sstevel@tonic-gate 		}
678*0Sstevel@tonic-gate 
679*0Sstevel@tonic-gate 		if (ap->ippa_id != aid) {
680*0Sstevel@tonic-gate 			mdb_warn("corrupt action at %p", ptr);
681*0Sstevel@tonic-gate 			mdb_free(ap, sizeof (ipp_action_t));
682*0Sstevel@tonic-gate 			strcpy(buf, "???");
683*0Sstevel@tonic-gate 			break;
684*0Sstevel@tonic-gate 		}
685*0Sstevel@tonic-gate 
686*0Sstevel@tonic-gate 		strcpy(buf, ap->ippa_name);
687*0Sstevel@tonic-gate 	}
688*0Sstevel@tonic-gate }
689*0Sstevel@tonic-gate 
690*0Sstevel@tonic-gate static const mdb_dcmd_t dcmds[] = {
691*0Sstevel@tonic-gate 	{ "ipp_action", "?[-v]",
692*0Sstevel@tonic-gate 	    "display ipp_action structure", action },
693*0Sstevel@tonic-gate 	{ "ipp_mod", "?[-v]",
694*0Sstevel@tonic-gate 	    "display ipp_mod structure", mod },
695*0Sstevel@tonic-gate 	{ "cfglock", ":",
696*0Sstevel@tonic-gate 	    "display cfglock structure", cfglock },
697*0Sstevel@tonic-gate 	{ "ippops", ":",
698*0Sstevel@tonic-gate 	    "display ipp_ops structure", ippops },
699*0Sstevel@tonic-gate 	{ "ipp_packet", ":",
700*0Sstevel@tonic-gate 	    "display ipp_packet structure", packet },
701*0Sstevel@tonic-gate 	{ NULL }
702*0Sstevel@tonic-gate };
703*0Sstevel@tonic-gate 
704*0Sstevel@tonic-gate static const mdb_walker_t walkers[] = {
705*0Sstevel@tonic-gate 	{ "ipp_byid", "walk byid array", byid_walk_init, byid_walk_step,
706*0Sstevel@tonic-gate 	    byid_walk_fini },
707*0Sstevel@tonic-gate 	{ "ipp_ref", "walk reference list", ref_walk_init, ref_walk_step,
708*0Sstevel@tonic-gate 	    ref_walk_fini },
709*0Sstevel@tonic-gate 	{ NULL }
710*0Sstevel@tonic-gate };
711*0Sstevel@tonic-gate 
712*0Sstevel@tonic-gate static const mdb_modinfo_t ipp_modinfo = { MDB_API_VERSION, dcmds, walkers };
713*0Sstevel@tonic-gate 
714*0Sstevel@tonic-gate const mdb_modinfo_t *
_mdb_init(void)715*0Sstevel@tonic-gate _mdb_init(void)
716*0Sstevel@tonic-gate {
717*0Sstevel@tonic-gate 	GElf_Sym sym;
718*0Sstevel@tonic-gate 
719*0Sstevel@tonic-gate 	if (mdb_lookup_by_name("ipp_action_byid", &sym) == -1) {
720*0Sstevel@tonic-gate 		mdb_warn("failed to lookup 'ipp_action_byid'");
721*0Sstevel@tonic-gate 		return (NULL);
722*0Sstevel@tonic-gate 	}
723*0Sstevel@tonic-gate 
724*0Sstevel@tonic-gate 	ipp_action_byid = (uintptr_t)sym.st_value;
725*0Sstevel@tonic-gate 
726*0Sstevel@tonic-gate 	if (mdb_lookup_by_name("ipp_mod_byid", &sym) == -1) {
727*0Sstevel@tonic-gate 		mdb_warn("failed to lookup 'ipp_mod_byid'");
728*0Sstevel@tonic-gate 		return (NULL);
729*0Sstevel@tonic-gate 	}
730*0Sstevel@tonic-gate 
731*0Sstevel@tonic-gate 	ipp_mod_byid = (uintptr_t)sym.st_value;
732*0Sstevel@tonic-gate 
733*0Sstevel@tonic-gate 	return (&ipp_modinfo);
734*0Sstevel@tonic-gate }
735