u_int juniper_services_print(const struct pcap_pkthdr *h, register const u_char *p) { struct juniper_l2info_t l2info; struct juniper_services_header { u_int8_t svc_id; u_int8_t flags_len; u_int8_t svc_set_id[2]; u_int8_t dir_iif[4]; }; const struct juniper_services_header *sh; l2info.pictype = DLT_JUNIPER_SERVICES; if(juniper_parse_header(p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; sh = (struct juniper_services_header *)p; if (eflag) printf("service-id %u flags 0x%02x service-set-id 0x%04x iif %u: ", sh->svc_id, sh->flags_len, EXTRACT_16BITS(&sh->svc_set_id), EXTRACT_24BITS(&sh->dir_iif[1])); ip_heuristic_guess(p, l2info.length); return l2info.header_len; }
u_int juniper_services_print(const struct pcap_pkthdr *h, packetbody_t p) { struct juniper_l2info_t l2info; struct juniper_services_header { u_int8_t svc_id; u_int8_t flags_len; u_int8_t svc_set_id[2]; u_int8_t dir_iif[4]; }; __capability const struct juniper_services_header *sh; l2info.pictype = DLT_JUNIPER_SERVICES; if(juniper_parse_header(p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; sh = (__capability const struct juniper_services_header *)p; if (eflag) printf("service-id %u flags 0x%02x service-set-id 0x%04x iif %u: ", sh->svc_id, sh->flags_len, EXTRACT_16BITS(&sh->svc_set_id), EXTRACT_24BITS(&sh->dir_iif[1])); /* no proto field - lets guess by first byte of IP header*/ ip_heuristic_guess(p, l2info.length); return l2info.header_len; }
u_int juniper_monitor_print(const struct pcap_pkthdr *h, register const u_char *p) { struct juniper_l2info_t l2info; struct juniper_monitor_header { u_int8_t pkt_type; u_int8_t padding; u_int8_t iif[2]; u_int8_t service_id[4]; }; const struct juniper_monitor_header *mh; l2info.pictype = DLT_JUNIPER_MONITOR; if(juniper_parse_header(p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; mh = (struct juniper_monitor_header *)p; if (eflag) printf("service-id %u, iif %u, pkt-type %u: ", EXTRACT_32BITS(&mh->service_id), EXTRACT_16BITS(&mh->iif), mh->pkt_type); ip_heuristic_guess(p, l2info.length); return l2info.header_len; }
u_int juniper_monitor_print(const struct pcap_pkthdr *h, packetbody_t p) { struct juniper_l2info_t l2info; struct juniper_monitor_header { u_int8_t pkt_type; u_int8_t padding; u_int8_t iif[2]; u_int8_t service_id[4]; }; __capability const struct juniper_monitor_header *mh; l2info.pictype = DLT_JUNIPER_MONITOR; if(juniper_parse_header(p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; mh = (__capability const struct juniper_monitor_header *)p; if (eflag) printf("service-id %u, iif %u, pkt-type %u: ", EXTRACT_32BITS(&mh->service_id), EXTRACT_16BITS(&mh->iif), mh->pkt_type); /* no proto field - lets guess by first byte of IP header*/ ip_heuristic_guess(p, l2info.length); return l2info.header_len; }
u_int juniper_services_print(netdissect_options *ndo, const struct pcap_pkthdr *h, register const u_char *p) { struct juniper_l2info_t l2info; struct juniper_services_header { uint8_t svc_id; uint8_t flags_len; uint8_t svc_set_id[2]; uint8_t dir_iif[4]; }; const struct juniper_services_header *sh; l2info.pictype = DLT_JUNIPER_SERVICES; if (juniper_parse_header(ndo, p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; sh = (struct juniper_services_header *)p; if (ndo->ndo_eflag) ND_PRINT((ndo, "service-id %u flags 0x%02x service-set-id 0x%04x iif %u: ", sh->svc_id, sh->flags_len, EXTRACT_16BITS(&sh->svc_set_id), EXTRACT_24BITS(&sh->dir_iif[1]))); /* no proto field - lets guess by first byte of IP header*/ ip_heuristic_guess (ndo, p, l2info.length); return l2info.header_len; }
u_int juniper_monitor_print(netdissect_options *ndo, const struct pcap_pkthdr *h, register const u_char *p) { struct juniper_l2info_t l2info; struct juniper_monitor_header { uint8_t pkt_type; uint8_t padding; uint8_t iif[2]; uint8_t service_id[4]; }; const struct juniper_monitor_header *mh; l2info.pictype = DLT_JUNIPER_MONITOR; if (juniper_parse_header(ndo, p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; mh = (struct juniper_monitor_header *)p; if (ndo->ndo_eflag) ND_PRINT((ndo, "service-id %u, iif %u, pkt-type %u: ", EXTRACT_32BITS(&mh->service_id), EXTRACT_16BITS(&mh->iif), mh->pkt_type)); /* no proto field - lets guess by first byte of IP header*/ ip_heuristic_guess (ndo, p, l2info.length); return l2info.header_len; }
u_int juniper_atm2_print(netdissect_options *ndo, const struct pcap_pkthdr *h, register const u_char *p) { uint16_t extracted_ethertype; struct juniper_l2info_t l2info; l2info.pictype = DLT_JUNIPER_ATM2; if (juniper_parse_header(ndo, p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; if (l2info.cookie[7] & ATM2_PKT_TYPE_MASK) { /* OAM cell ? */ oam_print(ndo, p, l2info.length, ATM_OAM_NOHEC); return l2info.header_len; } if (EXTRACT_24BITS(p) == 0xfefe03 || /* NLPID encaps ? */ EXTRACT_24BITS(p) == 0xaaaa03) { /* SNAP encaps ? */ if (llc_print(ndo, p, l2info.length, l2info.caplen, NULL, NULL, &extracted_ethertype) != 0) return l2info.header_len; } if (l2info.direction != JUNIPER_BPF_PKT_IN && /* ether-over-1483 encaps ? */ (EXTRACT_32BITS(l2info.cookie) & ATM2_GAP_COUNT_MASK)) { ether_print(ndo, p, l2info.length, l2info.caplen, NULL, NULL); return l2info.header_len; } if (p[0] == 0x03) { /* Cisco style NLPID encaps ? */ isoclns_print(ndo, p + 1, l2info.length - 1, l2info.caplen - 1); /* FIXME check if frame was recognized */ return l2info.header_len; } if(juniper_ppp_heuristic_guess(ndo, p, l2info.length) != 0) /* PPPoA vcmux encaps ? */ return l2info.header_len; if (ip_heuristic_guess(ndo, p, l2info.length) != 0) /* last try - vcmux encaps ? */ return l2info.header_len; return l2info.header_len; }
u_int juniper_atm2_print(const struct pcap_pkthdr *h, register const u_char *p) { u_int16_t extracted_ethertype; struct juniper_l2info_t l2info; l2info.pictype = DLT_JUNIPER_ATM2; if(juniper_parse_header(p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; if (l2info.cookie[7] & ATM2_PKT_TYPE_MASK) { oam_print(p,l2info.length,ATM_OAM_NOHEC); return l2info.header_len; } if (EXTRACT_24BITS(p) == 0xfefe03 || EXTRACT_24BITS(p) == 0xaaaa03) { if (llc_print(p, l2info.length, l2info.caplen, NULL, NULL, &extracted_ethertype) != 0) return l2info.header_len; } if (l2info.direction != JUNIPER_BPF_PKT_IN && (EXTRACT_32BITS(l2info.cookie) & ATM2_GAP_COUNT_MASK)) { ether_print(p, l2info.length, l2info.caplen); return l2info.header_len; } if (p[0] == 0x03) { isoclns_print(p + 1, l2info.length - 1, l2info.caplen - 1); return l2info.header_len; } if(juniper_ppp_heuristic_guess(p, l2info.length) != 0) return l2info.header_len; if(ip_heuristic_guess(p, l2info.length) != 0) return l2info.header_len; return l2info.header_len; }
u_int juniper_atm1_print(const struct pcap_pkthdr *h, register const u_char *p) { u_int16_t extracted_ethertype; struct juniper_l2info_t l2info; l2info.pictype = DLT_JUNIPER_ATM1; if(juniper_parse_header(p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; if (l2info.cookie[0] == 0x80) { oam_print(p,l2info.length,ATM_OAM_NOHEC); return l2info.header_len; } if (EXTRACT_24BITS(p) == 0xfefe03 || EXTRACT_24BITS(p) == 0xaaaa03) { if (llc_print(p, l2info.length, l2info.caplen, NULL, NULL, &extracted_ethertype) != 0) return l2info.header_len; } if (p[0] == 0x03) { isoclns_print(p + 1, l2info.length - 1, l2info.caplen - 1); return l2info.header_len; } if(ip_heuristic_guess(p, l2info.length) != 0) return l2info.header_len; return l2info.header_len; }
u_int juniper_atm1_print(const struct pcap_pkthdr *h, register const u_char *p) { u_int16_t extracted_ethertype; struct juniper_l2info_t l2info; l2info.pictype = DLT_JUNIPER_ATM1; if(juniper_parse_header(p, h, &l2info) == 0) return l2info.header_len; p+=l2info.header_len; if (l2info.cookie[0] == 0x80) { /* OAM cell ? */ oam_print(p,l2info.length,ATM_OAM_NOHEC); return l2info.header_len; } if (EXTRACT_24BITS(p) == 0xfefe03 || /* NLPID encaps ? */ EXTRACT_24BITS(p) == 0xaaaa03) { /* SNAP encaps ? */ if (llc_print(p, l2info.length, l2info.caplen, NULL, NULL, &extracted_ethertype) != 0) return l2info.header_len; } if (p[0] == 0x03) { /* Cisco style NLPID encaps ? */ isoclns_print(p + 1, l2info.length - 1, l2info.caplen - 1); /* FIXME check if frame was recognized */ return l2info.header_len; } if(ip_heuristic_guess(p, l2info.length) != 0) /* last try - vcmux encaps ? */ return l2info.header_len; return l2info.header_len; }
static int juniper_parse_header (const u_char *p, const struct pcap_pkthdr *h, struct juniper_l2info_t *l2info) { struct juniper_cookie_table_t *lp = juniper_cookie_table; u_int idx, offset; #ifdef DLT_JUNIPER_ATM2 u_int32_t control_word; #endif l2info->header_len = 0; l2info->cookie_len = 0; l2info->proto = 0; l2info->length = h->len; l2info->caplen = h->caplen; l2info->direction = p[3]&JUNIPER_BPF_PKT_IN; TCHECK2(p[0],4); if (EXTRACT_24BITS(p) != JUNIPER_MGC_NUMBER) { printf("no magic-number found!"); return 0; } if (eflag) printf("%3s ",tok2str(juniper_direction_values,"---",l2info->direction)); if ((p[3] & JUNIPER_BPF_EXT ) == JUNIPER_BPF_EXT ) { offset = 6 + EXTRACT_16BITS(p+4); if (eflag>1) printf("ext-len %u, ",EXTRACT_16BITS(p+4)); } else offset = 4; if ((p[3] & JUNIPER_BPF_NO_L2 ) == JUNIPER_BPF_NO_L2 ) { if (eflag) printf("no-L2-hdr, "); TCHECK2(p[offset+4],1); if(ip_heuristic_guess(p+offset+4,l2info->length-(offset+4)) == 0) printf("no IP-hdr found!"); l2info->header_len=offset+4; return 0; } l2info->header_len = offset; p+=l2info->header_len; l2info->length -= l2info->header_len; l2info->caplen -= l2info->header_len; while (lp->s != NULL) { if (lp->pictype == l2info->pictype) { l2info->cookie_len += lp->cookie_len; switch (p[0]) { case LS_COOKIE_ID: l2info->cookie_type = LS_COOKIE_ID; l2info->cookie_len += 2; break; case AS_COOKIE_ID: l2info->cookie_type = AS_COOKIE_ID; l2info->cookie_len = 8; break; default: l2info->bundle = l2info->cookie[0]; break; } #ifdef DLT_JUNIPER_MFR if (l2info->pictype == DLT_JUNIPER_MFR && (p[0] & MFR_BE_MASK) == MFR_BE_MASK) { l2info->cookie_len = 0; } #endif l2info->header_len += l2info->cookie_len; l2info->length -= l2info->cookie_len; l2info->caplen -= l2info->cookie_len; if (eflag) printf("%s-PIC, cookie-len %u", lp->s, l2info->cookie_len); if (l2info->cookie_len > 0) { TCHECK2(p[0],l2info->cookie_len); if (eflag) printf(", cookie 0x"); for (idx = 0; idx < l2info->cookie_len; idx++) { l2info->cookie[idx] = p[idx]; if (eflag) printf("%02x",p[idx]); } } if (eflag) printf(": "); l2info->proto = EXTRACT_16BITS(p+l2info->cookie_len); break; } ++lp; } p+=l2info->cookie_len; switch(l2info->pictype) { #ifdef DLT_JUNIPER_MLPPP case DLT_JUNIPER_MLPPP: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(&l2info->cookie[6])>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; break; } break; #endif #ifdef DLT_JUNIPER_MLFR case DLT_JUNIPER_MLFR: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; l2info->proto = EXTRACT_16BITS(p); l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(&l2info->cookie[6])>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; } break; #endif #ifdef DLT_JUNIPER_MFR case DLT_JUNIPER_MFR: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; l2info->proto = EXTRACT_16BITS(p); l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(&l2info->cookie[6])>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; break; } break; #endif #ifdef DLT_JUNIPER_ATM2 case DLT_JUNIPER_ATM2: TCHECK2(p[0],4); if (l2info->cookie[7] & ATM2_PKT_TYPE_MASK) { control_word = EXTRACT_32BITS(p); switch(control_word) { case 0: case 0x08000000: case 0x08380000: l2info->header_len += 4; break; default: break; } if (eflag) printf("control-word 0x%08x ", control_word); } break; #endif #ifdef DLT_JUNIPER_ATM1 case DLT_JUNIPER_ATM1: break; #endif #ifdef DLT_JUNIPER_PPP case DLT_JUNIPER_PPP: break; #endif #ifdef DLT_JUNIPER_CHDLC case DLT_JUNIPER_CHDLC: break; #endif #ifdef DLT_JUNIPER_ETHER case DLT_JUNIPER_ETHER: break; #endif #ifdef DLT_JUNIPER_FRELAY case DLT_JUNIPER_FRELAY: break; #endif default: printf("Unknown Juniper DLT_ type %u: ", l2info->pictype); break; } if (eflag > 1) printf("hlen %u, proto 0x%04x, ",l2info->header_len,l2info->proto); return 1; trunc: printf("[|juniper_hdr], length %u",h->len); return 0; }
static int juniper_parse_header (const u_char *p, const struct pcap_pkthdr *h, struct juniper_l2info_t *l2info) { struct juniper_cookie_table_t *lp = juniper_cookie_table; u_int idx, offset; #ifdef DLT_JUNIPER_ATM2 u_int32_t control_word; #endif l2info->header_len = 0; l2info->cookie_len = 0; l2info->proto = 0; l2info->length = h->len; l2info->caplen = h->caplen; l2info->direction = p[3]&JUNIPER_BPF_PKT_IN; TCHECK2(p[0],4); if (EXTRACT_24BITS(p) != JUNIPER_MGC_NUMBER) { /* magic number found ? */ printf("no magic-number found!"); return 0; } if (eflag) /* print direction */ printf("%3s ",tok2str(juniper_direction_values,"---",l2info->direction)); /* extensions present ? - calculate how much bytes to skip */ if ((p[3] & JUNIPER_BPF_EXT ) == JUNIPER_BPF_EXT ) { offset = 6 + EXTRACT_16BITS(p+4); if (eflag>1) printf("ext-len %u, ",EXTRACT_16BITS(p+4)); } else offset = 4; if ((p[3] & JUNIPER_BPF_NO_L2 ) == JUNIPER_BPF_NO_L2 ) { if (eflag) printf("no-L2-hdr, "); /* there is no link-layer present - * perform the v4/v6 heuristics * to figure out what it is */ TCHECK2(p[offset+4],1); if(ip_heuristic_guess(p+offset+4,l2info->length-(offset+4)) == 0) printf("no IP-hdr found!"); l2info->header_len=offset+4; return 0; /* stop parsing the output further */ } l2info->header_len = offset; p+=l2info->header_len; l2info->length -= l2info->header_len; l2info->caplen -= l2info->header_len; /* search through the cookie table and copy values matching for our PIC type */ while (lp->s != NULL) { if (lp->pictype == l2info->pictype) { l2info->cookie_len += lp->cookie_len; switch (p[0]) { case LS_COOKIE_ID: l2info->cookie_type = LS_COOKIE_ID; l2info->cookie_len += 2; break; case AS_COOKIE_ID: l2info->cookie_type = AS_COOKIE_ID; l2info->cookie_len = 8; break; default: l2info->bundle = l2info->cookie[0]; break; } #ifdef DLT_JUNIPER_MFR /* MFR child links don't carry cookies */ if (l2info->pictype == DLT_JUNIPER_MFR && (p[0] & MFR_BE_MASK) == MFR_BE_MASK) { l2info->cookie_len = 0; } #endif l2info->header_len += l2info->cookie_len; l2info->length -= l2info->cookie_len; l2info->caplen -= l2info->cookie_len; if (eflag) printf("%s-PIC, cookie-len %u", lp->s, l2info->cookie_len); if (l2info->cookie_len > 0) { TCHECK2(p[0],l2info->cookie_len); if (eflag) printf(", cookie 0x"); for (idx = 0; idx < l2info->cookie_len; idx++) { l2info->cookie[idx] = p[idx]; /* copy cookie data */ if (eflag) printf("%02x",p[idx]); } } if (eflag) printf(": "); /* print demarc b/w L2/L3*/ l2info->proto = EXTRACT_16BITS(p+l2info->cookie_len); break; } ++lp; } p+=l2info->cookie_len; /* DLT_ specific parsing */ switch(l2info->pictype) { #ifdef DLT_JUNIPER_MLPPP case DLT_JUNIPER_MLPPP: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(&l2info->cookie[6])>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; break; } break; #endif #ifdef DLT_JUNIPER_MLFR case DLT_JUNIPER_MLFR: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; l2info->proto = EXTRACT_16BITS(p); l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(&l2info->cookie[6])>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; } break; #endif #ifdef DLT_JUNIPER_MFR case DLT_JUNIPER_MFR: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; l2info->proto = EXTRACT_16BITS(p); l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(&l2info->cookie[6])>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; break; } break; #endif #ifdef DLT_JUNIPER_ATM2 case DLT_JUNIPER_ATM2: TCHECK2(p[0],4); /* ATM cell relay control word present ? */ if (l2info->cookie[7] & ATM2_PKT_TYPE_MASK) { control_word = EXTRACT_32BITS(p); /* some control word heuristics */ switch(control_word) { case 0: /* zero control word */ case 0x08000000: /* < JUNOS 7.4 control-word */ case 0x08380000: /* cntl word plus cell length (56) >= JUNOS 7.4*/ l2info->header_len += 4; break; default: break; } if (eflag) printf("control-word 0x%08x ", control_word); } break; #endif #ifdef DLT_JUNIPER_ATM1 case DLT_JUNIPER_ATM1: break; #endif #ifdef DLT_JUNIPER_PPP case DLT_JUNIPER_PPP: break; #endif #ifdef DLT_JUNIPER_CHDLC case DLT_JUNIPER_CHDLC: break; #endif #ifdef DLT_JUNIPER_ETHER case DLT_JUNIPER_ETHER: break; #endif #ifdef DLT_JUNIPER_FRELAY case DLT_JUNIPER_FRELAY: break; #endif default: printf("Unknown Juniper DLT_ type %u: ", l2info->pictype); break; } if (eflag > 1) printf("hlen %u, proto 0x%04x, ",l2info->header_len,l2info->proto); return 1; /* everything went ok so far. continue parsing */ trunc: printf("[|juniper_hdr], length %u",h->len); return 0; }
static int juniper_parse_header (packetbody_t p, const struct pcap_pkthdr *h, struct juniper_l2info_t *l2info) { struct juniper_cookie_table_t *lp = juniper_cookie_table; u_int idx, jnx_ext_len, jnx_header_len = 0; u_int8_t tlv_type,tlv_len; u_int32_t control_word; int tlv_value; packetbody_t tptr; l2info->header_len = 0; l2info->cookie_len = 0; l2info->proto = 0; l2info->length = h->len; l2info->caplen = h->caplen; PACKET_HAS_SPACE_OR_TRUNC(p,4); l2info->flags = p[3]; l2info->direction = p[3]&JUNIPER_BPF_PKT_IN; if (EXTRACT_24BITS(p) != JUNIPER_MGC_NUMBER) { /* magic number found ? */ printf("no magic-number found!"); return 0; } if (eflag) /* print direction */ printf("%3s ",tok2str(juniper_direction_values,"---",l2info->direction)); /* magic number + flags */ jnx_header_len = 4; if (vflag>1) printf("\n\tJuniper PCAP Flags [%s]", bittok2str(jnx_flag_values, "none", l2info->flags)); /* extensions present ? - calculate how much bytes to skip */ if ((l2info->flags & JUNIPER_BPF_EXT ) == JUNIPER_BPF_EXT ) { tptr = p+jnx_header_len; /* ok to read extension length ? */ PACKET_HAS_SPACE_OR_TRUNC(tptr, 2); jnx_ext_len = EXTRACT_16BITS(tptr); jnx_header_len += 2; tptr +=2; /* nail up the total length - * just in case something goes wrong * with TLV parsing */ jnx_header_len += jnx_ext_len; if (vflag>1) printf(", PCAP Extension(s) total length %u", jnx_ext_len); PACKET_HAS_SPACE_OR_TRUNC(tptr, jnx_ext_len); while (jnx_ext_len > JUNIPER_EXT_TLV_OVERHEAD) { tlv_type = *(tptr++); tlv_len = *(tptr++); tlv_value = 0; /* sanity check */ if (tlv_type == 0 || tlv_len == 0) break; if (vflag>1) printf("\n\t %s Extension TLV #%u, length %u, value ", tok2str(jnx_ext_tlv_values,"Unknown",tlv_type), tlv_type, tlv_len); tlv_value = juniper_read_tlv_value(tptr, tlv_type, tlv_len); switch (tlv_type) { case JUNIPER_EXT_TLV_IFD_NAME: /* FIXME */ break; case JUNIPER_EXT_TLV_IFD_MEDIATYPE: case JUNIPER_EXT_TLV_TTP_IFD_MEDIATYPE: if (tlv_value != -1) { if (vflag>1) printf("%s (%u)", tok2str(juniper_ifmt_values, "Unknown", tlv_value), tlv_value); } break; case JUNIPER_EXT_TLV_IFL_ENCAPS: case JUNIPER_EXT_TLV_TTP_IFL_ENCAPS: if (tlv_value != -1) { if (vflag>1) printf("%s (%u)", tok2str(juniper_ifle_values, "Unknown", tlv_value), tlv_value); } break; case JUNIPER_EXT_TLV_IFL_IDX: /* fall through */ case JUNIPER_EXT_TLV_IFL_UNIT: case JUNIPER_EXT_TLV_IFD_IDX: default: if (tlv_value != -1) { if (vflag>1) printf("%u",tlv_value); } break; } tptr+=tlv_len; jnx_ext_len -= tlv_len+JUNIPER_EXT_TLV_OVERHEAD; } if (vflag>1) printf("\n\t-----original packet-----\n\t"); } if ((l2info->flags & JUNIPER_BPF_NO_L2 ) == JUNIPER_BPF_NO_L2 ) { if (eflag) printf("no-L2-hdr, "); /* there is no link-layer present - * perform the v4/v6 heuristics * to figure out what it is */ PACKET_HAS_SPACE_OR_TRUNC(p, (jnx_header_len+4) + 1); if(ip_heuristic_guess(p+jnx_header_len+4,l2info->length-(jnx_header_len+4)) == 0) printf("no IP-hdr found!"); l2info->header_len=jnx_header_len+4; return 0; /* stop parsing the output further */ } l2info->header_len = jnx_header_len; p+=l2info->header_len; l2info->length -= l2info->header_len; l2info->caplen -= l2info->header_len; /* search through the cookie table and copy values matching for our PIC type */ while (lp->s != NULL) { if (lp->pictype == l2info->pictype) { l2info->cookie_len += lp->cookie_len; switch (p[0]) { case LS_COOKIE_ID: l2info->cookie_type = LS_COOKIE_ID; l2info->cookie_len += 2; break; case AS_COOKIE_ID: l2info->cookie_type = AS_COOKIE_ID; l2info->cookie_len = 8; break; default: l2info->bundle = l2info->cookie[0]; break; } #ifdef DLT_JUNIPER_MFR /* MFR child links don't carry cookies */ if (l2info->pictype == DLT_JUNIPER_MFR && (p[0] & MFR_BE_MASK) == MFR_BE_MASK) { l2info->cookie_len = 0; } #endif l2info->header_len += l2info->cookie_len; l2info->length -= l2info->cookie_len; l2info->caplen -= l2info->cookie_len; if (eflag) printf("%s-PIC, cookie-len %u", lp->s, l2info->cookie_len); if (l2info->cookie_len > 0) { PACKET_HAS_SPACE_OR_TRUNC(p,l2info->cookie_len); if (eflag) printf(", cookie 0x"); for (idx = 0; idx < l2info->cookie_len; idx++) { l2info->cookie[idx] = p[idx]; /* copy cookie data */ if (eflag) printf("%02x",p[idx]); } } if (eflag) printf(": "); /* print demarc b/w L2/L3*/ l2info->proto = EXTRACT_16BITS(p+l2info->cookie_len); break; } ++lp; } p+=l2info->cookie_len; /* DLT_ specific parsing */ switch(l2info->pictype) { #ifdef DLT_JUNIPER_MLPPP case DLT_JUNIPER_MLPPP: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(cheri_ptr(&l2info->cookie[6], 2))>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; break; } break; #endif #ifdef DLT_JUNIPER_MLFR case DLT_JUNIPER_MLFR: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; l2info->proto = EXTRACT_16BITS(p); l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(cheri_ptr(&l2info->cookie[6], 2))>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; } break; #endif #ifdef DLT_JUNIPER_MFR case DLT_JUNIPER_MFR: switch (l2info->cookie_type) { case LS_COOKIE_ID: l2info->bundle = l2info->cookie[1]; l2info->proto = EXTRACT_16BITS(p); l2info->header_len += 2; l2info->length -= 2; l2info->caplen -= 2; break; case AS_COOKIE_ID: l2info->bundle = (EXTRACT_16BITS(cheri_ptr(&l2info->cookie[6], 2))>>3)&0xfff; l2info->proto = (l2info->cookie[5])&JUNIPER_LSQ_L3_PROTO_MASK; break; default: l2info->bundle = l2info->cookie[0]; break; } break; #endif #ifdef DLT_JUNIPER_ATM2 case DLT_JUNIPER_ATM2: PACKET_HAS_SPACE_OR_TRUNC(p,4); /* ATM cell relay control word present ? */ if (l2info->cookie[7] & ATM2_PKT_TYPE_MASK) { control_word = EXTRACT_32BITS(p); /* some control word heuristics */ switch(control_word) { case 0: /* zero control word */ case 0x08000000: /* < JUNOS 7.4 control-word */ case 0x08380000: /* cntl word plus cell length (56) >= JUNOS 7.4*/ l2info->header_len += 4; break; default: break; } if (eflag) printf("control-word 0x%08x ", control_word); } break; #endif #ifdef DLT_JUNIPER_GGSN case DLT_JUNIPER_GGSN: break; #endif #ifdef DLT_JUNIPER_ATM1 case DLT_JUNIPER_ATM1: break; #endif #ifdef DLT_JUNIPER_PPP case DLT_JUNIPER_PPP: break; #endif #ifdef DLT_JUNIPER_CHDLC case DLT_JUNIPER_CHDLC: break; #endif #ifdef DLT_JUNIPER_ETHER case DLT_JUNIPER_ETHER: break; #endif #ifdef DLT_JUNIPER_FRELAY case DLT_JUNIPER_FRELAY: break; #endif default: printf("Unknown Juniper DLT_ type %u: ", l2info->pictype); break; } if (eflag > 1) printf("hlen %u, proto 0x%04x, ",l2info->header_len,l2info->proto); return 1; /* everything went ok so far. continue parsing */ trunc: printf("[|juniper_hdr], length %u",h->len); return 0; }