From: hannes Date: Fri, 13 Dec 2002 00:40:34 +0000 (+0000) Subject: initial checkin for a Label Distribution Protocol dissector X-Git-Tag: tcpdump-3.8-bp~269 X-Git-Url: https://git.tcpdump.org/tcpdump/commitdiff_plain/8df276dff34a0db4f43ed222ff4a90aad02d05c0 initial checkin for a Label Distribution Protocol dissector --- diff --git a/Makefile.in b/Makefile.in index 0c29326d..6d08605a 100644 --- a/Makefile.in +++ b/Makefile.in @@ -17,7 +17,7 @@ # WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF # MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. # -# @(#) $Header: /tcpdump/master/tcpdump/Makefile.in,v 1.268 2002-10-18 09:17:47 guy Exp $ (LBL) +# @(#) $Header: /tcpdump/master/tcpdump/Makefile.in,v 1.269 2002-12-13 00:40:34 hannes Exp $ (LBL) # # Various configurable paths (remember to edit Makefile.in, not Makefile) @@ -74,7 +74,7 @@ CSRC = addrtoname.c gmt2local.c machdep.c parsenfsfh.c \ print-fddi.c print-fr.c print-gre.c print-hsrp.c \ print-icmp.c print-igmp.c print-igrp.c print-ip.c \ print-ipcomp.c print-ipfc.c print-ipx.c print-isakmp.c \ - print-isoclns.c print-krb.c print-l2tp.c print-lane.c \ + print-isoclns.c print-krb.c print-l2tp.c print-ldp.c print-lane.c \ print-llc.c print-lwres.c print-msdp.c print-mobile.c \ print-mpls.c print-nfs.c print-ntp.c print-null.c \ print-ospf.c print-pflog.c print-pim.c print-ppp.c \ diff --git a/interface.h b/interface.h index 97c3c766..e48cf7ed 100644 --- a/interface.h +++ b/interface.h @@ -18,7 +18,7 @@ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. * - * @(#) $Header: /tcpdump/master/tcpdump/interface.h,v 1.199 2002-12-12 07:28:35 guy Exp $ (LBL) + * @(#) $Header: /tcpdump/master/tcpdump/interface.h,v 1.200 2002-12-13 00:40:34 hannes Exp $ (LBL) */ #ifndef tcpdump_interface_h @@ -257,6 +257,7 @@ extern void ospf_print(const u_char *, u_int, const u_char *); extern void pimv1_print(const u_char *, u_int); extern void cisco_autorp_print(const u_char *, u_int); extern void rsvp_print(const u_char *, u_int); +extern void ldp_print(const u_char *, u_int); extern void mobile_print(const u_char *, u_int); extern void pim_print(const u_char *, u_int); extern u_int pppoe_print(const u_char *, u_int); diff --git a/print-ldp.c b/print-ldp.c new file mode 100644 index 00000000..25ea9581 --- /dev/null +++ b/print-ldp.c @@ -0,0 +1,207 @@ +/* + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that: (1) source code + * distributions retain the above copyright notice and this paragraph + * in its entirety, and (2) distributions including binary code include + * the above copyright notice and this paragraph in its entirety in + * the documentation or other materials provided with the distribution. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND + * WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, WITHOUT + * LIMITATION, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE. + * + * Original code by Hannes Gredler (hannes@juniper.net) + */ + +#ifndef lint +static const char rcsid[] = + "@(#) $Header: /tcpdump/master/tcpdump/print-ldp.c,v 1.1 2002-12-13 00:40:35 hannes Exp $"; +#endif + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include + +#include +#include +#include + +#include "interface.h" +#include "extract.h" +#include "addrtoname.h" +#include "ethertype.h" + +/* + * ldp common header + * + * 0 1 2 3 + * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 + * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * | Version | PDU Length | + * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * | LDP Identifier | + * + +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * | | + * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * + */ + +struct ldp_common_header { + u_int8_t version[2]; + u_int8_t pdu_length[2]; + u_int8_t lsr_id[4]; + u_int8_t label_space[2]; +}; + +#define LDP_VERSION 1 + +/* + * ldp tlv header + * + * 0 1 2 3 + * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 + * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * |U|F| Type | Length | + * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * | | + * | Value | + * ~ ~ + * | | + * | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + * | | + * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + */ + +struct ldp_tlv_header { + u_int8_t type[2]; + u_int8_t length[2]; +}; + +#define LDP_MASK_TLV_TYPE(x) ((x)&0x3fff) +#define LDP_MASK_TLV_U_BIT(x) ((x)&0x8000) +#define LDP_MASK_TLV_F_BIT(x) ((x)&0x4000) + +#define LDP_TLV_FEC 0x0100 +#define LDP_TLV_ADDRESS_LIST 0x0101 +#define LDP_TLV_HOP_COUNT 0x0103 +#define LDP_TLV_PATH_VECTOR 0x0104 +#define LDP_TLV_GENERIC_LABEL 0x0200 +#define LDP_TLV_ATM_LABEL 0x0201 +#define LDP_TLV_FR_LABEL 0x0202 +#define LDP_TLV_STATUS 0x0300 + +static const struct tok ldp_tlv_values[] = { + { LDP_TLV_FEC, "FEC" }, + { LDP_TLV_ADDRESS_LIST, "Address List" }, + { LDP_TLV_HOP_COUNT, "Hop Count" }, + { LDP_TLV_HOP_COUNT, "Path Vector" }, + { LDP_TLV_GENERIC_LABEL, "Generic Label" }, + { LDP_TLV_ATM_LABEL, "ATM Label" }, + { LDP_TLV_FR_LABEL, "Frame-Relay Label" }, + { LDP_TLV_STATUS, "Status" }, + { 0, NULL} +}; + +#define FALSE 0 +#define TRUE 1 + +void +ldp_print(register const u_char *pptr, register u_int len) { + + const struct ldp_common_header *ldp_com_header; + const struct ldp_tlv_header *ldp_tlv_header; + const u_char *tptr,*tlv_tptr; + u_short tlen,tlv_len,tlv_type,tlv_tlen; + int hexdump; + + tptr=pptr; + ldp_com_header = (const struct ldp_common_header *)pptr; + TCHECK(*ldp_com_header); + + /* + * Sanity checking of the header. + */ + if (EXTRACT_16BITS(&ldp_com_header->version) != LDP_VERSION) { + printf("LDP version %u packet not supported", + EXTRACT_16BITS(&ldp_com_header->version)); + return; + } + + /* print the LSR-ID, label-space & length */ + printf("%sLDP, Label-Space-ID: %s:%u, length: %u", + (vflag < 1) ? "" : "\n\t", + ipaddr_string(&ldp_com_header->lsr_id), + EXTRACT_16BITS(&ldp_com_header->label_space), + len); + + /* bail out if non-verbose */ + if (vflag < 1) + return; + + /* ok they seem to want to know everything - lets fully decode it */ + tlen=EXTRACT_16BITS(ldp_com_header->pdu_length); + + tptr+=sizeof(const struct ldp_common_header); + tlen-=sizeof(const struct ldp_common_header); + + while(tlen>0) { + /* did we capture enough for fully decoding the tlv header ? */ + if (!TTEST2(*tptr, sizeof(struct ldp_tlv_header))) + goto trunc; + + ldp_tlv_header = (const struct ldp_tlv_header *)tptr; + tlv_len=EXTRACT_16BITS(ldp_tlv_header->length); + tlv_type=LDP_MASK_TLV_TYPE(EXTRACT_16BITS(ldp_tlv_header->type)); + + printf("\n\t %s TLV (0x%04x), length: %u, Flags: [%s and %s forward if unknown]", + tok2str(ldp_tlv_values, + "Unknown", + tlv_type), + tlv_type, + tlv_len, + LDP_MASK_TLV_U_BIT(EXTRACT_16BITS(&ldp_tlv_header->type)) ? "continue processing" : "ignore all, notify", + LDP_MASK_TLV_F_BIT(EXTRACT_16BITS(&ldp_tlv_header->type)) ? "do" : "don't"); + + tlv_tptr=tptr+sizeof(struct ldp_tlv_header); + tlv_tlen=tlv_len-sizeof(struct ldp_tlv_header); + + /* did we capture enough for fully decoding the object ? */ + if (!TTEST2(*tptr, tlv_len)) + goto trunc; + hexdump=FALSE; + + switch(tlv_type) { + + /* + * FIXME those are the defined objects that lack a decoder + * you are welcome to contribute code ;-) + */ + + case LDP_TLV_FEC: + case LDP_TLV_ADDRESS_LIST: + case LDP_TLV_HOP_COUNT: + case LDP_TLV_PATH_VECTOR: + case LDP_TLV_GENERIC_LABEL: + case LDP_TLV_ATM_LABEL: + case LDP_TLV_FR_LABEL: + case LDP_TLV_STATUS: + default: + if (vflag <= 1) + print_unknown_data(tlv_tptr,"\n\t ",tlv_tlen); + break; + } + /* do we want to see an additionally hexdump ? */ + if (vflag > 1 || hexdump==TRUE) + print_unknown_data(tptr+sizeof(sizeof(struct ldp_tlv_header)),"\n\t ", + tlv_len-sizeof(struct ldp_tlv_header)); + + tptr+=tlv_len; + tlen-=tlv_len; + } + return; +trunc: + printf("\n\t\t packet exceeded snapshot"); +} + diff --git a/print-udp.c b/print-udp.c index 67c36715..75d46839 100644 --- a/print-udp.c +++ b/print-udp.c @@ -21,7 +21,7 @@ #ifndef lint static const char rcsid[] = - "@(#) $Header: /tcpdump/master/tcpdump/print-udp.c,v 1.113 2002-12-11 07:14:10 guy Exp $ (LBL)"; + "@(#) $Header: /tcpdump/master/tcpdump/print-udp.c,v 1.114 2002-12-13 00:40:34 hannes Exp $ (LBL)"; #endif #ifdef HAVE_CONFIG_H @@ -663,7 +663,7 @@ udp_print(register const u_char *bp, u_int length, else if (ISPORT(LWRES_PORT)) lwres_print((const u_char *)(up + 1), length); else if (ISPORT(LDP_PORT)) - printf("LDP, length: %u", length); + ldp_print((const u_char *)(up + 1), length); else (void)printf("udp %u", (u_int32_t)(ulen - sizeof(*up)));