Sync with NetBSD.
[dragonfly/vkernel-mp.git] / lib / libnetgraph / debug.c
blob374ec9de735d45dc20e1f611800469ea20253fe5
2 /*
3 * debug.c
5 * Copyright (c) 1996-1999 Whistle Communications, Inc.
6 * All rights reserved.
7 *
8 * Subject to the following obligations and disclaimer of warranty, use and
9 * redistribution of this software, in source or object code forms, with or
10 * without modifications are expressly permitted by Whistle Communications;
11 * provided, however, that:
12 * 1. Any and all reproductions of the source or object code must include the
13 * copyright notice above and the following disclaimer of warranties; and
14 * 2. No rights are granted, in any manner or form, to use Whistle
15 * Communications, Inc. trademarks, including the mark "WHISTLE
16 * COMMUNICATIONS" on advertising, endorsements, or otherwise except as
17 * such appears in the above copyright notice or in the software.
19 * THIS SOFTWARE IS BEING PROVIDED BY WHISTLE COMMUNICATIONS "AS IS", AND
20 * TO THE MAXIMUM EXTENT PERMITTED BY LAW, WHISTLE COMMUNICATIONS MAKES NO
21 * REPRESENTATIONS OR WARRANTIES, EXPRESS OR IMPLIED, REGARDING THIS SOFTWARE,
22 * INCLUDING WITHOUT LIMITATION, ANY AND ALL IMPLIED WARRANTIES OF
23 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, OR NON-INFRINGEMENT.
24 * WHISTLE COMMUNICATIONS DOES NOT WARRANT, GUARANTEE, OR MAKE ANY
25 * REPRESENTATIONS REGARDING THE USE OF, OR THE RESULTS OF THE USE OF THIS
26 * SOFTWARE IN TERMS OF ITS CORRECTNESS, ACCURACY, RELIABILITY OR OTHERWISE.
27 * IN NO EVENT SHALL WHISTLE COMMUNICATIONS BE LIABLE FOR ANY DAMAGES
28 * RESULTING FROM OR ARISING OUT OF ANY USE OF THIS SOFTWARE, INCLUDING
29 * WITHOUT LIMITATION, ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
30 * PUNITIVE, OR CONSEQUENTIAL DAMAGES, PROCUREMENT OF SUBSTITUTE GOODS OR
31 * SERVICES, LOSS OF USE, DATA OR PROFITS, HOWEVER CAUSED AND UNDER ANY
32 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
33 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
34 * THIS SOFTWARE, EVEN IF WHISTLE COMMUNICATIONS IS ADVISED OF THE POSSIBILITY
35 * OF SUCH DAMAGE.
37 * Author: Archie Cobbs <archie@whistle.com>
39 * $FreeBSD: src/lib/libnetgraph/debug.c,v 1.5.2.1 2000/05/01 18:09:54 archie Exp $
40 * $DragonFly: src/lib/libnetgraph/debug.c,v 1.3 2003/08/08 06:18:34 dillon Exp $
41 * $Whistle: debug.c,v 1.24 1999/01/24 01:15:33 archie Exp $
44 #include <sys/types.h>
45 #include <sys/time.h>
46 #include <sys/ioctl.h>
48 #include <stdarg.h>
50 #include <netinet/in.h>
51 #include <net/ethernet.h>
52 #include <net/bpf.h>
54 #include <netgraph/ng_message.h>
55 #include <netgraph/socket/ng_socket.h>
57 #include "netgraph.h"
58 #include "internal.h"
60 #include <netgraph/UI/ng_UI.h>
61 #include <netgraph/async/ng_async.h>
62 #include <netgraph/bpf/ng_bpf.h>
63 #include <netgraph/cisco/ng_cisco.h>
64 #include <netgraph/echo/ng_echo.h>
65 #include <netgraph/ether/ng_ether.h>
66 #include <netgraph/frame_relay/ng_frame_relay.h>
67 #include <netgraph/hole/ng_hole.h>
68 #include <netgraph/iface/ng_iface.h>
69 #include <netgraph/ksocket/ng_ksocket.h>
70 #include <netgraph/lmi/ng_lmi.h>
71 #include <netgraph/ppp/ng_ppp.h>
72 #include <netgraph/pppoe/ng_pppoe.h>
73 #include <netgraph/rfc1490/ng_rfc1490.h>
74 #include <netgraph/socket/ng_socket.h>
75 #include <netgraph/tee/ng_tee.h>
76 #include <netgraph/tty/ng_tty.h>
77 #include <netgraph/vjc/ng_vjc.h>
78 #ifdef WHISTLE
79 #include <machine/../isa/df_def.h>
80 #include <machine/../isa/if_wfra.h>
81 #include <machine/../isa/ipac.h>
82 #include <netgraph/ng_df.h>
83 #include <netgraph/ng_ipac.h>
84 #include <netgraph/mppc/ng_mppc.h>
85 #include <netgraph/pptpgre/ng_pptpgre.h>
86 #include <netgraph/ng_tn.h>
87 #endif
89 /* Global debug level */
90 int _gNgDebugLevel = 0;
92 /* Debug printing functions */
93 void (*_NgLog) (const char *fmt,...) = warn;
94 void (*_NgLogx) (const char *fmt,...) = warnx;
96 /* Internal functions */
97 static const char *NgCookie(int cookie);
99 /* Known typecookie list */
100 struct ng_cookie {
101 int cookie;
102 const char *type;
105 #define COOKIE(c) { NGM_ ## c ## _COOKIE, #c }
107 /* List of known cookies */
108 static const struct ng_cookie cookies[] = {
109 COOKIE(UI),
110 COOKIE(ASYNC),
111 COOKIE(BPF),
112 COOKIE(CISCO),
113 COOKIE(ECHO),
114 COOKIE(ETHER),
115 COOKIE(FRAMERELAY),
116 COOKIE(GENERIC),
117 COOKIE(HOLE),
118 COOKIE(IFACE),
119 COOKIE(KSOCKET),
120 COOKIE(LMI),
121 COOKIE(PPP),
122 COOKIE(PPPOE),
123 COOKIE(RFC1490),
124 COOKIE(SOCKET),
125 COOKIE(TEE),
126 COOKIE(TTY),
127 COOKIE(VJC),
128 #ifdef WHISTLE
129 COOKIE(DF),
130 COOKIE(IPAC),
131 COOKIE(MPPC),
132 COOKIE(PPTPGRE),
133 COOKIE(TN),
134 COOKIE(WFRA),
135 #endif
136 { 0, NULL }
140 * Set debug level, ie, verbosity, if "level" is non-negative.
141 * Returns old debug level.
144 NgSetDebug(int level)
146 int old = _gNgDebugLevel;
148 if (level < 0)
149 level = old;
150 _gNgDebugLevel = level;
151 return (old);
155 * Set debug logging functions.
157 void
158 NgSetErrLog(void (*log) (const char *fmt,...),
159 void (*logx) (const char *fmt,...))
161 _NgLog = log;
162 _NgLogx = logx;
166 * Display a netgraph sockaddr
168 void
169 _NgDebugSockaddr(const struct sockaddr_ng *sg)
171 NGLOGX("SOCKADDR: { fam=%d len=%d addr=\"%s\" }",
172 sg->sg_family, sg->sg_len, sg->sg_data);
175 #define ARGS_BUFSIZE 2048
176 #define RECURSIVE_DEBUG_ADJUST 4
179 * Display a negraph message
181 void
182 _NgDebugMsg(const struct ng_mesg *msg, const char *path)
184 u_char buf[2 * sizeof(struct ng_mesg) + ARGS_BUFSIZE];
185 struct ng_mesg *const req = (struct ng_mesg *)buf;
186 struct ng_mesg *const bin = (struct ng_mesg *)req->data;
187 int arglen, csock = -1;
189 /* Display header stuff */
190 NGLOGX("NG_MESG :");
191 NGLOGX(" vers %d", msg->header.version);
192 NGLOGX(" arglen %d", msg->header.arglen);
193 NGLOGX(" flags %ld", msg->header.flags);
194 NGLOGX(" token %lu", (u_long)msg->header.token);
195 NGLOGX(" cookie %s (%d)",
196 NgCookie(msg->header.typecookie), msg->header.typecookie);
198 /* At lower debugging levels, skip ASCII translation */
199 if (_gNgDebugLevel <= 2)
200 goto fail2;
202 /* If path is not absolute, don't bother trying to use relative
203 address on a different socket for the ASCII translation */
204 if (strchr(path, ':') == NULL)
205 goto fail2;
207 /* Get a temporary socket */
208 if (NgMkSockNode(NULL, &csock, NULL) < 0)
209 goto fail;
211 /* Copy binary message into request message payload */
212 arglen = msg->header.arglen;
213 if (arglen > ARGS_BUFSIZE)
214 arglen = ARGS_BUFSIZE;
215 memcpy(bin, msg, sizeof(*msg) + arglen);
216 bin->header.arglen = arglen;
218 /* Lower debugging to avoid infinite recursion */
219 _gNgDebugLevel -= RECURSIVE_DEBUG_ADJUST;
221 /* Ask the node to translate the binary message to ASCII for us */
222 if (NgSendMsg(csock, path, NGM_GENERIC_COOKIE,
223 NGM_BINARY2ASCII, bin, sizeof(*bin) + bin->header.arglen) < 0) {
224 _gNgDebugLevel += RECURSIVE_DEBUG_ADJUST;
225 goto fail;
227 if (NgRecvMsg(csock, req, sizeof(buf), NULL) < 0) {
228 _gNgDebugLevel += RECURSIVE_DEBUG_ADJUST;
229 goto fail;
232 /* Restore debugging level */
233 _gNgDebugLevel += RECURSIVE_DEBUG_ADJUST;
235 /* Display command string and arguments */
236 NGLOGX(" cmd %s (%d)", bin->header.cmdstr, bin->header.cmd);
237 NGLOGX(" args %s", bin->data);
238 goto done;
240 fail:
241 /* Just display binary version */
242 NGLOGX(" [error decoding message: %s]", strerror(errno));
243 fail2:
244 NGLOGX(" cmd %d", msg->header.cmd);
245 NGLOGX(" args (%d bytes)", msg->header.arglen);
246 _NgDebugBytes(msg->data, msg->header.arglen);
248 done:
249 if (csock != -1)
250 (void)close(csock);
254 * Return the name of the node type corresponding to the cookie
256 static const char *
257 NgCookie(int cookie)
259 int k;
261 for (k = 0; cookies[k].cookie != 0; k++) {
262 if (cookies[k].cookie == cookie)
263 return cookies[k].type;
265 return "??";
269 * Dump bytes in hex
271 void
272 _NgDebugBytes(const u_char *ptr, int len)
274 char buf[100];
275 int k, count;
277 #define BYPERLINE 16
279 for (count = 0; count < len; ptr += BYPERLINE, count += BYPERLINE) {
281 /* Do hex */
282 snprintf(buf, sizeof(buf), "%04x: ", count);
283 for (k = 0; k < BYPERLINE; k++, count++)
284 if (count < len)
285 snprintf(buf + strlen(buf),
286 sizeof(buf) - strlen(buf), "%02x ", ptr[k]);
287 else
288 snprintf(buf + strlen(buf),
289 sizeof(buf) - strlen(buf), " ");
290 snprintf(buf + strlen(buf), sizeof(buf) - strlen(buf), " ");
291 count -= BYPERLINE;
293 /* Do ASCII */
294 for (k = 0; k < BYPERLINE; k++, count++)
295 if (count < len)
296 snprintf(buf + strlen(buf),
297 sizeof(buf) - strlen(buf),
298 "%c", isprint(ptr[k]) ? ptr[k] : '.');
299 else
300 snprintf(buf + strlen(buf),
301 sizeof(buf) - strlen(buf), " ");
302 count -= BYPERLINE;
304 /* Print it */
305 NGLOGX("%s", buf);