2 * Copyright (c) 1992, 1993, 1994, 1995, 1996
3 * The Regents of the University of California. All rights reserved.
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
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.
21 * Original code by Matt Thomas, Digital Equipment Corporation
23 * Extensively modified by Hannes Gredler (hannes@juniper.net) for more
24 * complete IS-IS support.
28 static const char rcsid
[] =
29 "@(#) $Header: /tcpdump/master/tcpdump/print-isoclns.c,v 1.44 2002-04-12 07:56:49 guy Exp $ (LBL)";
36 #include <sys/types.h>
38 #include <sys/socket.h>
40 #include <netinet/in.h>
45 #include "interface.h"
46 #include "addrtoname.h"
47 #include "ethertype.h"
51 #define NLPID_CLNS 129 /* 0x81 */
52 #define NLPID_ESIS 130 /* 0x82 */
53 #define NLPID_ISIS 131 /* 0x83 */
54 #define NLPID_IP6 0x8e
56 #define NLPID_NULLNS 0
59 * IS-IS is defined in ISO 10589. Look there for protocol definitions.
62 #define SYSTEM_ID_LEN ETHER_ADDR_LEN
63 #define ISIS_VERSION 1
64 #define PDU_TYPE_MASK 0x1F
65 #define PRIORITY_MASK 0x7F
77 static struct tok isis_pdu_values
[] = {
78 { L1_LAN_IIH
, "L1 Lan IIH"},
79 { L2_LAN_IIH
, "L2 Lan IIH"},
80 { PTP_IIH
, "p2p IIH"},
83 { L1_CSNP
, "L1 CSNP"},
84 { L2_CSNP
, "L2 CSNP"},
85 { L1_PSNP
, "L1 PSNP"},
86 { L2_PSNP
, "L2 PSNP"},
91 * A TLV is a tuple of a type, length and a value and is normally used for
92 * encoding information in all sorts of places. This is an enumeration of
93 * the well known types.
95 * list taken from draft-ietf-isis-wg-tlv-codepoints-01.txt
98 #define TLV_AREA_ADDR 1
99 #define TLV_IS_REACH 2
100 #define TLV_ESNEIGH 3
101 #define TLV_PART_DIS 4
102 #define TLV_SUMMARY 5
103 #define TLV_ISNEIGH 6
104 #define TLV_PADDING 8
107 #define TLV_CHECKSUM 12
108 #define TLV_LSP_BUFFERSIZE 14
109 #define TLV_EXT_IS_REACH 22
110 #define TLV_IS_ALIAS_ID 24
111 #define TLV_DECNET_PHASE4 42
112 #define TLV_LUCENT_PRIVATE 66
113 #define TLV_IP_REACH 128
114 #define TLV_PROTOCOLS 129
115 #define TLV_IP_REACH_EXT 130
116 #define TLV_IDRP_INFO 131
117 #define TLV_IPADDR 132
118 #define TLV_IPAUTH 133
119 #define TLV_TE_ROUTER_ID 134
120 #define TLV_EXT_IP_REACH 135
121 #define TLV_HOSTNAME 137
122 #define TLV_SHARED_RISK_GROUP 138
123 #define TLV_NORTEL_PRIVATE1 176
124 #define TLV_NORTEL_PRIVATE2 177
125 #define TLV_RESTART_SIGNALING 211
126 #define TLV_MT_IS_REACH 222
127 #define TLV_MT_SUPPORTED 229
128 #define TLV_IP6ADDR 232
129 #define TLV_MT_IP_REACH 235
130 #define TLV_IP6_REACH 236
131 #define TLV_MT_IP6_REACH 237
132 #define TLV_PTP_ADJ 240
134 static struct tok isis_tlv_values
[] = {
135 { TLV_AREA_ADDR
, "Area address(es)"},
136 { TLV_IS_REACH
, "IS Reachability"},
137 { TLV_ESNEIGH
, "IS Neighbor(s)"},
138 { TLV_PART_DIS
, "Partition DIS"},
139 { TLV_SUMMARY
, "Prefix Neighbors"},
140 { TLV_ISNEIGH
, "IS Neighbor(s)"},
141 { TLV_PADDING
, "Padding"},
142 { TLV_LSP
, "LSP entries"},
143 { TLV_AUTH
, "Authentication"},
144 { TLV_CHECKSUM
, "Checksum"},
145 { TLV_LSP_BUFFERSIZE
, "LSP Buffersize"},
146 { TLV_EXT_IS_REACH
, "Extended IS Reachability"},
147 { TLV_IS_ALIAS_ID
, "IS Alias ID"},
148 { TLV_DECNET_PHASE4
, "DECnet Phase IV"},
149 { TLV_LUCENT_PRIVATE
, "Lucent Proprietary"},
150 { TLV_IP_REACH
, "IP Internal reachability"},
151 { TLV_PROTOCOLS
, "Protocols supported"},
152 { TLV_IP_REACH_EXT
, "IP External reachability"},
153 { TLV_IDRP_INFO
, "Inter-Domain Information Type"},
154 { TLV_IPADDR
, "IP Interface address(es)"},
155 { TLV_IPAUTH
, "IP authentication (depreciated)"},
156 { TLV_TE_ROUTER_ID
, "Traffic Engineering Router ID"},
157 { TLV_EXT_IP_REACH
, "Extended IP reachability"},
158 { TLV_HOSTNAME
, "Hostname"},
159 { TLV_SHARED_RISK_GROUP
, "Shared Risk Link Group"},
160 { TLV_NORTEL_PRIVATE1
, "Nortel Proprietary"},
161 { TLV_NORTEL_PRIVATE2
, "Nortel Proprietary"},
162 { TLV_RESTART_SIGNALING
, "Restart Signaling"},
163 { TLV_MT_IS_REACH
, "Multi Topology IS Reachability"},
164 { TLV_MT_SUPPORTED
, "Multi Topology"},
165 { TLV_IP6ADDR
, "IP6 Interface address(es)"},
166 { TLV_MT_IP_REACH
, "Multi-Topology IP reachability"},
167 { TLV_IP6_REACH
, "IP6 reachability"},
168 { TLV_MT_IP6_REACH
, "Multi-Topology IP6 reachability"},
169 { TLV_PTP_ADJ
, "Point-to-point Adjacency State"},
173 #define SUBTLV_EXT_IS_REACH_ADMIN_GROUP 3
174 #define SUBTLV_EXT_IS_REACH_LINK_LOCAL_ID 4
175 #define SUBTLV_EXT_IS_REACH_LINK_REMOTE_ID 5
176 #define SUBTLV_EXT_IS_REACH_IPV4_INTF_ADDR 6
177 #define SUBTLV_EXT_IS_REACH_IPV4_NEIGHBOR_ADDR 8
178 #define SUBTLV_EXT_IS_REACH_MAX_LINK_BW 9
179 #define SUBTLV_EXT_IS_REACH_RESERVABLE_BW 10
180 #define SUBTLV_EXT_IS_REACH_UNRESERVED_BW 11
181 #define SUBTLV_EXT_IS_REACH_TE_METRIC 18
182 #define SUBTLV_EXT_IS_REACH_LINK_PROTECTION_TYPE 20
183 #define SUBTLV_EXT_IS_REACH_INTF_SW_CAP_DESCR 21
185 #define SUBTLV_EXT_IP_REACH_ADMIN_TAG 1
187 #define SUBTLV_AUTH_SIMPLE 1
188 #define SUBTLV_AUTH_MD5 54
189 #define SUBTLV_AUTH_MD5_LEN 16
190 #define SUBTLV_AUTH_PRIVATE 255
192 static struct tok isis_subtlv_auth_values
[] = {
193 { SUBTLV_AUTH_SIMPLE
, "simple text password"},
194 { SUBTLV_AUTH_MD5
, "HMAC-MD5 password"},
195 { SUBTLV_AUTH_PRIVATE
, "Routing Domain private password"},
200 #define ISIS_8BIT_MASK(x) ((x)&0xff)
202 #define ISIS_MASK_LSP_OL_BIT(x) ((x)&0x4)
203 #define ISIS_MASK_LSP_ISTYPE_BITS(x) ((x)&0x3)
204 #define ISIS_MASK_LSP_PARTITION_BIT(x) ((x)&0x80)
205 #define ISIS_MASK_LSP_ATT_BITS(x) ((x)&0x78)
206 #define ISIS_MASK_LSP_ATT_ERROR_BIT(x) ((x)&0x40)
207 #define ISIS_MASK_LSP_ATT_EXPENSE_BIT(x) ((x)&0x20)
208 #define ISIS_MASK_LSP_ATT_DELAY_BIT(x) ((x)&0x10)
209 #define ISIS_MASK_LSP_ATT_DEFAULT_BIT(x) ((x)&0x8)
211 #define ISIS_MASK_MTID(x) ((x)&0xfff)
212 #define ISIS_MASK_MTSUB(x) ((x)&0x8000)
213 #define ISIS_MASK_MTATT(x) ((x)&0x4000)
215 #define ISIS_MASK_TLV_EXT_IP_UPDOWN(x) ((x)&0x80)
216 #define ISIS_MASK_TLV_EXT_IP_SUBTLV(x) ((x)&0x40)
218 #define ISIS_MASK_TLV_IP6_UPDOWN(x) ((x)&0x80)
219 #define ISIS_MASK_TLV_IP6_IE(x) ((x)&0x40)
220 #define ISIS_MASK_TLV_IP6_SUBTLV(x) ((x)&0x20)
222 #define ISIS_MASK_TLV_RESTART_RR(x) ((x)&0x1)
223 #define ISIS_MASK_TLV_RESTART_RA(x) ((x)&0x2)
225 #define ISIS_LSP_TLV_METRIC_SUPPORTED(x) ((x)&0x80)
226 #define ISIS_LSP_TLV_METRIC_IE(x) ((x)&0x40)
227 #define ISIS_LSP_TLV_METRIC_UPDOWN(x) ((x)&0x80)
228 #define ISIS_LSP_TLV_METRIC_VALUE(x) ((x)&0x3f)
230 #define ISIS_MASK_TLV_SHARED_RISK_GROUP(x) ((x)&0x1)
232 static const char *isis_gmpls_link_prot_values
[] = {
243 static struct tok isis_gmpls_sw_cap_values
[] = {
244 { 1, "Packet-Switch Capable-1"},
245 { 2, "Packet-Switch Capable-2"},
246 { 3, "Packet-Switch Capable-3"},
247 { 4, "Packet-Switch Capable-4"},
248 { 51, "Layer-2 Switch Capable"},
249 { 100, "Time-Division-Multiplex"},
250 { 150, "Lambda-Switch Capable"},
251 { 200, "Fiber-Switch Capable"},
255 static struct tok isis_gmpls_lsp_enc_values
[] = {
257 { 2, "Ethernet V2/DIX"},
260 { 5, "SDH ITU-T G.707"},
261 { 6, "SONET ANSI T1.105"},
262 { 7, "Digital Wrapper"},
263 { 8, "Lambda (photonic)"},
265 { 10, "Ethernet 802.3"},
266 { 11, "FiberChannel"},
270 static struct tok isis_mt_values
[] = {
271 { 0, "IPv4 unicast"},
272 { 1, "In-Band Management"},
273 { 2, "IPv6 unicast"},
275 { 4095, "Development, Experimental or Proprietary"},
279 static struct tok isis_iih_circuit_type_values
[] = {
280 { 1, "Level 1 only"},
281 { 2, "Level 2 only"},
282 { 3, "Level 1, Level 2"},
286 #define ISIS_LSP_TYPE_UNUSED0 0
287 #define ISIS_LSP_TYPE_LEVEL_1 1
288 #define ISIS_LSP_TYPE_UNUSED2 2
289 #define ISIS_LSP_TYPE_LEVEL_2 3
291 static struct tok isis_lsp_istype_values
[] = {
292 { ISIS_LSP_TYPE_UNUSED0
, "Unused 0x0 (invalid)"},
293 { ISIS_LSP_TYPE_LEVEL_1
, "L1 IS"},
294 { ISIS_LSP_TYPE_UNUSED2
, "Unused 0x2 (invalid)"},
295 { ISIS_LSP_TYPE_LEVEL_2
, "L1L2 IS"},
299 static struct tok isis_nlpid_values
[] = {
300 { NLPID_CLNS
, "CLNS"},
302 { NLPID_IP6
, "IPv6"},
307 * Katz's point to point adjacency TLV uses codes to tell us the state of
308 * the remote adjacency. Enumerate them.
311 #define ISIS_PTP_ADJ_UP 0
312 #define ISIS_PTP_ADJ_INIT 1
313 #define ISIS_PTP_ADJ_DOWN 2
316 static struct tok isis_ptp_adjancey_values
[] = {
317 { ISIS_PTP_ADJ_UP
, "Up" },
318 { ISIS_PTP_ADJ_INIT
, "Initializing" },
319 { ISIS_PTP_ADJ_DOWN
, "Down" },
323 struct isis_tlv_ptp_adj
{
324 u_char adjacency_state
;
325 u_char ext_local_circuit_id
[4];
326 u_char neighbor_sysid
[SYSTEM_ID_LEN
];
327 u_char neighbor_ext_local_circuit_id
[4];
330 static int osi_cksum(const u_char
*, u_int
);
331 static void esis_print(const u_char
*, u_int
);
332 static int isis_print(const u_char
*, u_int
);
334 struct isis_tlv_ip_reach
{
335 u_char metric_default
;
337 u_char metric_expense
;
343 struct isis_tlv_is_reach
{
344 u_char metric_default
;
346 u_char metric_expense
;
348 u_char neighbor_nodeid
[SYSTEM_ID_LEN
+1];
351 static struct tok isis_is_reach_virtual_values
[] = {
352 { 0, "IsNotVirtual"},
357 struct isis_common_header
{
360 u_char version
; /* Protocol version? */
362 u_char pdu_type
; /* 3 MSbs are reserved */
363 u_char pkt_version
; /* Packet format version? */
368 struct isis_iih_lan_header
{
370 u_char source_id
[SYSTEM_ID_LEN
];
371 u_char holding_time
[2];
374 u_char lan_id
[SYSTEM_ID_LEN
+1];
377 struct isis_iih_ptp_header
{
379 u_char source_id
[SYSTEM_ID_LEN
];
380 u_char holding_time
[2];
385 struct isis_lsp_header
{
387 u_char remaining_lifetime
[2];
388 u_char lsp_id
[SYSTEM_ID_LEN
+2];
389 u_char sequence_number
[4];
394 struct isis_csnp_header
{
396 u_char source_id
[SYSTEM_ID_LEN
+1];
397 u_char start_lsp_id
[SYSTEM_ID_LEN
+2];
398 u_char end_lsp_id
[SYSTEM_ID_LEN
+2];
401 struct isis_psnp_header
{
403 u_char source_id
[SYSTEM_ID_LEN
+1];
406 struct isis_tlv_lsp
{
407 u_char remaining_lifetime
[2];
408 u_char lsp_id
[SYSTEM_ID_LEN
+2];
409 u_char sequence_number
[4];
413 #define ISIS_COMMON_HEADER_SIZE (sizeof(struct isis_common_header))
414 #define ISIS_IIH_LAN_HEADER_SIZE (sizeof(struct isis_iih_lan_header))
415 #define ISIS_IIH_PTP_HEADER_SIZE (sizeof(struct isis_iih_ptp_header))
416 #define ISIS_LSP_HEADER_SIZE (sizeof(struct isis_lsp_header))
417 #define ISIS_CSNP_HEADER_SIZE (sizeof(struct isis_csnp_header))
418 #define ISIS_PSNP_HEADER_SIZE (sizeof(struct isis_psnp_header))
420 void isoclns_print(const u_char
*p
, u_int length
, u_int caplen
,
421 const u_char
*esrc
, const u_char
*edst
)
424 const struct isis_common_header
*header
;
426 header
= (const struct isis_common_header
*)p
;
427 pdu_type
= header
->pdu_type
& PDU_TYPE_MASK
;
430 printf("[|iso-clns] ");
431 if (!eflag
&& esrc
!= NULL
&& edst
!= NULL
)
433 etheraddr_string(esrc
),
434 etheraddr_string(edst
));
441 (void)printf("CLNS(%d)", length
);
442 if (!eflag
&& esrc
!= NULL
&& edst
!= NULL
)
443 (void)printf(", %s > %s",
444 etheraddr_string(esrc
),
445 etheraddr_string(edst
));
449 (void)printf("ESIS");
450 if (!eflag
&& esrc
!= NULL
&& edst
!= NULL
)
451 (void)printf(", %s > %s",
452 etheraddr_string(esrc
),
453 etheraddr_string(edst
));
454 esis_print(p
, length
);
458 (void)printf("ISIS(%d)", length
);
459 if (!eflag
&& esrc
!= NULL
&& edst
!= NULL
)
460 (void)printf(", %s > %s",
461 etheraddr_string(esrc
),
462 etheraddr_string(edst
));
463 if (!isis_print(p
, length
))
464 default_print_unaligned(p
, caplen
);
468 (void)printf("ISO NULLNS(%d)", length
);
469 if (!eflag
&& esrc
!= NULL
&& edst
!= NULL
)
470 (void)printf(", %s > %s",
471 etheraddr_string(esrc
),
472 etheraddr_string(edst
));
476 (void)printf("CLNS %02x(%d)", p
[0], length
);
477 if (!eflag
&& esrc
!= NULL
&& edst
!= NULL
)
478 (void)printf(", %s > %s",
479 etheraddr_string(esrc
),
480 etheraddr_string(edst
));
482 default_print_unaligned(p
, caplen
);
487 #define ESIS_REDIRECT 6
500 esis_print(const u_char
*p
, u_int length
)
504 const struct esis_hdr
*eh
;
510 printf(" no header at all!");
514 eh
= (const struct esis_hdr
*) &p
[2];
520 printf(" LI(%d) > PDU size (%d)!", li
, length
);
523 if (li
< sizeof(struct esis_hdr
) + 2) {
527 printf(" too short for esis header %d:", li
);
528 while (--length
!= 0)
529 printf("%02X", *p
++);
533 switch (eh
->type
& 0x1f) {
548 printf(" type %d", eh
->type
& 0x1f);
551 if (vflag
&& osi_cksum(p
, li
)) {
552 printf(" bad cksum (got 0x%02x%02x)",
553 eh
->cksum
[1], eh
->cksum
[0]);
554 default_print(p
, length
);
557 if (eh
->version
!= 1) {
558 printf(" unsupported version %d", eh
->version
);
561 p
+= sizeof(*eh
) + 2;
562 li
-= sizeof(*eh
) + 2; /* protoid * li */
564 switch (eh
->type
& 0x1f) {
565 case ESIS_REDIRECT
: {
566 const u_char
*dst
, *snpa
, *is
;
568 dst
= p
; p
+= *p
+ 1;
571 printf("\n\t\t\t %s", isonsap_string(dst
));
572 snpa
= p
; p
+= *p
+ 1;
581 printf(" > %s", etheraddr_string(&snpa
[1]));
583 printf(" > %s", isonsap_string(is
));
603 printf("\n\t\t\t %s", isonsap_string(is
));
609 (void)printf(" len=%d", length
);
610 if (length
&& p
< snapend
) {
611 length
= snapend
- p
;
612 default_print(p
, length
);
617 while (p
< ep
&& li
) {
624 printf(" bad opts/li");
631 printf(" opt (%d) too long", op
);
639 if (op
== 198 && opli
== 2) {
640 printf(" tmo=%d", q
[0] * 256 + q
[1]);
643 printf (" %d:<", op
);
645 printf("%02x", *q
++);
655 print_nsap(register const u_char
*cp
, register int length
)
659 for (i
= 0; i
< length
; i
++) {
662 printf("%02x", *cp
++);
663 if (((i
& 1) == 0) && (i
+ 1 < length
)) {
670 char *isis_print_sysid (const u_char
*);
671 /* allocate space for the following string
673 * 14 bytes plus one termination byte */
676 isis_print_sysid(const u_char
*cp
)
681 for (i
= 1; i
<= 6; i
++) {
684 pos
+=sprintf(pos
, "%02x", *cp
++);
686 pos
+=sprintf(pos
, ".");
694 char *isis_print_nodeid (const u_char
*);
695 /* allocate space for the following string
697 * 17 bytes plus one termination byte */
700 isis_print_nodeid(const u_char
*cp
)
705 for (i
= 1; i
<= 7; i
++) {
708 pos
+=sprintf(pos
, "%02x", *cp
++);
710 pos
+=sprintf(pos
, ".");
717 char *isis_print_lspid (const u_char
*);
718 /* allocate space for the following string
719 * xxxx.xxxx.xxxx.yy-zz
720 * 20 bytes plus one termination byte */
723 isis_print_lspid(const u_char
*cp
)
728 for (i
= 1; i
<= 7; i
++) {
729 pos
+=sprintf(pos
, "%02x", *cp
++);
731 pos
+=sprintf(pos
, ".");
733 pos
+=sprintf(pos
, "-%02x", *cp
);
738 * this is a generic routine for printing unknown data;
739 * as it is called from various places (TLV and subTLV parsing routines)
740 * we pass on the linefeed plus indentation string to
741 * get a proper output - returns 0 on error
745 isis_print_unknown_data(const u_char
*cp
,const u_char
*lf
,int len
)
749 printf("%s0x0000: ",lf
);
751 if (!TTEST2(*(cp
+i
), 1))
753 printf("%02x",*(cp
+i
));
756 if (i
/16!=(i
+1)/16) {
758 printf("%s0x%04x: ",lf
,i
);
761 return(1); /* everything is ok */
764 printf("%spacket exceeded snapshot",lf
);
770 isis_print_tlv_ip_reach (const u_char
*cp
, int length
)
772 u_int bitmasks
[33] = {
774 0x80000000, 0xc0000000, 0xe0000000, 0xf0000000,
775 0xf8000000, 0xfc000000, 0xfe000000, 0xff000000,
776 0xff800000, 0xffc00000, 0xffe00000, 0xfff00000,
777 0xfff80000, 0xfffc0000, 0xfffe0000, 0xffff0000,
778 0xffff8000, 0xffffc000, 0xffffe000, 0xfffff000,
779 0xfffff800, 0xfffffc00, 0xfffffe00, 0xffffff00,
780 0xffffff80, 0xffffffc0, 0xffffffe0, 0xfffffff0,
781 0xfffffff8, 0xfffffffc, 0xfffffffe, 0xffffffff
785 const struct isis_tlv_ip_reach
*tlv_ip_reach
;
787 tlv_ip_reach
= (const struct isis_tlv_ip_reach
*)cp
;
790 if (length
< sizeof(*tlv_ip_reach
)) {
791 printf("short IP reachability (%d vs %lu)", length
,
792 (unsigned long)sizeof(*tlv_ip_reach
));
796 if (!TTEST(*tlv_ip_reach
))
799 mask
= EXTRACT_32BITS(tlv_ip_reach
->mask
);
802 /* lets see if we can transform the mask into a prefixlen */
803 while (prefix_len
<= 33) {
804 if (bitmasks
[prefix_len
++] == mask
) {
811 * 34 indicates no match -> must be a discontiguous netmask
812 * lets dump the mask, otherwise print the prefix_len
814 if (prefix_len
== 34)
815 printf("\n\t\t\tIPv4 prefix: %s mask %s",
816 ipaddr_string((tlv_ip_reach
->prefix
)),
817 ipaddr_string((tlv_ip_reach
->mask
)));
819 printf("\n\t\t\tIPv4 prefix: %s/%u",
820 ipaddr_string((tlv_ip_reach
->prefix
)),
823 printf("\n\t\t\t Default Metric: %02d, %s, Distribution: %s",
824 ISIS_LSP_TLV_METRIC_VALUE(tlv_ip_reach
->metric_default
),
825 ISIS_LSP_TLV_METRIC_IE(tlv_ip_reach
->metric_default
) ? "External" : "Internal",
826 ISIS_LSP_TLV_METRIC_UPDOWN(tlv_ip_reach
->metric_default
) ? "down" : "up");
828 if (!ISIS_LSP_TLV_METRIC_SUPPORTED(tlv_ip_reach
->metric_delay
))
829 printf("\n\t\t\t Delay Metric: %02d, %s",
830 ISIS_LSP_TLV_METRIC_VALUE(tlv_ip_reach
->metric_delay
),
831 ISIS_LSP_TLV_METRIC_IE(tlv_ip_reach
->metric_delay
) ? "External" : "Internal");
833 if (!ISIS_LSP_TLV_METRIC_SUPPORTED(tlv_ip_reach
->metric_expense
))
834 printf("\n\t\t\t Expense Metric: %02d, %s",
835 ISIS_LSP_TLV_METRIC_VALUE(tlv_ip_reach
->metric_expense
),
836 ISIS_LSP_TLV_METRIC_IE(tlv_ip_reach
->metric_expense
) ? "External" : "Internal");
838 if (!ISIS_LSP_TLV_METRIC_SUPPORTED(tlv_ip_reach
->metric_error
))
839 printf("\n\t\t\t Error Metric: %02d, %s",
840 ISIS_LSP_TLV_METRIC_VALUE(tlv_ip_reach
->metric_error
),
841 ISIS_LSP_TLV_METRIC_IE(tlv_ip_reach
->metric_error
) ? "External" : "Internal");
843 length
-= sizeof(struct isis_tlv_ip_reach
);
850 * this is the common IP-REACH subTLV decoder it is called
851 * from various EXTD-IP REACH TLVs (135,236)
855 isis_print_ip_reach_subtlv (const u_char
*tptr
,int subt
,int subl
,const u_char
*lf
) {
858 case SUBTLV_EXT_IP_REACH_ADMIN_TAG
:
859 if (!TTEST2(*tptr
,4))
861 printf("%sAdministrative tag: 0x%08x",
863 EXTRACT_32BITS(tptr
));
866 printf("%sunknown subTLV, type %d, length %d",
870 if(!isis_print_unknown_data(tptr
,"\n\t\t\t ",
878 printf("%spacket exceeded snapshot",lf
);
883 * this is the common IS-REACH subTLV decoder it is called
884 * from various EXTD-IS REACH TLVs (22,222)
888 isis_print_is_reach_subtlv (const u_char
*tptr
,int subt
,int subl
,const u_char
*lf
) {
891 float bw
; /* copy buffer for several subTLVs */
894 case SUBTLV_EXT_IS_REACH_ADMIN_GROUP
:
895 if (!TTEST2(*tptr
,4))
897 printf("%sAdministrative groups: 0x%08x",
899 EXTRACT_32BITS(tptr
));
901 case SUBTLV_EXT_IS_REACH_LINK_LOCAL_ID
:
902 if (!TTEST2(*tptr
,4))
904 printf("%sLink Local Identifier: 0x%08x",
906 EXTRACT_32BITS(tptr
));
908 case SUBTLV_EXT_IS_REACH_LINK_REMOTE_ID
:
909 if (!TTEST2(*tptr
,4))
911 printf("%sLink Remote Identifier: 0x%08x",
913 EXTRACT_32BITS(tptr
));
915 case SUBTLV_EXT_IS_REACH_MAX_LINK_BW
:
916 if (!TTEST2(*tptr
,4))
918 j
= EXTRACT_32BITS(tptr
);
920 printf("%sMaximum link bandwidth : %.3f Mbps",
924 case SUBTLV_EXT_IS_REACH_RESERVABLE_BW
:
925 if (!TTEST2(*tptr
,4))
927 j
= EXTRACT_32BITS(tptr
);
929 printf("%sReservable link bandwidth: %.3f Mbps",
933 case SUBTLV_EXT_IS_REACH_UNRESERVED_BW
:
934 printf("%sUnreserved bandwidth:",lf
);
935 for (i
= 0; i
< 8; i
++) {
936 if (!TTEST2(*(tptr
+i
*4),4))
938 j
= EXTRACT_32BITS(tptr
);
940 printf("%s priority level %d: %.3f Mbps",
946 case SUBTLV_EXT_IS_REACH_TE_METRIC
:
947 if (!TTEST2(*tptr
,3))
949 printf("%sTraffic Engineering Metric: %d",
951 EXTRACT_24BITS(tptr
));
953 case SUBTLV_EXT_IS_REACH_IPV4_INTF_ADDR
:
954 if (!TTEST2(*tptr
,4))
956 printf("%sIPv4 interface address: %s",
958 ipaddr_string(tptr
));
960 case SUBTLV_EXT_IS_REACH_IPV4_NEIGHBOR_ADDR
:
961 if (!TTEST2(*tptr
,4))
963 printf("%sIPv4 neighbor address: %s",
965 ipaddr_string(tptr
));
967 case SUBTLV_EXT_IS_REACH_LINK_PROTECTION_TYPE
:
968 if (!TTEST2(*tptr
,2))
971 j
= (ISIS_8BIT_MASK(*tptr
)); /* fetch the typecode and make sure
972 that no high-order LSBs are set */
973 printf("%sLink Protection Type: %s",
976 /* scan through the bits until the typecode is zero */
978 printf("%s", isis_gmpls_link_prot_values
[i
]);
980 if (j
) /*any other bit set ?*/
984 printf(", Priority %u", *(tptr
+1));
986 case SUBTLV_EXT_IS_REACH_INTF_SW_CAP_DESCR
:
987 printf("%sInterface Switching Capability",lf
);
989 if (!TTEST2(*tptr
,1))
991 printf("%s Interface Switching Capability:%s",
993 tok2str(isis_gmpls_sw_cap_values
, "Unknown", *(tptr
)));
995 if (!TTEST2(*(tptr
+1),1))
997 printf(", LSP Encoding: %s",
998 tok2str(isis_gmpls_lsp_enc_values
, "Unknown", *(tptr
+1)));
1000 if (!TTEST2(*(tptr
+2),2)) /* skip 2 res. bytes */
1003 printf("%s Max LSP Bandwidth:",lf
);
1004 for (i
= 0; i
< 8; i
++) {
1005 if (!TTEST2(*(tptr
+(i
*4)+4),4))
1007 j
= EXTRACT_32BITS(tptr
);
1008 memcpy (&bw
, &j
, 4);
1009 printf("%s priority level %d: %.3f Mbps",
1015 /* there is some optional stuff left to decode but this is as of yet
1016 not specified so just lets hexdump what is left */
1018 if(!isis_print_unknown_data(tptr
,"\n\t\t\t ",
1028 printf("%sReserved for cisco specific extensions, type %d, length %d",
1034 printf("%sReserved for future expansion, type %d, length %d",
1040 printf("%sunknown subTLV, type %d, length %d",
1044 if(!isis_print_unknown_data(tptr
,"\n\t\t\t ",
1052 printf("%spacket exceeded snapshot",lf
);
1059 * Decode IS-IS packets. Return 0 on error.
1062 static int isis_print (const u_char
*p
, u_int length
)
1064 const struct isis_common_header
*header
;
1066 const struct isis_iih_lan_header
*header_iih_lan
;
1067 const struct isis_iih_ptp_header
*header_iih_ptp
;
1068 const struct isis_lsp_header
*header_lsp
;
1069 const struct isis_csnp_header
*header_csnp
;
1070 const struct isis_psnp_header
*header_psnp
;
1072 const struct isis_tlv_lsp
*tlv_lsp
;
1073 const struct isis_tlv_ptp_adj
*tlv_ptp_adj
;
1074 const struct isis_tlv_is_reach
*tlv_is_reach
;
1076 u_char pdu_type
, max_area
, id_length
, type
, len
, tmp
, alen
, subl
, subt
, tslen
;
1077 const u_char
*optr
, *pptr
, *tptr
;
1078 u_short packet_len
,pdu_len
,time_remain
;
1079 u_int i
,j
,bit_length
,byte_length
,metric
,ra
,rr
;
1080 u_char prefix
[4]; /* copy buffer for ipv4 prefixes */
1082 u_char prefix6
[16]; /* copy buffer for ipv6 prefixes */
1085 optr
= p
; /* initialize the _o_riginal pointer to the packet start -
1086 need it for parsing the checksum TLV */
1087 header
= (const struct isis_common_header
*)p
;
1089 pptr
= p
+(ISIS_COMMON_HEADER_SIZE
);
1090 header_iih_lan
= (const struct isis_iih_lan_header
*)pptr
;
1091 header_iih_ptp
= (const struct isis_iih_ptp_header
*)pptr
;
1092 header_lsp
= (const struct isis_lsp_header
*)pptr
;
1093 header_csnp
= (const struct isis_csnp_header
*)pptr
;
1094 header_psnp
= (const struct isis_psnp_header
*)pptr
;
1097 * Sanity checking of the header.
1099 if (header
->nlpid
!= NLPID_ISIS
) {
1100 printf(", coding error!");
1104 if (header
->version
!= ISIS_VERSION
) {
1105 printf(", version %d packet not supported", header
->version
);
1109 if ((header
->id_length
!= SYSTEM_ID_LEN
) && (header
->id_length
!= 0)) {
1110 printf(", system ID length of %d is not supported",
1115 if (header
->pkt_version
!= ISIS_VERSION
) {
1116 printf(", version %d packet not supported", header
->pkt_version
);
1120 max_area
= header
->max_area
;
1123 max_area
= 3; /* silly shit */
1126 printf(", bad packet -- 255 areas");
1132 id_length
= header
->id_length
;
1135 id_length
= 6; /* silly shit again */
1137 case 1: /* 1-8 are valid sys-ID lenghts */
1147 id_length
= 0; /* entirely useless */
1150 printf(", bad packet -- illegal sys-ID length (%u)", id_length
);
1155 printf(", hlen: %u, v: %u, sys-id-len: %u (%u), max-area: %u (%u)",
1163 pdu_type
=header
->pdu_type
;
1165 /* first lets see if we know the PDU name*/
1167 tok2str(isis_pdu_values
,
1168 "unknown PDU, type %d",
1175 if (header
->fixed_len
!= (ISIS_COMMON_HEADER_SIZE
+ISIS_IIH_LAN_HEADER_SIZE
)) {
1176 printf(", bogus fixed header length %u should be %lu",
1177 header
->fixed_len
, (unsigned long)ISIS_IIH_LAN_HEADER_SIZE
);
1181 pdu_len
=EXTRACT_16BITS(header_iih_lan
->pdu_len
);
1182 if (packet_len
>pdu_len
) {
1183 packet_len
=pdu_len
; /* do TLV decoding as long as it makes sense */
1187 TCHECK(*header_iih_lan
);
1188 printf("\n\t\t source-id: %s, holding time: %u, %s",
1189 isis_print_sysid(header_iih_lan
->source_id
),
1190 EXTRACT_16BITS(header_iih_lan
->holding_time
),
1191 tok2str(isis_iih_circuit_type_values
,
1192 "unknown circuit type 0x%02x",
1193 header_iih_lan
->circuit_type
));
1195 printf("\n\t\t lan-id: %s, Priority: %u, PDU Length: %u",
1196 isis_print_nodeid(header_iih_lan
->lan_id
),
1197 (header_iih_lan
->priority
) & PRIORITY_MASK
,
1200 packet_len
-= (ISIS_COMMON_HEADER_SIZE
+ISIS_IIH_LAN_HEADER_SIZE
);
1201 pptr
= p
+ (ISIS_COMMON_HEADER_SIZE
+ISIS_IIH_LAN_HEADER_SIZE
);
1205 if (header
->fixed_len
!= (ISIS_COMMON_HEADER_SIZE
+ISIS_IIH_PTP_HEADER_SIZE
)) {
1206 printf(", bogus fixed header length %u should be %lu",
1207 header
->fixed_len
, (unsigned long)ISIS_IIH_PTP_HEADER_SIZE
);
1211 pdu_len
=EXTRACT_16BITS(header_iih_ptp
->pdu_len
);
1212 if (packet_len
>pdu_len
) {
1213 packet_len
=pdu_len
; /* do TLV decoding as long as it makes sense */
1217 TCHECK(*header_iih_ptp
);
1218 printf("\n\t\t source-id: %s, holding time: %us, circuit-id: 0x%02x, %s, PDU Length: %u",
1219 isis_print_sysid(header_iih_ptp
->source_id
),
1220 EXTRACT_16BITS(header_iih_ptp
->holding_time
),
1221 header_iih_ptp
->circuit_id
,
1222 tok2str(isis_iih_circuit_type_values
,
1223 "unknown circuit type 0x%02x",
1224 header_iih_ptp
->circuit_type
),
1227 packet_len
-= (ISIS_COMMON_HEADER_SIZE
+ISIS_IIH_PTP_HEADER_SIZE
);
1228 pptr
= p
+ (ISIS_COMMON_HEADER_SIZE
+ISIS_IIH_PTP_HEADER_SIZE
);
1233 if (header
->fixed_len
!= (ISIS_COMMON_HEADER_SIZE
+ISIS_LSP_HEADER_SIZE
)) {
1234 printf(", bogus fixed header length %u should be %lu",
1235 header
->fixed_len
, (unsigned long)ISIS_LSP_HEADER_SIZE
);
1239 pdu_len
=EXTRACT_16BITS(header_lsp
->pdu_len
);
1240 if (packet_len
>pdu_len
) {
1241 packet_len
=pdu_len
; /* do TLV decoding as long as it makes sense */
1245 TCHECK(*header_lsp
);
1246 printf("\n\t\t lsp-id: %s, seq: 0x%08x, lifetime: %5us",
1247 isis_print_lspid(header_lsp
->lsp_id
),
1248 EXTRACT_32BITS(header_lsp
->sequence_number
),
1249 EXTRACT_16BITS(header_lsp
->remaining_lifetime
));
1250 printf("\n\t\t chksum: 0x%04x, PDU Length: %u",
1251 EXTRACT_16BITS(header_lsp
->checksum
),
1253 /* verify the checksum -
1254 * checking starts at the lsp-id field
1255 * which is 12 bytes after the packet start*/
1256 if (osi_cksum(optr
+12, length
-12))
1257 printf(" (incorrect)");
1259 printf(" (correct)");
1261 printf(", %s", ISIS_MASK_LSP_OL_BIT(header_lsp
->typeblock
) ? "Overload bit set, " : "");
1263 if (ISIS_MASK_LSP_ATT_BITS(header_lsp
->typeblock
)) {
1264 printf("%s", ISIS_MASK_LSP_ATT_DEFAULT_BIT(header_lsp
->typeblock
) ? "default " : "");
1265 printf("%s", ISIS_MASK_LSP_ATT_DELAY_BIT(header_lsp
->typeblock
) ? "delay " : "");
1266 printf("%s", ISIS_MASK_LSP_ATT_EXPENSE_BIT(header_lsp
->typeblock
) ? "expense " : "");
1267 printf("%s", ISIS_MASK_LSP_ATT_ERROR_BIT(header_lsp
->typeblock
) ? "error " : "");
1268 printf("ATT bit set, ");
1270 printf("%s", ISIS_MASK_LSP_PARTITION_BIT(header_lsp
->typeblock
) ? "P bit set, " : "");
1271 printf("%s", tok2str(isis_lsp_istype_values
,"Unknown(0x%x)",ISIS_MASK_LSP_ISTYPE_BITS(header_lsp
->typeblock
)));
1273 packet_len
-= (ISIS_COMMON_HEADER_SIZE
+ISIS_LSP_HEADER_SIZE
);
1274 pptr
= p
+ (ISIS_COMMON_HEADER_SIZE
+ISIS_LSP_HEADER_SIZE
);
1279 if (header
->fixed_len
!= (ISIS_COMMON_HEADER_SIZE
+ISIS_CSNP_HEADER_SIZE
)) {
1280 printf(", bogus fixed header length %u should be %lu",
1281 header
->fixed_len
, (unsigned long)ISIS_CSNP_HEADER_SIZE
);
1285 pdu_len
=EXTRACT_16BITS(header_csnp
->pdu_len
);
1286 if (packet_len
>pdu_len
) {
1287 packet_len
=pdu_len
; /* do TLV decoding as long as it makes sense */
1291 TCHECK(*header_csnp
);
1292 printf("\n\t\t source-id: %s, PDU Length: %u",
1293 isis_print_nodeid(header_csnp
->source_id
),
1295 printf("\n\t\t start lsp-id: %s",
1296 isis_print_lspid(header_csnp
->start_lsp_id
));
1297 printf("\n\t\t end lsp-id: %s",
1298 isis_print_lspid(header_csnp
->end_lsp_id
));
1300 packet_len
-= (ISIS_COMMON_HEADER_SIZE
+ISIS_CSNP_HEADER_SIZE
);
1301 pptr
= p
+ (ISIS_COMMON_HEADER_SIZE
+ISIS_CSNP_HEADER_SIZE
);
1306 if (header
->fixed_len
!= (ISIS_COMMON_HEADER_SIZE
+ISIS_PSNP_HEADER_SIZE
)) {
1307 printf("- bogus fixed header length %u should be %lu",
1308 header
->fixed_len
, (unsigned long)ISIS_PSNP_HEADER_SIZE
);
1312 pdu_len
=EXTRACT_16BITS(header_psnp
->pdu_len
);
1313 if (packet_len
>pdu_len
) {
1314 packet_len
=pdu_len
; /* do TLV decoding as long as it makes sense */
1318 TCHECK(*header_psnp
);
1319 printf("\n\t\t source-id: %s",
1320 isis_print_nodeid(header_psnp
->source_id
));
1322 packet_len
-= (ISIS_COMMON_HEADER_SIZE
+ISIS_PSNP_HEADER_SIZE
);
1323 pptr
= p
+ (ISIS_COMMON_HEADER_SIZE
+ISIS_PSNP_HEADER_SIZE
);
1327 if(!isis_print_unknown_data(pptr
,"\n\t\t ",length
))
1333 * Now print the TLV's.
1336 while (packet_len
>= 2) {
1337 if (pptr
== snapend
) {
1341 if (!TTEST2(*pptr
, 2)) {
1342 printf("\n\t\t\t packet exceeded snapshot (%ld) bytes",
1343 (long)(pptr
-snapend
));
1348 tmp
=len
; /* copy temporary len & pointer to packet data */
1351 if (len
> packet_len
) {
1355 /* first lets see if we know the TLVs name*/
1356 printf("\n\t\t %s (%u)",
1357 tok2str(isis_tlv_values
,
1358 "unknown TLV, type %d, length",
1362 /* now check if we have a decoder otherwise do a hexdump at the end*/
1365 if (!TTEST2(*tptr
, 1))
1368 while (tmp
&& alen
< tmp
) {
1369 printf("\n\t\t\tArea address (%u): ",alen
);
1370 if (!print_nsap(tptr
, alen
))
1374 if (tmp
==0) /* if this is the last area address do not attemt a boundary check */
1376 if (!TTEST2(*tptr
, 1))
1382 while (tmp
>= ETHER_ADDR_LEN
) {
1383 printf("\n\t\t\tIS Neighbor: %s",isis_print_sysid(tptr
));
1384 tmp
-= ETHER_ADDR_LEN
;
1385 tptr
+= ETHER_ADDR_LEN
;
1392 case TLV_MT_IS_REACH
:
1394 if (!TTEST2(*tptr
, 2))
1396 printf("\n\t\t\t%s",
1397 tok2str(isis_mt_values
,
1398 "Reserved for IETF Consensus",
1399 ISIS_MASK_MTID(EXTRACT_16BITS(tptr
))));
1401 printf(" Topology (0x%03x)",
1402 ISIS_MASK_MTID(EXTRACT_16BITS(tptr
)));
1404 printf("\n\t\t\t IS Neighbor: %s", isis_print_nodeid(tptr
));
1405 tptr
+=(SYSTEM_ID_LEN
+1);
1406 if (!TTEST2(*tptr
, 3))
1408 printf(", Metric: %d",EXTRACT_24BITS(tptr
));
1410 if (!TTEST2(*tptr
, 1))
1413 printf(", %ssub-TLVs present",tslen
? "" : "no ");
1415 printf(" (%u)",tslen
);
1417 if (!TTEST2(*tptr
,2))
1421 if(!isis_print_is_reach_subtlv(tptr
,subt
,subl
,"\n\t\t\t "))
1428 tmp
-=(SYSTEM_ID_LEN
+7);
1432 case TLV_EXT_IS_REACH
:
1434 if (!TTEST2(*tptr
, SYSTEM_ID_LEN
+1))
1436 printf("\n\t\t\tIS Neighbor: %s", isis_print_nodeid(tptr
));
1437 tptr
+=(SYSTEM_ID_LEN
+1);
1439 if (!TTEST2(*tptr
, 3))
1441 printf(", Metric: %d",EXTRACT_24BITS(tptr
));
1444 if (!TTEST2(*tptr
, 1))
1446 tslen
=*(tptr
++); /* read out subTLV length */
1447 printf(", %ssub-TLVs present",tslen
? "" : "no ");
1449 printf(" (%u)",tslen
);
1451 if (!TTEST2(*tptr
,2))
1455 if(!isis_print_is_reach_subtlv(tptr
,subt
,subl
,"\n\t\t\t "))
1462 tmp
-=(SYSTEM_ID_LEN
+5);
1466 if (!TTEST2(*tptr
,1)) /* check if there is one byte left to read out the virtual flag */
1469 printf("\n\t\t\t%s",
1470 tok2str(isis_is_reach_virtual_values
,
1471 "bogus virtual flag 0x%02x",
1474 tlv_is_reach
= (const struct isis_tlv_is_reach
*)tptr
;
1476 while (tmp
>= sizeof(struct isis_tlv_is_reach
)) {
1477 if (!TTEST(*tlv_is_reach
))
1480 printf("\n\t\t\tIS Neighbor: %s", isis_print_nodeid(tlv_is_reach
->neighbor_nodeid
));
1481 printf(", Default Metric: %d, %s",
1482 ISIS_LSP_TLV_METRIC_VALUE(tlv_is_reach
->metric_default
),
1483 ISIS_LSP_TLV_METRIC_IE(tlv_is_reach
->metric_default
) ? "External" : "Internal");
1485 if (!ISIS_LSP_TLV_METRIC_SUPPORTED(tlv_is_reach
->metric_delay
))
1486 printf("\n\t\t\t Delay Metric: %d, %s",
1487 ISIS_LSP_TLV_METRIC_VALUE(tlv_is_reach
->metric_delay
),
1488 ISIS_LSP_TLV_METRIC_IE(tlv_is_reach
->metric_delay
) ? "External" : "Internal");
1490 if (!ISIS_LSP_TLV_METRIC_SUPPORTED(tlv_is_reach
->metric_expense
))
1491 printf("\n\t\t\t Expense Metric: %d, %s",
1492 ISIS_LSP_TLV_METRIC_VALUE(tlv_is_reach
->metric_expense
),
1493 ISIS_LSP_TLV_METRIC_IE(tlv_is_reach
->metric_expense
) ? "External" : "Internal");
1495 if (!ISIS_LSP_TLV_METRIC_SUPPORTED(tlv_is_reach
->metric_error
))
1496 printf("\n\t\t\t Error Metric: %d, %s",
1497 ISIS_LSP_TLV_METRIC_VALUE(tlv_is_reach
->metric_error
),
1498 ISIS_LSP_TLV_METRIC_IE(tlv_is_reach
->metric_error
) ? "External" : "Internal");
1500 tmp
-= sizeof(struct isis_tlv_is_reach
);
1505 /* those two TLVs share the same format */
1507 case TLV_IP_REACH_EXT
:
1508 if (!isis_print_tlv_ip_reach(pptr
, len
))
1512 case TLV_MT_IP_REACH
:
1514 if (!TTEST2(*tptr
, 2))
1517 printf("\n\t\t\t%s",
1518 tok2str(isis_mt_values
,
1519 "Reserved for IETF Consensus",
1520 ISIS_MASK_MTID(EXTRACT_16BITS(tptr
))));
1522 printf(" Topology (0x%03x)",
1523 ISIS_MASK_MTID(EXTRACT_16BITS(tptr
)));
1526 memset (prefix
, 0, 4);
1527 if (!TTEST2(*tptr
, 4))
1529 metric
= EXTRACT_32BITS(tptr
);
1532 if (!TTEST2(*tptr
, 1)) /* fetch status byte */
1535 bit_length
= (*(tptr
)++&0x3f);
1536 byte_length
= (bit_length
+ 7) / 8; /* prefix has variable length encoding */
1538 if (!TTEST2(*tptr
, byte_length
))
1540 memcpy(prefix
,tptr
,byte_length
);
1542 printf("\n\t\t\tIPv4 prefix: %s/%d",
1543 ipaddr_string(prefix
),
1546 printf("\n\t\t\t Metric: %u, Distribution: %s",
1548 ISIS_MASK_TLV_EXT_IP_UPDOWN(j
) ? "down" : "up");
1550 printf(", %ssub-TLVs present",
1551 ISIS_MASK_TLV_EXT_IP_SUBTLV(j
) ? "" : "no ");
1553 if (ISIS_MASK_TLV_EXT_IP_SUBTLV(j
)) {
1554 /* assume that one prefix can hold more
1555 than one subTLV - therefore the first byte must reflect
1556 the aggregate bytecount of the subTLVs for this prefix
1558 if (!TTEST2(*tptr
, 1))
1562 printf(" (%u)",tslen
); /* print out subTLV length */
1565 if (!TTEST2(*tptr
,2))
1569 if(!isis_print_ip_reach_subtlv(tptr
,subt
,subl
,"\n\t\t\t "))
1576 tmp
-=(7+byte_length
);
1580 case TLV_EXT_IP_REACH
:
1582 memset (prefix
, 0, 4);
1583 if (!TTEST2(*tptr
, 4))
1585 metric
= EXTRACT_32BITS(tptr
);
1588 if (!TTEST2(*tptr
, 1)) /* fetch status byte */
1591 bit_length
= (*(tptr
)++&0x3f);
1592 byte_length
= (bit_length
+ 7) / 8; /* prefix has variable length encoding */
1594 if (!TTEST2(*tptr
, byte_length
))
1596 memcpy(prefix
,tptr
,byte_length
);
1598 printf("\n\t\t\tIPv4 prefix: %s/%d",
1599 ipaddr_string(prefix
),
1602 printf("\n\t\t\t Metric: %u, Distribution: %s",
1604 ISIS_MASK_TLV_EXT_IP_UPDOWN(j
) ? "down" : "up");
1606 printf(", %ssub-TLVs present",
1607 ISIS_MASK_TLV_EXT_IP_SUBTLV(j
) ? "" : "no ");
1609 if (ISIS_MASK_TLV_EXT_IP_SUBTLV(j
)) {
1610 /* assume that one prefix can hold more
1611 than one subTLV - therefore the first byte must reflect
1612 the aggregate bytecount of the subTLVs for this prefix
1614 if (!TTEST2(*tptr
, 1))
1618 printf(" (%u)",tslen
); /* print out subTLV length */
1621 if (!TTEST2(*tptr
,2))
1625 if(!isis_print_ip_reach_subtlv(tptr
,subt
,subl
,"\n\t\t\t "))
1632 tmp
-=(5+byte_length
);
1640 if (!TTEST2(*tptr
, 4))
1642 metric
= EXTRACT_32BITS(tptr
);
1645 if (!TTEST2(*tptr
, 2))
1648 bit_length
= (*(tptr
)++);
1649 byte_length
= (bit_length
+ 7) / 8;
1650 if (!TTEST2(*tptr
, byte_length
))
1653 memset(prefix6
, 0, 16);
1654 memcpy(prefix6
,tptr
,byte_length
);
1656 printf("\n\t\t\tIPv6 prefix: %s/%u",
1657 ip6addr_string(prefix6
),
1660 printf("\n\t\t\t Metric: %u, %s, Distribution: %s, %ssub-TLVs present",
1662 ISIS_MASK_TLV_IP6_IE(j
) ? "External" : "Internal",
1663 ISIS_MASK_TLV_IP6_UPDOWN(j
) ? "down" : "up",
1664 ISIS_MASK_TLV_IP6_SUBTLV(j
) ? "" : "no ");
1666 if (ISIS_MASK_TLV_IP6_SUBTLV(j
)) {
1667 /* assume that one prefix can hold more
1668 than one subTLV - therefore the first byte must reflect
1669 the aggregate bytecount of the subTLVs for this prefix
1671 if (!TTEST2(*tptr
, 1))
1675 printf(" (%u)",tslen
); /* print out subTLV length */
1678 if (!TTEST2(*tptr
,2))
1682 if(!isis_print_ip_reach_subtlv(tptr
,subt
,subl
,"\n\t\t\t "))
1689 tmp
-=(6+byte_length
);
1698 if (!TTEST2(*tptr
, 16))
1701 printf("\n\t\t\tIPv6 interface address: %s",
1702 ip6addr_string(tptr
));
1710 if (!TTEST2(*tptr
, 1))
1713 printf("\n\t\t\t%s: ",
1714 tok2str(isis_subtlv_auth_values
,
1715 "unknown Authentication type 0x%02x",
1719 case SUBTLV_AUTH_SIMPLE
:
1720 for(i
=1;i
<len
;i
++) {
1721 if (!TTEST2(*(tptr
+i
), 1))
1723 printf("%c",*(tptr
+i
));
1726 case SUBTLV_AUTH_MD5
:
1727 for(i
=1;i
<len
;i
++) {
1728 if (!TTEST2(*(tptr
+i
), 1))
1730 printf("%02x",*(tptr
+i
));
1732 if (len
!= SUBTLV_AUTH_MD5_LEN
+1)
1733 printf(", (malformed subTLV) ");
1735 case SUBTLV_AUTH_PRIVATE
:
1737 if(!isis_print_unknown_data(tptr
+1,"\n\t\t\t ",len
-1))
1744 tlv_ptp_adj
= (const struct isis_tlv_ptp_adj
*)tptr
;
1746 if (!TTEST2(*tptr
, 1))
1748 printf("\n\t\t\tAdjacency State: %s",
1749 tok2str(isis_ptp_adjancey_values
, "0x%02x", *tptr
));
1753 if (!TTEST2(tlv_ptp_adj
->ext_local_circuit_id
, 4))
1755 printf("\n\t\t\tExtended Local circuit ID: 0x%08x",
1756 EXTRACT_32BITS(tlv_ptp_adj
->ext_local_circuit_id
));
1760 if (!TTEST2(tlv_ptp_adj
->neighbor_sysid
, 6))
1762 printf("\n\t\t\tNeighbor SystemID: %s",
1763 isis_print_sysid(tlv_ptp_adj
->neighbor_sysid
));
1767 if (!TTEST2(tlv_ptp_adj
->neighbor_ext_local_circuit_id
, 4))
1769 printf("\n\t\t\tNeighbor Extended Local circuit ID: 0x%08x",
1770 EXTRACT_32BITS(tlv_ptp_adj
->neighbor_ext_local_circuit_id
));
1775 printf("\n\t\t\tNLPID(s): ");
1777 if (!TTEST2(*(tptr
), 1))
1780 tok2str(isis_nlpid_values
,
1783 if (tmp
>1) /* further NPLIDs ? - put comma */
1789 case TLV_TE_ROUTER_ID
:
1790 if (!TTEST2(*pptr
, 4))
1792 printf("\n\t\t\tTraffic Engineering Router ID: %s", ipaddr_string(pptr
));
1797 if (!TTEST2(*tptr
, 4))
1799 printf("\n\t\t\tIPv4 interface address: %s", ipaddr_string(tptr
));
1806 printf("\n\t\t\tHostname: ");
1808 if (!TTEST2(*tptr
, 1))
1810 printf("%c",*tptr
++);
1815 case TLV_SHARED_RISK_GROUP
:
1816 if (!TTEST2(*tptr
, 7))
1818 printf("\n\t\t\tIS Neighbor: %s", isis_print_nodeid(tptr
));
1819 tptr
+=(SYSTEM_ID_LEN
+1);
1820 len
-=(SYSTEM_ID_LEN
+1);
1822 if (!TTEST2(*tptr
, 1))
1824 printf(", %s", ISIS_MASK_TLV_SHARED_RISK_GROUP(*tptr
++) ? "numbered" : "unnumbered");
1827 if (!TTEST2(*tptr
,4))
1829 printf("\n\t\t\tIPv4 interface address: %s", ipaddr_string(tptr
));
1833 if (!TTEST2(*tptr
,4))
1835 printf("\n\t\t\tIPv4 neighbor address: %s", ipaddr_string(tptr
));
1840 if (!TTEST2(*tptr
, 4))
1842 printf("\n\t\t\tLink-ID: 0x%08x", EXTRACT_32BITS(tptr
));
1849 tlv_lsp
= (const struct isis_tlv_lsp
*)tptr
;
1851 printf("\n\t\t\tlsp-id: %s",
1852 isis_print_nodeid(tlv_lsp
->lsp_id
));
1853 if (!TTEST((tlv_lsp
->lsp_id
)[SYSTEM_ID_LEN
+1]))
1855 printf("-%02x",(tlv_lsp
->lsp_id
)[SYSTEM_ID_LEN
+1]);
1856 if (!TTEST2(tlv_lsp
->sequence_number
, 4))
1858 printf(", seq: 0x%08x",EXTRACT_32BITS(tlv_lsp
->sequence_number
));
1859 if (!TTEST2(tlv_lsp
->remaining_lifetime
, 2))
1861 printf(", lifetime: %5ds",EXTRACT_16BITS(tlv_lsp
->remaining_lifetime
));
1862 if (!TTEST2(tlv_lsp
->checksum
, 2))
1864 printf(", chksum: 0x%04x",EXTRACT_16BITS(tlv_lsp
->checksum
));
1865 tmp
-=sizeof(struct isis_tlv_lsp
);
1871 if (!TTEST2(*tptr
, 2))
1873 printf("\n\t\t\tchecksum: 0x%04x",
1874 EXTRACT_16BITS(tptr
));
1875 if (osi_cksum(optr
, length
))
1876 printf(" (incorrect)");
1878 printf(" (correct)");
1881 case TLV_MT_SUPPORTED
:
1883 /* length can only be a multiple of 2, otherwise there is
1884 something broken -> so decode down until length is 1 */
1886 if (!TTEST2(*tptr
, 2))
1888 printf("\n\t\t\t%s",
1889 tok2str(isis_mt_values
,
1890 "Reserved for IETF Consensus",
1891 ISIS_MASK_MTID(EXTRACT_16BITS(tptr
))));
1893 printf(" Topology (0x%03x)%s%s",
1894 ISIS_MASK_MTID(EXTRACT_16BITS(tptr
)),
1895 ISIS_MASK_MTSUB(EXTRACT_16BITS(tptr
)) ? "" : ", no sub-TLVs present",
1896 ISIS_MASK_MTATT(EXTRACT_16BITS(tptr
)) ? ", ATT bit set" : "" );
1898 printf("\n\t\t\tmalformed MT-ID");
1906 case TLV_RESTART_SIGNALING
:
1907 if (!TTEST2(*tptr
, 3))
1909 rr
= ISIS_MASK_TLV_RESTART_RR(*tptr
);
1910 ra
= ISIS_MASK_TLV_RESTART_RA(*tptr
);
1912 time_remain
= EXTRACT_16BITS(tptr
);
1913 printf("\n\t\t\tRestart Request bit %s, Restart Acknowledgement bit %s\n\t\t\tRemaining holding time: %us",
1914 rr
? "set" : "clear", ra
? "set" : "clear", time_remain
);
1918 * FIXME those are the defined TLVs that lack a decoder
1919 * you are welcome to contribute code ;-)
1925 case TLV_LSP_BUFFERSIZE
:
1926 case TLV_IS_ALIAS_ID
:
1927 case TLV_DECNET_PHASE4
:
1928 case TLV_LUCENT_PRIVATE
:
1931 case TLV_NORTEL_PRIVATE1
:
1932 case TLV_NORTEL_PRIVATE2
:
1933 case TLV_MT_IP6_REACH
:
1936 if(!isis_print_unknown_data(pptr
,"\n\t\t\t",len
))
1945 if (packet_len
!= 0) {
1946 printf("\n\t\t\t %d straggler bytes", packet_len
);
1951 fputs("[|isis]", stdout
);
1955 printf("\n\t\t\t packet exceeded snapshot");
1960 * Verify the checksum. See 8473-1, Appendix C, section C.4.
1964 osi_cksum(const u_char
*tptr
, u_int len
)
1966 int32_t c0
= 0, c1
= 0;
1968 while ((int)--len
>= 0) {