xref: /freebsd/contrib/tcpdump/print-l2tp.c (revision 70fe064ad7cab6c0444b91622f60ec6a462f308a)
1 /*
2  * Copyright (c) 1991, 1993, 1994, 1995, 1996, 1997
3  *      The Regents of the University of California.  All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that: (1) source code distributions
7  * retain the above copyright notice and this paragraph in its entirety, (2)
8  * distributions including binary code include the above copyright notice and
9  * this paragraph in its entirety in the documentation or other materials
10  * provided with the distribution, and (3) all advertising materials mentioning
11  * features or use of this software display the following acknowledgement:
12  * ``This product includes software developed by the University of California,
13  * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of
14  * the University nor the names of its contributors may be used to endorse
15  * or promote products derived from this software without specific prior
16  * written permission.
17  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
18  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
19  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
20  *
21  * L2TP support contributed by Motonori Shindo (mshindo@mshindo.net)
22  */
23 
24 #ifndef lint
25 static const char rcsid[] =
26     "@(#) $Header: /tcpdump/master/tcpdump/print-l2tp.c,v 1.8 2000/08/18 07:44:46 itojun Exp $";
27 #endif
28 
29 #ifdef HAVE_CONFIG_H
30 #include "config.h"
31 #endif
32 
33 #include <stdio.h>
34 #include <sys/types.h>
35 #include <sys/param.h>
36 #include <netinet/in.h>
37 #include <arpa/inet.h>
38 
39 #include "l2tp.h"
40 #include "interface.h"
41 
42 static char tstr[] = " [|l2tp]";
43 
44 #ifndef TRUE
45 #define TRUE 1
46 #endif
47 
48 #ifndef FALSE
49 #define FALSE 0
50 #endif
51 
52 static char *l2tp_message_type_string[] = {
53 	"RESERVED_0",		/* 0  Reserved */
54 	"SCCRQ",		/* 1  Start-Control-Connection-Request */
55 	"SCCRP",		/* 2  Start-Control-Connection-Reply */
56 	"SCCCN",		/* 3  Start-Control-Connection-Connected */
57 	"StopCCN",		/* 4  Stop-Control-Connection-Notification */
58 	"RESERVED_5",		/* 5  Reserved */
59 	"HELLO",		/* 6  Hello */
60 	"OCRQ",			/* 7  Outgoing-Call-Request */
61 	"OCRP",			/* 8  Outgoing-Call-Reply */
62 	"OCCN",			/* 9  Outgoing-Call-Connected */
63 	"ICRQ",			/* 10 Incoming-Call-Request */
64 	"ICRP",			/* 11 Incoming-Call-Reply */
65 	"ICCN",			/* 12 Incoming-Call-Connected */
66 	"RESERVED_13",		/* 13 Reserved */
67 	"CDN",			/* 14 Call-Disconnect-Notify */
68 	"WEN",			/* 15 WAN-Error-Notify */
69 	"SLI"			/* 16 Set-Link-Info */
70 #define L2TP_MAX_MSGTYPE_INDEX	17
71 };
72 
73 static void l2tp_msgtype_print(const u_char *dat, u_int length);
74 static void l2tp_result_code_print(const u_char *dat, u_int length);
75 static void l2tp_proto_ver_print(const u_char *dat, u_int length);
76 static void l2tp_framing_cap_print(const u_char *dat, u_int length);
77 static void l2tp_bearer_cap_print(const u_char *dat, u_int length);
78 static void l2tp_tie_breaker_print(const u_char *dat, u_int length);
79 static void l2tp_firm_ver_print(const u_char *dat, u_int length);
80 static void l2tp_host_name_print(const u_char *dat, u_int length);
81 static void l2tp_vendor_name_print(const u_char *dat, u_int length);
82 static void l2tp_assnd_tun_id_print(const u_char *dat, u_int length);
83 static void l2tp_recv_win_size_print(const u_char *dat, u_int length);
84 static void l2tp_challenge_print(const u_char *dat, u_int length);
85 static void l2tp_q931_cc_print(const u_char *dat, u_int length);
86 static void l2tp_challenge_resp_print(const u_char *dat, u_int length);
87 static void l2tp_assnd_sess_id_print(const u_char *dat, u_int length);
88 static void l2tp_call_ser_num_print(const u_char *dat, u_int length);
89 static void l2tp_minimum_bps_print(const u_char *dat, u_int length);
90 static void l2tp_maximum_bps_print(const u_char *dat, u_int length);
91 static void l2tp_bearer_type_print(const u_char *dat, u_int length);
92 static void l2tp_framing_type_print(const u_char *dat, u_int length);
93 static void l2tp_packet_proc_delay_print(const u_char *dat, u_int length);
94 static void l2tp_called_number_print(const u_char *dat, u_int length);
95 static void l2tp_calling_number_print(const u_char *dat, u_int length);
96 static void l2tp_sub_address_print(const u_char *dat, u_int length);
97 static void l2tp_tx_conn_speed_print(const u_char *dat, u_int length);
98 static void l2tp_phy_channel_id_print(const u_char *dat, u_int length);
99 static void l2tp_ini_recv_lcp_print(const u_char *dat, u_int length);
100 static void l2tp_last_sent_lcp_print(const u_char *dat, u_int length);
101 static void l2tp_last_recv_lcp_print(const u_char *dat, u_int length);
102 static void l2tp_proxy_auth_type_print(const u_char *dat, u_int length);
103 static void l2tp_proxy_auth_name_print(const u_char *dat, u_int length);
104 static void l2tp_proxy_auth_chal_print(const u_char *dat, u_int length);
105 static void l2tp_proxy_auth_id_print(const u_char *dat, u_int length);
106 static void l2tp_proxy_auth_resp_print(const u_char *dat, u_int length);
107 static void l2tp_call_errors_print(const u_char *dat, u_int length);
108 static void l2tp_accm_print(const u_char *dat, u_int length);
109 static void l2tp_random_vector_print(const u_char *dat, u_int length);
110 static void l2tp_private_grp_id_print(const u_char *dat, u_int length);
111 static void l2tp_rx_conn_speed_print(const u_char *dat, u_int length);
112 static void l2tp_seq_required_print(const u_char *dat, u_int length);
113 static void l2tp_avp_print(const u_char *dat, u_int length);
114 
115 static struct l2tp_avp_vec l2tp_avp[] = {
116   {"MSGTYPE", l2tp_msgtype_print}, 		/* 0  Message Type */
117   {"RESULT_CODE", l2tp_result_code_print},	/* 1  Result Code */
118   {"PROTO_VER", l2tp_proto_ver_print},		/* 2  Protocol Version */
119   {"FRAMING_CAP", l2tp_framing_cap_print},	/* 3  Framing Capabilities */
120   {"BEARER_CAP", l2tp_bearer_cap_print},	/* 4  Bearer Capabilities */
121   {"TIE_BREAKER", l2tp_tie_breaker_print},	/* 5  Tie Breaker */
122   {"FIRM_VER", l2tp_firm_ver_print},		/* 6  Firmware Revision */
123   {"HOST_NAME", l2tp_host_name_print},		/* 7  Host Name */
124   {"VENDOR_NAME", l2tp_vendor_name_print},	/* 8  Vendor Name */
125   {"ASSND_TUN_ID", l2tp_assnd_tun_id_print}, 	/* 9  Assigned Tunnel ID */
126   {"RECV_WIN_SIZE", l2tp_recv_win_size_print},	/* 10 Receive Window Size */
127   {"CHALLENGE", l2tp_challenge_print},		/* 11 Challenge */
128   {"Q931_CC", l2tp_q931_cc_print},		/* 12 Q.931 Cause Code */
129   {"CHALLENGE_RESP", l2tp_challenge_resp_print},/* 13 Challenge Response */
130   {"ASSND_SESS_ID", l2tp_assnd_sess_id_print},  /* 14 Assigned Session ID */
131   {"CALL_SER_NUM", l2tp_call_ser_num_print}, 	/* 15 Call Serial Number */
132   {"MINIMUM_BPS",	l2tp_minimum_bps_print},/* 16 Minimum BPS */
133   {"MAXIMUM_BPS", l2tp_maximum_bps_print},	/* 17 Maximum BPS */
134   {"BEARER_TYPE",	l2tp_bearer_type_print},/* 18 Bearer Type */
135   {"FRAMING_TYPE", l2tp_framing_type_print}, 	/* 19 Framing Type */
136   {"PACKET_PROC_DELAY", l2tp_packet_proc_delay_print}, /* 20 Packet Processing Delay (OBSOLETE) */
137   {"CALLED_NUMBER", l2tp_called_number_print},	/* 21 Called Number */
138   {"CALLING_NUMBER", l2tp_calling_number_print},/* 22 Calling Number */
139   {"SUB_ADDRESS",	l2tp_sub_address_print},/* 23 Sub-Address */
140   {"TX_CONN_SPEED", l2tp_tx_conn_speed_print},	/* 24 (Tx) Connect Speed */
141   {"PHY_CHANNEL_ID", l2tp_phy_channel_id_print},/* 25 Physical Channel ID */
142   {"INI_RECV_LCP", l2tp_ini_recv_lcp_print}, 	/* 26 Initial Received LCP CONFREQ */
143   {"LAST_SENT_LCP", l2tp_last_sent_lcp_print},	/* 27 Last Sent LCP CONFREQ */
144   {"LAST_RECV_LCP", l2tp_last_recv_lcp_print},	/* 28 Last Received LCP CONFREQ */
145   {"PROXY_AUTH_TYPE", l2tp_proxy_auth_type_print},/* 29 Proxy Authen Type */
146   {"PROXY_AUTH_NAME", l2tp_proxy_auth_name_print},/* 30 Proxy Authen Name */
147   {"PROXY_AUTH_CHAL", l2tp_proxy_auth_chal_print},/* 31 Proxy Authen Challenge */
148   {"PROXY_AUTH_ID", l2tp_proxy_auth_id_print},	/* 32 Proxy Authen ID */
149   {"PROXY_AUTH_RESP", l2tp_proxy_auth_resp_print},/* 33 Proxy Authen Response */
150   {"CALL_ERRORS", l2tp_call_errors_print},	/* 34 Call Errors */
151   {"ACCM", l2tp_accm_print},			/* 35 ACCM */
152   {"RANDOM_VECTOR", l2tp_random_vector_print},	/* 36 Random Vector */
153   {"PRIVATE_GRP_ID", l2tp_private_grp_id_print},/* 37 Private Group ID */
154   {"RX_CONN_SPEED", l2tp_rx_conn_speed_print},	/* 38 (Rx) Connect Speed */
155   {"SEQ_REQUIRED", l2tp_seq_required_print}, 	/* 39 Sequencing Required */
156 #define L2TP_MAX_AVP_INDEX	40
157 };
158 
159 #if 0
160 static char *l2tp_result_code_StopCCN[] = {
161          "Reserved",
162          "General request to clear control connection",
163          "General error--Error Code indicates the problem",
164          "Control channel already exists",
165          "Requester is not authorized to establish a control channel",
166          "The protocol version of the requester is not supported",
167          "Requester is being shut down",
168          "Finite State Machine error"
169 #define L2TP_MAX_RESULT_CODE_STOPCC_INDEX	8
170 };
171 #endif
172 
173 #if 0
174 static char *l2tp_result_code_CDN[] = {
175 	"Reserved",
176 	"Call disconnected due to loss of carrier",
177 	"Call disconnected for the reason indicated in error code",
178 	"Call disconnected for administrative reasons",
179 	"Call failed due to lack of appropriate facilities being " \
180 	"available (temporary condition)",
181 	"Call failed due to lack of appropriate facilities being " \
182 	"available (permanent condition)",
183 	"Invalid destination",
184 	"Call failed due to no carrier detected",
185 	"Call failed due to detection of a busy signal",
186 	"Call failed due to lack of a dial tone",
187 	"Call was not established within time allotted by LAC",
188 	"Call was connected but no appropriate framing was detected"
189 #define L2TP_MAX_RESULT_CODE_CDN_INDEX	12
190 };
191 #endif
192 
193 #if 0
194 static char *l2tp_error_code_general[] = {
195 	"No general error",
196 	"No control connection exists yet for this LAC-LNS pair",
197 	"Length is wrong",
198 	"One of the field values was out of range or " \
199 	"reserved field was non-zero"
200 	"Insufficient resources to handle this operation now",
201 	"The Session ID is invalid in this context",
202 	"A generic vendor-specific error occurred in the LAC",
203 	"Try another"
204 #define L2TP_MAX_ERROR_CODE_GENERAL_INDEX	8
205 };
206 #endif
207 
208 /******************************/
209 /* generic print out routines */
210 /******************************/
211 static void
212 print_string(const u_char *dat, u_int length)
213 {
214 	int i;
215 	for (i=0; i<length; i++) {
216 		printf("%c", *dat++);
217 	}
218 }
219 
220 static void
221 print_octets(const u_char *dat, u_int length)
222 {
223 	int i;
224 	for (i=0; i<length; i++) {
225 		printf("%02x", *dat++);
226 	}
227 }
228 
229 static void
230 print_short(const u_short *dat)
231 {
232 	printf("%u", ntohs(*dat));
233 }
234 
235 static void
236 print_int(const u_int *dat)
237 {
238 	printf("%lu", (u_long)ntohl(*dat));
239 }
240 
241 /**********************************/
242 /* AVP-specific print out routines*/
243 /**********************************/
244 static void
245 l2tp_msgtype_print(const u_char *dat, u_int length)
246 {
247 	u_short *ptr = (u_short *)dat;
248 
249 	if (ntohs(*ptr) < L2TP_MAX_MSGTYPE_INDEX) {
250 		printf("%s", l2tp_message_type_string[ntohs(*ptr)]);
251 	}
252 }
253 
254 static void
255 l2tp_result_code_print(const u_char *dat, u_int length)
256 {
257 	/* we just print out the result and error code number */
258 	u_short *ptr = (u_short *)dat;
259 
260 	if (length == 2) {		/* result code */
261 		printf("%u", ntohs(*ptr));
262 	} else if (length == 4) { 	/* result & error code */
263 		printf("%u/%u", ntohs(*ptr), ntohs(*(ptr+1)));
264 	} else if (length > 4) {	/* result & error code & msg */
265 		printf("%u/%u ", ntohs(*ptr), ntohs(*(ptr+1)));
266 		print_string((u_char *)(ptr+2), length - 4);
267 	}
268 }
269 
270 static void
271 l2tp_proto_ver_print(const u_char *dat, u_int length)
272 {
273 	printf("%d.%d", *dat, *(dat+1));
274 }
275 
276 
277 static void
278 l2tp_framing_cap_print(const u_char *dat, u_int length)
279 {
280 	u_int *ptr = (u_int *)dat;
281 
282 	if (ntohl(*ptr) &  L2TP_FRAMING_CAP_ASYNC_MASK) {
283 		printf("A");
284 	}
285 	if (ntohl(*ptr) &  L2TP_FRAMING_CAP_SYNC_MASK) {
286 		printf("S");
287 	}
288 }
289 
290 static void
291 l2tp_bearer_cap_print(const u_char *dat, u_int length)
292 {
293 	u_int *ptr = (u_int *)dat;
294 
295 	if (ntohl(*ptr) &  L2TP_BEARER_CAP_ANALOG_MASK) {
296 		printf("A");
297 	}
298 	if (ntohl(*ptr) &  L2TP_BEARER_CAP_DIGITAL_MASK) {
299 		printf("D");
300 	}
301 }
302 
303 static void
304 l2tp_tie_breaker_print(const u_char *dat, u_int length)
305 {
306 	print_octets(dat, 8);	/* Tie Break Value is 64bits long */
307 }
308 
309 static void
310 l2tp_firm_ver_print(const u_char *dat, u_int length)
311 {
312 	print_short((u_short *)dat);
313 }
314 
315 static void
316 l2tp_host_name_print(const u_char *dat, u_int length)
317 {
318 	print_string(dat, length);
319 }
320 
321 static void
322 l2tp_vendor_name_print(const u_char *dat, u_int length)
323 {
324 	print_string(dat, length);
325 }
326 
327 static void
328 l2tp_assnd_tun_id_print(const u_char *dat, u_int length)
329 {
330 	print_short((u_short *)dat);
331 }
332 
333 static void
334 l2tp_recv_win_size_print(const u_char *dat, u_int length)
335 {
336 	print_short((u_short *)dat);
337 }
338 
339 static void
340 l2tp_challenge_print(const u_char *dat, u_int length)
341 {
342 	print_octets(dat, length);
343 }
344 
345 static void
346 l2tp_q931_cc_print(const u_char *dat, u_int length)
347 {
348 	print_short((u_short *)dat);
349 	printf(", %02x", dat[2]);
350 	if (length > 3) {
351 		printf(" ");
352 		print_string(dat+3, length-3);
353 	}
354 }
355 
356 static void
357 l2tp_challenge_resp_print(const u_char *dat, u_int length)
358 {
359 	print_octets(dat, 16);		/* XXX length should be 16? */
360 }
361 
362 static void
363 l2tp_assnd_sess_id_print(const u_char *dat, u_int length)
364 {
365 	print_short((u_short *)dat);
366 }
367 
368 static void
369 l2tp_call_ser_num_print(const u_char *dat, u_int length)
370 {
371 	print_int((u_int *)dat);
372 }
373 
374 static void
375 l2tp_minimum_bps_print(const u_char *dat, u_int length)
376 {
377 	print_int((u_int *)dat);
378 }
379 
380 static void
381 l2tp_maximum_bps_print(const u_char *dat, u_int length)
382 {
383 	print_int((u_int *)dat);
384 }
385 
386 static void
387 l2tp_bearer_type_print(const u_char *dat, u_int length)
388 {
389 	u_int *ptr = (u_int *)dat;
390 
391 	if (ntohl(*ptr) &  L2TP_BEARER_TYPE_ANALOG_MASK) {
392 		printf("A");
393 	}
394 	if (ntohl(*ptr) &  L2TP_BEARER_TYPE_DIGITAL_MASK) {
395 		printf("D");
396 	}
397 }
398 
399 static void
400 l2tp_framing_type_print(const u_char *dat, u_int length)
401 {
402 	u_int *ptr = (u_int *)dat;
403 
404 	if (ntohl(*ptr) &  L2TP_FRAMING_TYPE_ASYNC_MASK) {
405 		printf("A");
406 	}
407 	if (ntohl(*ptr) &  L2TP_FRAMING_TYPE_SYNC_MASK) {
408 		printf("S");
409 	}
410 }
411 
412 static void
413 l2tp_packet_proc_delay_print(const u_char *dat, u_int length)
414 {
415 	printf("obsolete");
416 }
417 
418 static void
419 l2tp_called_number_print(const u_char *dat, u_int length)
420 {
421 	print_string(dat, length);
422 }
423 
424 static void
425 l2tp_calling_number_print(const u_char *dat, u_int length)
426 {
427 	print_string(dat, length);
428 }
429 
430 static void
431 l2tp_sub_address_print(const u_char *dat, u_int length)
432 {
433 	print_string(dat, length);
434 }
435 
436 static void
437 l2tp_tx_conn_speed_print(const u_char *dat, u_int length)
438 {
439 	print_int((u_int *)dat);
440 }
441 
442 static void
443 l2tp_phy_channel_id_print(const u_char *dat, u_int length)
444 {
445 	print_int((u_int *)dat);
446 }
447 
448 static void
449 l2tp_ini_recv_lcp_print(const u_char *dat, u_int length)
450 {
451 	print_octets(dat, length);
452 }
453 
454 static void
455 l2tp_last_sent_lcp_print(const u_char *dat, u_int length)
456 {
457 	print_octets(dat, length);
458 }
459 
460 static void
461 l2tp_last_recv_lcp_print(const u_char *dat, u_int length)
462 {
463 	print_octets(dat, length);
464 }
465 
466 static void
467 l2tp_proxy_auth_type_print(const u_char *dat, u_int length)
468 {
469 	u_short *ptr = (u_short *)dat;
470 
471 	switch (ntohs(*ptr)) {
472 	case L2TP_AUTHEN_TYPE_RESERVED:
473 		printf("Reserved");
474 		break;
475 	case L2TP_AUTHEN_TYPE_TEXTUAL:
476 		printf("Textual");
477 		break;
478 	case L2TP_AUTHEN_TYPE_CHAP:
479 		printf("CHAP");
480 		break;
481 	case L2TP_AUTHEN_TYPE_PAP:
482 		printf("PAP");
483 		break;
484 	case L2TP_AUTHEN_TYPE_NO_AUTH:
485 		printf("No Auth");
486 		break;
487 	case L2TP_AUTHEN_TYPE_MSCHAP:
488 		printf("MS-CHAP");
489 		break;
490 	default:
491 		printf("unknown");
492 	}
493 }
494 
495 static void
496 l2tp_proxy_auth_name_print(const u_char *dat, u_int length)
497 {
498 	print_octets(dat, length);
499 }
500 
501 static void
502 l2tp_proxy_auth_chal_print(const u_char *dat, u_int length)
503 {
504 	print_octets(dat, length);
505 }
506 
507 static void
508 l2tp_proxy_auth_id_print(const u_char *dat, u_int length)
509 {
510 	u_short *ptr = (u_short *)dat;
511 
512 	printf("%u", ntohs(*ptr) & L2TP_PROXY_AUTH_ID_MASK);
513 }
514 
515 static void
516 l2tp_proxy_auth_resp_print(const u_char *dat, u_int length)
517 {
518 	print_octets(dat, length);
519 }
520 
521 static void
522 l2tp_call_errors_print(const u_char *dat, u_int length)
523 {
524 	struct l2tp_call_errors *ptr = (struct l2tp_call_errors *)dat;
525 
526 	printf("CRCErr=%d FrameErr=%d HardOver=%d BufOver=%d ",
527 	       ptr->crc_errs,
528 	       ptr->framing_errs,
529 	       ptr->hardware_overruns,
530 	       ptr->buffer_overruns);
531 	printf("Timeout=%d AlingErr=%d",
532 	       ptr->timeout_errs,
533 	       ptr->alignment_errs);
534 }
535 
536 static void
537 l2tp_accm_print(const u_char *dat, u_int length)
538 {
539 	struct l2tp_accm *ptr = (struct l2tp_accm *)dat;
540 
541 	printf("send=%x recv=%x", ptr->send_accm, ptr->recv_accm);
542 }
543 
544 static void
545 l2tp_random_vector_print(const u_char *dat, u_int length)
546 {
547 	print_octets(dat, length);
548 }
549 
550 static void
551 l2tp_private_grp_id_print(const u_char *dat, u_int length)
552 {
553 	print_string(dat, length);
554 	/* XXX print_octets is more appropriate?? */
555 }
556 
557 static void
558 l2tp_rx_conn_speed_print(const u_char *dat, u_int length)
559 {
560 	print_int((u_int *)dat);
561 }
562 
563 static void
564 l2tp_seq_required_print(const u_char *dat, u_int length)
565 {
566 	return;
567 }
568 
569 static void
570 l2tp_avp_print(const u_char *dat, u_int length)
571 {
572 	u_int len;
573 	const u_short *ptr = (u_short *)dat;
574 	int hidden = FALSE;
575 
576 	printf(" ");
577 	if (length > 0 && (snapend - dat) >= 2) {
578 		/* there must be at least two octets for the length
579 		   to be decoded */
580 		if ((len = (ntohs(*ptr) & L2TP_AVP_HDR_LEN_MASK)) <=
581 		    (snapend - dat)) {
582 			if (ntohs(*ptr) & L2TP_AVP_HDR_FLAG_MANDATORY) {
583 				printf("*");
584 			}
585 			if (ntohs(*ptr) & L2TP_AVP_HDR_FLAG_HIDDEN) {
586 				hidden = TRUE;
587 				printf("?");
588 			}
589 		} else {
590 			printf("|...");
591 			return;
592 		}
593 		ptr++;
594 
595 		if (ntohs(*ptr)) {
596 			/* Vendor Specific Attribute */
597 			printf("VENDOR%04x:", ntohs(*ptr));
598 			ptr++;
599 			printf("ATTR%04x", ntohs(*ptr));
600 			printf("(");
601 			print_octets((u_char *)ptr+2, len-6);
602 			printf(")");
603 		} else {
604 			/* IETF-defined Attribute */
605 			ptr++;
606 			if (ntohs(*ptr) < L2TP_MAX_AVP_INDEX) {
607 				printf("%s", l2tp_avp[ntohs(*ptr)].name);
608 				printf("(");
609 				if (!hidden) {
610 					(l2tp_avp[ntohs(*ptr)].print)
611 						((u_char *)ptr+2, len-6);
612 				} else {
613 					printf("???");
614 				}
615 				printf(")");
616 			} else {
617 				printf(" invalid AVP %u", ntohs(*ptr));
618 			}
619 		}
620 
621 		l2tp_avp_print(dat + len, length - len);
622 	} else if (length == 0) {
623 		return;
624 	} else {
625 		printf("|...");
626 	}
627 }
628 
629 
630 void
631 l2tp_print(const u_char *dat, u_int length)
632 {
633 	const u_short *ptr = (u_short *)dat;
634 	u_int cnt = 0;			/* total octets consumed */
635 	u_short pad;
636 	int flag_t, flag_l, flag_s, flag_o, flag_p;
637 	u_short l2tp_len;
638 
639 	flag_t = flag_l = flag_s = flag_o = flag_p = FALSE;
640 
641 	if (min(length, snapend - dat) - 6 < 0) {
642 		/* flag/ver, tunnel_id, session_id must be present for
643 		   this packet to be properly decoded */
644 		printf("%s", tstr);
645 		return;
646 	}
647 
648 	if ((ntohs(*ptr) & L2TP_VERSION_MASK) == L2TP_VERSION_L2TP) {
649 		printf(" l2tp:");
650 	} else if ((ntohs(*ptr) & L2TP_VERSION_MASK) == L2TP_VERSION_L2F) {
651 		printf(" l2f:");
652 		return;		/* nothing to do */
653 	} else {
654 		printf(" Unknown Version, neither L2F(1) nor L2TP(2)");
655 		return;		/* nothing we can do */
656 	}
657 
658 	printf("[");
659 	if (ntohs(*ptr) & L2TP_FLAG_TYPE) {
660 		flag_t = TRUE;
661 		printf("T");
662 	}
663 	if (ntohs(*ptr) & L2TP_FLAG_LENGTH) {
664 		flag_l = TRUE;
665 		printf("L");
666 	}
667 	if (ntohs(*ptr) & L2TP_FLAG_SEQUENCE) {
668 		flag_s = TRUE;
669 		printf("S");
670 	}
671 	if (ntohs(*ptr) & L2TP_FLAG_OFFSET) {
672 		flag_o = TRUE;
673 		printf("O");
674 	}
675 	if (ntohs(*ptr) & L2TP_FLAG_PRIORITY) {
676 		flag_p = TRUE;
677 		printf("P");
678 	}
679 	printf("]");
680 
681 	ptr++;
682 	cnt += 2;
683 
684 	if (flag_l) {
685 		l2tp_len = ntohs(*ptr++);	/* XXX need to consider
686 						   truncation ?? */
687 		cnt += 2;
688 	} else {
689 		l2tp_len = 0;
690 	}
691 
692 	printf("(%u/", ntohs(*ptr++));		/* Tunnel ID */
693 	printf("%u)",  ntohs(*ptr++));		/* Session ID */
694 	cnt += 4;
695 
696 	if (flag_s) {
697 		printf("Ns=%u,", ntohs(*ptr++));
698 		printf("Nr=%u",  ntohs(*ptr++));
699 		cnt += 4;
700 	}
701 
702 	if (flag_o) {
703 		pad =  ntohs(*ptr++);
704 		ptr += pad / sizeof(*ptr);
705 		cnt += (2 + pad);
706 	}
707 
708 	if (flag_t) {
709 		if (length - cnt == 0) {
710 			printf(" ZLB");
711 		} else {
712 			l2tp_avp_print((u_char *)ptr, length - cnt);
713 		}
714 	} else {
715 		printf(" {");
716 		ppp_print((u_char *)ptr, length - cnt);
717 		printf("}");
718 	}
719 }
720