print-bgp.c

来自「TCPDUMP的C语言源代码,是在数据链路层的应用」· C语言 代码 · 共 1,792 行 · 第 1/5 页

C
1,792
字号
		return -1;        plen-=(24+64); /* adjust prefixlen - labellength - RD len*/	if (32 < plen)		return -1;	memset(&addr, 0, sizeof(addr));	TCHECK2(pptr[12], (plen + 7) / 8);	memcpy(&addr, &pptr[12], (plen + 7) / 8);	if (plen % 8) {		((u_char *)&addr)[(plen + 7) / 8 - 1] &=			((0xff00 >> (plen % 8)) & 0xff);	}        /* the label may get offsetted by 4 bits so lets shift it right */	snprintf(buf, buflen, "RD: %s, %s/%d, label:%u %s",                 bgp_vpn_rd_print(pptr+4),                 getname((u_char *)&addr),                 plen,                 EXTRACT_24BITS(pptr+1)>>4,                 ((pptr[3]&1)==0) ? "(BOGUS: Bottom of Stack NOT set!)" : "(bottom)" );	return 12 + (plen + 7) / 8;trunc:	return -2;}#define BGP_MULTICAST_VPN_ROUTE_TYPE_INTRA_AS_I_PMSI   1#define BGP_MULTICAST_VPN_ROUTE_TYPE_INTER_AS_I_PMSI   2#define BGP_MULTICAST_VPN_ROUTE_TYPE_S_PMSI            3#define BGP_MULTICAST_VPN_ROUTE_TYPE_INTRA_AS_SEG_LEAF 4#define BGP_MULTICAST_VPN_ROUTE_TYPE_SOURCE_ACTIVE     5#define BGP_MULTICAST_VPN_ROUTE_TYPE_SHARED_TREE_JOIN  6#define BGP_MULTICAST_VPN_ROUTE_TYPE_SOURCE_TREE_JOIN  7static struct tok bgp_multicast_vpn_route_type_values[] = {    { BGP_MULTICAST_VPN_ROUTE_TYPE_INTRA_AS_I_PMSI, "Intra-AS I-PMSI"},    { BGP_MULTICAST_VPN_ROUTE_TYPE_INTER_AS_I_PMSI, "Inter-AS I-PMSI"},    { BGP_MULTICAST_VPN_ROUTE_TYPE_S_PMSI, "S-PMSI"},    { BGP_MULTICAST_VPN_ROUTE_TYPE_INTRA_AS_SEG_LEAF, "Intra-AS Segment-Leaf"},    { BGP_MULTICAST_VPN_ROUTE_TYPE_SOURCE_ACTIVE, "Source-Active"},    { BGP_MULTICAST_VPN_ROUTE_TYPE_SHARED_TREE_JOIN, "Shared Tree Join"},    { BGP_MULTICAST_VPN_ROUTE_TYPE_SOURCE_TREE_JOIN, "Source Tree Join"},};static intdecode_multicast_vpn(const u_char *pptr, char *buf, u_int buflen){        u_int8_t route_type, route_length, addr_length, sg_length;        u_int offset;	TCHECK2(pptr[0], 2);        route_type = *pptr++;        route_length = *pptr++;        snprintf(buf, buflen, "Route-Type: %s (%u), length: %u",                 tok2str(bgp_multicast_vpn_route_type_values,                         "Unknown", route_type),                 route_type, route_length);        switch(route_type) {        case BGP_MULTICAST_VPN_ROUTE_TYPE_INTRA_AS_I_PMSI:            TCHECK2(pptr[0], BGP_VPN_RD_LEN);            offset = strlen(buf);            snprintf(buf + offset, buflen - offset, ", RD: %s, Originator %s",                     bgp_vpn_rd_print(pptr),                     bgp_vpn_ip_print(pptr + BGP_VPN_RD_LEN,                                      (route_length - BGP_VPN_RD_LEN) << 3));            break;        case BGP_MULTICAST_VPN_ROUTE_TYPE_INTER_AS_I_PMSI:            TCHECK2(pptr[0], BGP_VPN_RD_LEN + 4);            offset = strlen(buf);            snprintf(buf + offset, buflen - offset, ", RD: %s, Source-AS %u",                     bgp_vpn_rd_print(pptr),                     EXTRACT_32BITS(pptr + BGP_VPN_RD_LEN));            break;        case BGP_MULTICAST_VPN_ROUTE_TYPE_S_PMSI:            TCHECK2(pptr[0], BGP_VPN_RD_LEN);            offset = strlen(buf);            snprintf(buf + offset, buflen - offset, ", RD: %s",                     bgp_vpn_rd_print(pptr));            pptr += BGP_VPN_RD_LEN;            sg_length = bgp_vpn_sg_print(pptr, buf, buflen);            addr_length =  route_length - sg_length;            TCHECK2(pptr[0], addr_length);            offset = strlen(buf);            snprintf(buf + offset, buflen - offset, ", Originator %s",                     bgp_vpn_ip_print(pptr, addr_length << 3));            break;        case BGP_MULTICAST_VPN_ROUTE_TYPE_SOURCE_ACTIVE:            TCHECK2(pptr[0], BGP_VPN_RD_LEN);            offset = strlen(buf);            snprintf(buf + offset, buflen - offset, ", RD: %s",                     bgp_vpn_rd_print(pptr));            pptr += BGP_VPN_RD_LEN;            bgp_vpn_sg_print(pptr, buf, buflen);            break;        case BGP_MULTICAST_VPN_ROUTE_TYPE_SHARED_TREE_JOIN: /* fall through */        case BGP_MULTICAST_VPN_ROUTE_TYPE_SOURCE_TREE_JOIN:            TCHECK2(pptr[0], BGP_VPN_RD_LEN);            offset = strlen(buf);            snprintf(buf + offset, buflen - offset, ", RD: %s, Source-AS %u",                     bgp_vpn_rd_print(pptr),                     EXTRACT_32BITS(pptr + BGP_VPN_RD_LEN));            pptr += BGP_VPN_RD_LEN;            bgp_vpn_sg_print(pptr, buf, buflen);            break;            /*             * no per route-type printing yet.             */        case BGP_MULTICAST_VPN_ROUTE_TYPE_INTRA_AS_SEG_LEAF:        default:            break;        }        return route_length + 2;trunc:	return -2;}/* * As I remember, some versions of systems have an snprintf() that * returns -1 if the buffer would have overflowed.  If the return * value is negative, set buflen to 0, to indicate that we've filled * the buffer up. * * If the return value is greater than buflen, that means that * the buffer would have overflowed; again, set buflen to 0 in * that case. */#define UPDATE_BUF_BUFLEN(buf, buflen, strlen) \    if (strlen<0) \       	buflen=0; \    else if ((u_int)strlen>buflen) \        buflen=0; \    else { \        buflen-=strlen; \	buf+=strlen; \    }static intdecode_labeled_vpn_l2(const u_char *pptr, char *buf, u_int buflen){        int plen,tlen,strlen,tlv_type,tlv_len,ttlv_len;	TCHECK2(pptr[0], 2);        plen=EXTRACT_16BITS(pptr);        tlen=plen;        pptr+=2;	TCHECK2(pptr[0],15);	buf[0]='\0';        strlen=snprintf(buf, buflen, "RD: %s, CE-ID: %u, Label-Block Offset: %u, Label Base %u",                        bgp_vpn_rd_print(pptr),                        EXTRACT_16BITS(pptr+8),                        EXTRACT_16BITS(pptr+10),                        EXTRACT_24BITS(pptr+12)>>4); /* the label is offsetted by 4 bits so lets shift it right */        UPDATE_BUF_BUFLEN(buf, buflen, strlen);        pptr+=15;        tlen-=15;        /* ok now the variable part - lets read out TLVs*/        while (tlen>0) {            if (tlen < 3)                return -1;            TCHECK2(pptr[0], 3);            tlv_type=*pptr++;            tlv_len=EXTRACT_16BITS(pptr);            ttlv_len=tlv_len;            pptr+=2;            switch(tlv_type) {            case 1:                if (buflen!=0) {                    strlen=snprintf(buf,buflen, "\n\t\tcircuit status vector (%u) length: %u: 0x",                                    tlv_type,                                    tlv_len);                    UPDATE_BUF_BUFLEN(buf, buflen, strlen);                }                ttlv_len=ttlv_len/8+1; /* how many bytes do we need to read ? */                while (ttlv_len>0) {                    TCHECK(pptr[0]);                    if (buflen!=0) {                        strlen=snprintf(buf,buflen, "%02x",*pptr++);                        UPDATE_BUF_BUFLEN(buf, buflen, strlen);                    }                    ttlv_len--;                }                break;            default:                if (buflen!=0) {                    strlen=snprintf(buf,buflen, "\n\t\tunknown TLV #%u, length: %u",                                    tlv_type,                                    tlv_len);                    UPDATE_BUF_BUFLEN(buf, buflen, strlen);                }                break;            }            tlen-=(tlv_len<<3); /* the tlv-length is expressed in bits so lets shift it right */        }        return plen+2;trunc:        return -2;}#ifdef INET6intdecode_prefix6(const u_char *pd, char *buf, u_int buflen){	struct in6_addr addr;	u_int plen;	TCHECK(pd[0]);	plen = pd[0];	if (128 < plen)		return -1;	memset(&addr, 0, sizeof(addr));	TCHECK2(pd[1], (plen + 7) / 8);	memcpy(&addr, &pd[1], (plen + 7) / 8);	if (plen % 8) {		addr.s6_addr[(plen + 7) / 8 - 1] &=			((0xff00 >> (plen % 8)) & 0xff);	}	snprintf(buf, buflen, "%s/%d", getname6((u_char *)&addr), plen);	return 1 + (plen + 7) / 8;trunc:	return -2;}static intdecode_labeled_prefix6(const u_char *pptr, char *buf, u_int buflen){	struct in6_addr addr;	u_int plen;	TCHECK(pptr[0]);	plen = pptr[0]; /* get prefix length */	if (24 > plen)		return -1;        plen-=24; /* adjust prefixlen - labellength */	if (128 < plen)		return -1;	memset(&addr, 0, sizeof(addr));	TCHECK2(pptr[4], (plen + 7) / 8);	memcpy(&addr, &pptr[4], (plen + 7) / 8);	if (plen % 8) {		addr.s6_addr[(plen + 7) / 8 - 1] &=			((0xff00 >> (plen % 8)) & 0xff);	}        /* the label may get offsetted by 4 bits so lets shift it right */	snprintf(buf, buflen, "%s/%d, label:%u %s",                 getname6((u_char *)&addr),                 plen,                 EXTRACT_24BITS(pptr+1)>>4,                 ((pptr[3]&1)==0) ? "(BOGUS: Bottom of Stack NOT set!)" : "(bottom)" );	return 4 + (plen + 7) / 8;trunc:	return -2;}static intdecode_labeled_vpn_prefix6(const u_char *pptr, char *buf, u_int buflen){	struct in6_addr addr;	u_int plen;	TCHECK(pptr[0]);	plen = pptr[0];   /* get prefix length */	if ((24+64) > plen)		return -1;        plen-=(24+64); /* adjust prefixlen - labellength - RD len*/	if (128 < plen)		return -1;	memset(&addr, 0, sizeof(addr));	TCHECK2(pptr[12], (plen + 7) / 8);	memcpy(&addr, &pptr[12], (plen + 7) / 8);	if (plen % 8) {		addr.s6_addr[(plen + 7) / 8 - 1] &=			((0xff00 >> (plen % 8)) & 0xff);	}        /* the label may get offsetted by 4 bits so lets shift it right */	snprintf(buf, buflen, "RD: %s, %s/%d, label:%u %s",                 bgp_vpn_rd_print(pptr+4),                 getname6((u_char *)&addr),                 plen,                 EXTRACT_24BITS(pptr+1)>>4,                 ((pptr[3]&1)==0) ? "(BOGUS: Bottom of Stack NOT set!)" : "(bottom)" );	return 12 + (plen + 7) / 8;trunc:	return -2;}#endifstatic intdecode_clnp_prefix(const u_char *pptr, char *buf, u_int buflen){        u_int8_t addr[19];	u_int plen;	TCHECK(pptr[0]);	plen = pptr[0]; /* get prefix length */	if (152 < plen)		return -1;	memset(&addr, 0, sizeof(addr));	TCHECK2(pptr[4], (plen + 7) / 8);	memcpy(&addr, &pptr[4], (plen + 7) / 8);	if (plen % 8) {		addr[(plen + 7) / 8 - 1] &=			((0xff00 >> (plen % 8)) & 0xff);	}	snprintf(buf, buflen, "%s/%d",                 isonsap_string(addr,(plen + 7) / 8),                 plen);	return 1 + (plen + 7) / 8;trunc:	return -2;}static intdecode_labeled_vpn_clnp_prefix(const u_char *pptr, char *buf, u_int buflen){        u_int8_t addr[19];	u_int plen;	TCHECK(pptr[0]);	plen = pptr[0];   /* get prefix length */	if ((24+64) > plen)		return -1;        plen-=(24+64); /* adjust prefixlen - labellength - RD len*/

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?