Home | History | Annotate | Download | only in tcpdump
      1 /*
      2  * Redistribution and use in source and binary forms, with or without
      3  * modification, are permitted provided that: (1) source code
      4  * distributions retain the above copyright notice and this paragraph
      5  * in its entirety, and (2) distributions including binary code include
      6  * the above copyright notice and this paragraph in its entirety in
      7  * the documentation or other materials provided with the distribution.
      8  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND
      9  * WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, WITHOUT
     10  * LIMITATION, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
     11  * FOR A PARTICULAR PURPOSE.
     12  *
     13  * Original code by Andy Heffernan (ahh (at) juniper.net)
     14  */
     15 
     16 /* \summary: Pragmatic General Multicast (PGM) printer */
     17 
     18 #ifdef HAVE_CONFIG_H
     19 #include "config.h"
     20 #endif
     21 
     22 #include <netdissect-stdinc.h>
     23 
     24 #include "netdissect.h"
     25 #include "extract.h"
     26 #include "addrtoname.h"
     27 #include "addrtostr.h"
     28 
     29 #include "ip.h"
     30 #include "ip6.h"
     31 #include "ipproto.h"
     32 #include "af.h"
     33 
     34 /*
     35  * PGM header (RFC 3208)
     36  */
     37 struct pgm_header {
     38     uint16_t	pgm_sport;
     39     uint16_t	pgm_dport;
     40     uint8_t	pgm_type;
     41     uint8_t	pgm_options;
     42     uint16_t	pgm_sum;
     43     uint8_t	pgm_gsid[6];
     44     uint16_t	pgm_length;
     45 };
     46 
     47 struct pgm_spm {
     48     uint32_t	pgms_seq;
     49     uint32_t	pgms_trailseq;
     50     uint32_t	pgms_leadseq;
     51     uint16_t	pgms_nla_afi;
     52     uint16_t	pgms_reserved;
     53     /* ... uint8_t	pgms_nla[0]; */
     54     /* ... options */
     55 };
     56 
     57 struct pgm_nak {
     58     uint32_t	pgmn_seq;
     59     uint16_t	pgmn_source_afi;
     60     uint16_t	pgmn_reserved;
     61     /* ... uint8_t	pgmn_source[0]; */
     62     /* ... uint16_t	pgmn_group_afi */
     63     /* ... uint16_t	pgmn_reserved2; */
     64     /* ... uint8_t	pgmn_group[0]; */
     65     /* ... options */
     66 };
     67 
     68 struct pgm_ack {
     69     uint32_t	pgma_rx_max_seq;
     70     uint32_t	pgma_bitmap;
     71     /* ... options */
     72 };
     73 
     74 struct pgm_poll {
     75     uint32_t	pgmp_seq;
     76     uint16_t	pgmp_round;
     77     uint16_t	pgmp_reserved;
     78     /* ... options */
     79 };
     80 
     81 struct pgm_polr {
     82     uint32_t	pgmp_seq;
     83     uint16_t	pgmp_round;
     84     uint16_t	pgmp_subtype;
     85     uint16_t	pgmp_nla_afi;
     86     uint16_t	pgmp_reserved;
     87     /* ... uint8_t	pgmp_nla[0]; */
     88     /* ... options */
     89 };
     90 
     91 struct pgm_data {
     92     uint32_t	pgmd_seq;
     93     uint32_t	pgmd_trailseq;
     94     /* ... options */
     95 };
     96 
     97 typedef enum _pgm_type {
     98     PGM_SPM = 0,		/* source path message */
     99     PGM_POLL = 1,		/* POLL Request */
    100     PGM_POLR = 2,		/* POLL Response */
    101     PGM_ODATA = 4,		/* original data */
    102     PGM_RDATA = 5,		/* repair data */
    103     PGM_NAK = 8,		/* NAK */
    104     PGM_NULLNAK = 9,		/* Null NAK */
    105     PGM_NCF = 10,		/* NAK Confirmation */
    106     PGM_ACK = 11,		/* ACK for congestion control */
    107     PGM_SPMR = 12,		/* SPM request */
    108     PGM_MAX = 255
    109 } pgm_type;
    110 
    111 #define PGM_OPT_BIT_PRESENT	0x01
    112 #define PGM_OPT_BIT_NETWORK	0x02
    113 #define PGM_OPT_BIT_VAR_PKTLEN	0x40
    114 #define PGM_OPT_BIT_PARITY	0x80
    115 
    116 #define PGM_OPT_LENGTH		0x00
    117 #define PGM_OPT_FRAGMENT        0x01
    118 #define PGM_OPT_NAK_LIST        0x02
    119 #define PGM_OPT_JOIN            0x03
    120 #define PGM_OPT_NAK_BO_IVL	0x04
    121 #define PGM_OPT_NAK_BO_RNG	0x05
    122 
    123 #define PGM_OPT_REDIRECT        0x07
    124 #define PGM_OPT_PARITY_PRM      0x08
    125 #define PGM_OPT_PARITY_GRP      0x09
    126 #define PGM_OPT_CURR_TGSIZE     0x0A
    127 #define PGM_OPT_NBR_UNREACH	0x0B
    128 #define PGM_OPT_PATH_NLA	0x0C
    129 
    130 #define PGM_OPT_SYN             0x0D
    131 #define PGM_OPT_FIN             0x0E
    132 #define PGM_OPT_RST             0x0F
    133 #define PGM_OPT_CR		0x10
    134 #define PGM_OPT_CRQST		0x11
    135 
    136 #define PGM_OPT_PGMCC_DATA	0x12
    137 #define PGM_OPT_PGMCC_FEEDBACK	0x13
    138 
    139 #define PGM_OPT_MASK		0x7f
    140 
    141 #define PGM_OPT_END		0x80    /* end of options marker */
    142 
    143 #define PGM_MIN_OPT_LEN		4
    144 
    145 void
    146 pgm_print(netdissect_options *ndo,
    147           register const u_char *bp, register u_int length,
    148           register const u_char *bp2)
    149 {
    150 	register const struct pgm_header *pgm;
    151 	register const struct ip *ip;
    152 	register char ch;
    153 	uint16_t sport, dport;
    154 	u_int nla_afnum;
    155 	char nla_buf[INET6_ADDRSTRLEN];
    156 	register const struct ip6_hdr *ip6;
    157 	uint8_t opt_type, opt_len;
    158 	uint32_t seq, opts_len, len, offset;
    159 
    160 	pgm = (const struct pgm_header *)bp;
    161 	ip = (const struct ip *)bp2;
    162 	if (IP_V(ip) == 6)
    163 		ip6 = (const struct ip6_hdr *)bp2;
    164 	else
    165 		ip6 = NULL;
    166 	ch = '\0';
    167 	if (!ND_TTEST(pgm->pgm_dport)) {
    168 		if (ip6) {
    169 			ND_PRINT((ndo, "%s > %s: [|pgm]",
    170 				ip6addr_string(ndo, &ip6->ip6_src),
    171 				ip6addr_string(ndo, &ip6->ip6_dst)));
    172 		} else {
    173 			ND_PRINT((ndo, "%s > %s: [|pgm]",
    174 				ipaddr_string(ndo, &ip->ip_src),
    175 				ipaddr_string(ndo, &ip->ip_dst)));
    176 		}
    177 		return;
    178 	}
    179 
    180 	sport = EXTRACT_16BITS(&pgm->pgm_sport);
    181 	dport = EXTRACT_16BITS(&pgm->pgm_dport);
    182 
    183 	if (ip6) {
    184 		if (ip6->ip6_nxt == IPPROTO_PGM) {
    185 			ND_PRINT((ndo, "%s.%s > %s.%s: ",
    186 				ip6addr_string(ndo, &ip6->ip6_src),
    187 				tcpport_string(ndo, sport),
    188 				ip6addr_string(ndo, &ip6->ip6_dst),
    189 				tcpport_string(ndo, dport)));
    190 		} else {
    191 			ND_PRINT((ndo, "%s > %s: ",
    192 				tcpport_string(ndo, sport), tcpport_string(ndo, dport)));
    193 		}
    194 	} else {
    195 		if (ip->ip_p == IPPROTO_PGM) {
    196 			ND_PRINT((ndo, "%s.%s > %s.%s: ",
    197 				ipaddr_string(ndo, &ip->ip_src),
    198 				tcpport_string(ndo, sport),
    199 				ipaddr_string(ndo, &ip->ip_dst),
    200 				tcpport_string(ndo, dport)));
    201 		} else {
    202 			ND_PRINT((ndo, "%s > %s: ",
    203 				tcpport_string(ndo, sport), tcpport_string(ndo, dport)));
    204 		}
    205 	}
    206 
    207 	ND_TCHECK(*pgm);
    208 
    209         ND_PRINT((ndo, "PGM, length %u", EXTRACT_16BITS(&pgm->pgm_length)));
    210 
    211         if (!ndo->ndo_vflag)
    212             return;
    213 
    214 	ND_PRINT((ndo, " 0x%02x%02x%02x%02x%02x%02x ",
    215 		     pgm->pgm_gsid[0],
    216                      pgm->pgm_gsid[1],
    217                      pgm->pgm_gsid[2],
    218 		     pgm->pgm_gsid[3],
    219                      pgm->pgm_gsid[4],
    220                      pgm->pgm_gsid[5]));
    221 	switch (pgm->pgm_type) {
    222 	case PGM_SPM: {
    223 	    const struct pgm_spm *spm;
    224 
    225 	    spm = (const struct pgm_spm *)(pgm + 1);
    226 	    ND_TCHECK(*spm);
    227 	    bp = (const u_char *) (spm + 1);
    228 
    229 	    switch (EXTRACT_16BITS(&spm->pgms_nla_afi)) {
    230 	    case AFNUM_INET:
    231 		ND_TCHECK2(*bp, sizeof(struct in_addr));
    232 		addrtostr(bp, nla_buf, sizeof(nla_buf));
    233 		bp += sizeof(struct in_addr);
    234 		break;
    235 	    case AFNUM_INET6:
    236 		ND_TCHECK2(*bp, sizeof(struct in6_addr));
    237 		addrtostr6(bp, nla_buf, sizeof(nla_buf));
    238 		bp += sizeof(struct in6_addr);
    239 		break;
    240 	    default:
    241 		goto trunc;
    242 		break;
    243 	    }
    244 
    245 	    ND_PRINT((ndo, "SPM seq %u trail %u lead %u nla %s",
    246 			 EXTRACT_32BITS(&spm->pgms_seq),
    247                          EXTRACT_32BITS(&spm->pgms_trailseq),
    248 			 EXTRACT_32BITS(&spm->pgms_leadseq),
    249                          nla_buf));
    250 	    break;
    251 	}
    252 
    253 	case PGM_POLL: {
    254 	    const struct pgm_poll *poll_msg;
    255 
    256 	    poll_msg = (const struct pgm_poll *)(pgm + 1);
    257 	    ND_TCHECK(*poll_msg);
    258 	    ND_PRINT((ndo, "POLL seq %u round %u",
    259 			 EXTRACT_32BITS(&poll_msg->pgmp_seq),
    260                          EXTRACT_16BITS(&poll_msg->pgmp_round)));
    261 	    bp = (const u_char *) (poll_msg + 1);
    262 	    break;
    263 	}
    264 	case PGM_POLR: {
    265 	    const struct pgm_polr *polr;
    266 	    uint32_t ivl, rnd, mask;
    267 
    268 	    polr = (const struct pgm_polr *)(pgm + 1);
    269 	    ND_TCHECK(*polr);
    270 	    bp = (const u_char *) (polr + 1);
    271 
    272 	    switch (EXTRACT_16BITS(&polr->pgmp_nla_afi)) {
    273 	    case AFNUM_INET:
    274 		ND_TCHECK2(*bp, sizeof(struct in_addr));
    275 		addrtostr(bp, nla_buf, sizeof(nla_buf));
    276 		bp += sizeof(struct in_addr);
    277 		break;
    278 	    case AFNUM_INET6:
    279 		ND_TCHECK2(*bp, sizeof(struct in6_addr));
    280 		addrtostr6(bp, nla_buf, sizeof(nla_buf));
    281 		bp += sizeof(struct in6_addr);
    282 		break;
    283 	    default:
    284 		goto trunc;
    285 		break;
    286 	    }
    287 
    288 	    ND_TCHECK2(*bp, sizeof(uint32_t));
    289 	    ivl = EXTRACT_32BITS(bp);
    290 	    bp += sizeof(uint32_t);
    291 
    292 	    ND_TCHECK2(*bp, sizeof(uint32_t));
    293 	    rnd = EXTRACT_32BITS(bp);
    294 	    bp += sizeof(uint32_t);
    295 
    296 	    ND_TCHECK2(*bp, sizeof(uint32_t));
    297 	    mask = EXTRACT_32BITS(bp);
    298 	    bp += sizeof(uint32_t);
    299 
    300 	    ND_PRINT((ndo, "POLR seq %u round %u nla %s ivl %u rnd 0x%08x "
    301 			 "mask 0x%08x", EXTRACT_32BITS(&polr->pgmp_seq),
    302 			 EXTRACT_16BITS(&polr->pgmp_round), nla_buf, ivl, rnd, mask));
    303 	    break;
    304 	}
    305 	case PGM_ODATA: {
    306 	    const struct pgm_data *odata;
    307 
    308 	    odata = (const struct pgm_data *)(pgm + 1);
    309 	    ND_TCHECK(*odata);
    310 	    ND_PRINT((ndo, "ODATA trail %u seq %u",
    311 			 EXTRACT_32BITS(&odata->pgmd_trailseq),
    312 			 EXTRACT_32BITS(&odata->pgmd_seq)));
    313 	    bp = (const u_char *) (odata + 1);
    314 	    break;
    315 	}
    316 
    317 	case PGM_RDATA: {
    318 	    const struct pgm_data *rdata;
    319 
    320 	    rdata = (const struct pgm_data *)(pgm + 1);
    321 	    ND_TCHECK(*rdata);
    322 	    ND_PRINT((ndo, "RDATA trail %u seq %u",
    323 			 EXTRACT_32BITS(&rdata->pgmd_trailseq),
    324 			 EXTRACT_32BITS(&rdata->pgmd_seq)));
    325 	    bp = (const u_char *) (rdata + 1);
    326 	    break;
    327 	}
    328 
    329 	case PGM_NAK:
    330 	case PGM_NULLNAK:
    331 	case PGM_NCF: {
    332 	    const struct pgm_nak *nak;
    333 	    char source_buf[INET6_ADDRSTRLEN], group_buf[INET6_ADDRSTRLEN];
    334 
    335 	    nak = (const struct pgm_nak *)(pgm + 1);
    336 	    ND_TCHECK(*nak);
    337 	    bp = (const u_char *) (nak + 1);
    338 
    339 	    /*
    340 	     * Skip past the source, saving info along the way
    341 	     * and stopping if we don't have enough.
    342 	     */
    343 	    switch (EXTRACT_16BITS(&nak->pgmn_source_afi)) {
    344 	    case AFNUM_INET:
    345 		ND_TCHECK2(*bp, sizeof(struct in_addr));
    346 		addrtostr(bp, source_buf, sizeof(source_buf));
    347 		bp += sizeof(struct in_addr);
    348 		break;
    349 	    case AFNUM_INET6:
    350 		ND_TCHECK2(*bp, sizeof(struct in6_addr));
    351 		addrtostr6(bp, source_buf, sizeof(source_buf));
    352 		bp += sizeof(struct in6_addr);
    353 		break;
    354 	    default:
    355 		goto trunc;
    356 		break;
    357 	    }
    358 
    359 	    /*
    360 	     * Skip past the group, saving info along the way
    361 	     * and stopping if we don't have enough.
    362 	     */
    363 	    bp += (2 * sizeof(uint16_t));
    364 	    ND_TCHECK_16BITS(bp);
    365 	    switch (EXTRACT_16BITS(bp)) {
    366 	    case AFNUM_INET:
    367 		ND_TCHECK2(*bp, sizeof(struct in_addr));
    368 		addrtostr(bp, group_buf, sizeof(group_buf));
    369 		bp += sizeof(struct in_addr);
    370 		break;
    371 	    case AFNUM_INET6:
    372 		ND_TCHECK2(*bp, sizeof(struct in6_addr));
    373 		addrtostr6(bp, group_buf, sizeof(group_buf));
    374 		bp += sizeof(struct in6_addr);
    375 		break;
    376 	    default:
    377 		goto trunc;
    378 		break;
    379 	    }
    380 
    381 	    /*
    382 	     * Options decoding can go here.
    383 	     */
    384 	    switch (pgm->pgm_type) {
    385 		case PGM_NAK:
    386 		    ND_PRINT((ndo, "NAK "));
    387 		    break;
    388 		case PGM_NULLNAK:
    389 		    ND_PRINT((ndo, "NNAK "));
    390 		    break;
    391 		case PGM_NCF:
    392 		    ND_PRINT((ndo, "NCF "));
    393 		    break;
    394 		default:
    395                     break;
    396 	    }
    397 	    ND_PRINT((ndo, "(%s -> %s), seq %u",
    398 			 source_buf, group_buf, EXTRACT_32BITS(&nak->pgmn_seq)));
    399 	    break;
    400 	}
    401 
    402 	case PGM_ACK: {
    403 	    const struct pgm_ack *ack;
    404 
    405 	    ack = (const struct pgm_ack *)(pgm + 1);
    406 	    ND_TCHECK(*ack);
    407 	    ND_PRINT((ndo, "ACK seq %u",
    408 			 EXTRACT_32BITS(&ack->pgma_rx_max_seq)));
    409 	    bp = (const u_char *) (ack + 1);
    410 	    break;
    411 	}
    412 
    413 	case PGM_SPMR:
    414 	    ND_PRINT((ndo, "SPMR"));
    415 	    break;
    416 
    417 	default:
    418 	    ND_PRINT((ndo, "UNKNOWN type 0x%02x", pgm->pgm_type));
    419 	    break;
    420 
    421 	}
    422 	if (pgm->pgm_options & PGM_OPT_BIT_PRESENT) {
    423 
    424 	    /*
    425 	     * make sure there's enough for the first option header
    426 	     */
    427 	    if (!ND_TTEST2(*bp, PGM_MIN_OPT_LEN)) {
    428 		ND_PRINT((ndo, "[|OPT]"));
    429 		return;
    430 	    }
    431 
    432 	    /*
    433 	     * That option header MUST be an OPT_LENGTH option
    434 	     * (see the first paragraph of section 9.1 in RFC 3208).
    435 	     */
    436 	    opt_type = *bp++;
    437 	    if ((opt_type & PGM_OPT_MASK) != PGM_OPT_LENGTH) {
    438 		ND_PRINT((ndo, "[First option bad, should be PGM_OPT_LENGTH, is %u]", opt_type & PGM_OPT_MASK));
    439 		return;
    440 	    }
    441 	    opt_len = *bp++;
    442 	    if (opt_len != 4) {
    443 		ND_PRINT((ndo, "[Bad OPT_LENGTH option, length %u != 4]", opt_len));
    444 		return;
    445 	    }
    446 	    opts_len = EXTRACT_16BITS(bp);
    447 	    if (opts_len < 4) {
    448 		ND_PRINT((ndo, "[Bad total option length %u < 4]", opts_len));
    449 		return;
    450 	    }
    451 	    bp += sizeof(uint16_t);
    452 	    ND_PRINT((ndo, " OPTS LEN %d", opts_len));
    453 	    opts_len -= 4;
    454 
    455 	    while (opts_len) {
    456 		if (opts_len < PGM_MIN_OPT_LEN) {
    457 		    ND_PRINT((ndo, "[Total option length leaves no room for final option]"));
    458 		    return;
    459 		}
    460 		if (!ND_TTEST2(*bp, 2)) {
    461 		    ND_PRINT((ndo, " [|OPT]"));
    462 		    return;
    463 		}
    464 		opt_type = *bp++;
    465 		opt_len = *bp++;
    466 		if (opt_len < PGM_MIN_OPT_LEN) {
    467 		    ND_PRINT((ndo, "[Bad option, length %u < %u]", opt_len,
    468 		        PGM_MIN_OPT_LEN));
    469 		    break;
    470 		}
    471 		if (opts_len < opt_len) {
    472 		    ND_PRINT((ndo, "[Total option length leaves no room for final option]"));
    473 		    return;
    474 		}
    475 		if (!ND_TTEST2(*bp, opt_len - 2)) {
    476 		    ND_PRINT((ndo, " [|OPT]"));
    477 		    return;
    478 		}
    479 
    480 		switch (opt_type & PGM_OPT_MASK) {
    481 		case PGM_OPT_LENGTH:
    482 #define PGM_OPT_LENGTH_LEN	(2+2)
    483 		    if (opt_len != PGM_OPT_LENGTH_LEN) {
    484 			ND_PRINT((ndo, "[Bad OPT_LENGTH option, length %u != %u]",
    485 			    opt_len, PGM_OPT_LENGTH_LEN));
    486 			return;
    487 		    }
    488 		    ND_PRINT((ndo, " OPTS LEN (extra?) %d", EXTRACT_16BITS(bp)));
    489 		    bp += 2;
    490 		    opts_len -= PGM_OPT_LENGTH_LEN;
    491 		    break;
    492 
    493 		case PGM_OPT_FRAGMENT:
    494 #define PGM_OPT_FRAGMENT_LEN	(2+2+4+4+4)
    495 		    if (opt_len != PGM_OPT_FRAGMENT_LEN) {
    496 			ND_PRINT((ndo, "[Bad OPT_FRAGMENT option, length %u != %u]",
    497 			    opt_len, PGM_OPT_FRAGMENT_LEN));
    498 			return;
    499 		    }
    500 		    bp += 2;
    501 		    seq = EXTRACT_32BITS(bp);
    502 		    bp += 4;
    503 		    offset = EXTRACT_32BITS(bp);
    504 		    bp += 4;
    505 		    len = EXTRACT_32BITS(bp);
    506 		    bp += 4;
    507 		    ND_PRINT((ndo, " FRAG seq %u off %u len %u", seq, offset, len));
    508 		    opts_len -= PGM_OPT_FRAGMENT_LEN;
    509 		    break;
    510 
    511 		case PGM_OPT_NAK_LIST:
    512 		    bp += 2;
    513 		    opt_len -= 4;	/* option header */
    514 		    ND_PRINT((ndo, " NAK LIST"));
    515 		    while (opt_len) {
    516 			if (opt_len < 4) {
    517 			    ND_PRINT((ndo, "[Option length not a multiple of 4]"));
    518 			    return;
    519 			}
    520 			ND_TCHECK2(*bp, 4);
    521 			ND_PRINT((ndo, " %u", EXTRACT_32BITS(bp)));
    522 			bp += 4;
    523 			opt_len -= 4;
    524 			opts_len -= 4;
    525 		    }
    526 		    break;
    527 
    528 		case PGM_OPT_JOIN:
    529 #define PGM_OPT_JOIN_LEN	(2+2+4)
    530 		    if (opt_len != PGM_OPT_JOIN_LEN) {
    531 			ND_PRINT((ndo, "[Bad OPT_JOIN option, length %u != %u]",
    532 			    opt_len, PGM_OPT_JOIN_LEN));
    533 			return;
    534 		    }
    535 		    bp += 2;
    536 		    seq = EXTRACT_32BITS(bp);
    537 		    bp += 4;
    538 		    ND_PRINT((ndo, " JOIN %u", seq));
    539 		    opts_len -= PGM_OPT_JOIN_LEN;
    540 		    break;
    541 
    542 		case PGM_OPT_NAK_BO_IVL:
    543 #define PGM_OPT_NAK_BO_IVL_LEN	(2+2+4+4)
    544 		    if (opt_len != PGM_OPT_NAK_BO_IVL_LEN) {
    545 			ND_PRINT((ndo, "[Bad OPT_NAK_BO_IVL option, length %u != %u]",
    546 			    opt_len, PGM_OPT_NAK_BO_IVL_LEN));
    547 			return;
    548 		    }
    549 		    bp += 2;
    550 		    offset = EXTRACT_32BITS(bp);
    551 		    bp += 4;
    552 		    seq = EXTRACT_32BITS(bp);
    553 		    bp += 4;
    554 		    ND_PRINT((ndo, " BACKOFF ivl %u ivlseq %u", offset, seq));
    555 		    opts_len -= PGM_OPT_NAK_BO_IVL_LEN;
    556 		    break;
    557 
    558 		case PGM_OPT_NAK_BO_RNG:
    559 #define PGM_OPT_NAK_BO_RNG_LEN	(2+2+4+4)
    560 		    if (opt_len != PGM_OPT_NAK_BO_RNG_LEN) {
    561 			ND_PRINT((ndo, "[Bad OPT_NAK_BO_RNG option, length %u != %u]",
    562 			    opt_len, PGM_OPT_NAK_BO_RNG_LEN));
    563 			return;
    564 		    }
    565 		    bp += 2;
    566 		    offset = EXTRACT_32BITS(bp);
    567 		    bp += 4;
    568 		    seq = EXTRACT_32BITS(bp);
    569 		    bp += 4;
    570 		    ND_PRINT((ndo, " BACKOFF max %u min %u", offset, seq));
    571 		    opts_len -= PGM_OPT_NAK_BO_RNG_LEN;
    572 		    break;
    573 
    574 		case PGM_OPT_REDIRECT:
    575 #define PGM_OPT_REDIRECT_FIXED_LEN	(2+2+2+2)
    576 		    if (opt_len < PGM_OPT_REDIRECT_FIXED_LEN) {
    577 			ND_PRINT((ndo, "[Bad OPT_REDIRECT option, length %u < %u]",
    578 			    opt_len, PGM_OPT_REDIRECT_FIXED_LEN));
    579 			return;
    580 		    }
    581 		    bp += 2;
    582 		    nla_afnum = EXTRACT_16BITS(bp);
    583 		    bp += 2+2;
    584 		    switch (nla_afnum) {
    585 		    case AFNUM_INET:
    586 			if (opt_len != PGM_OPT_REDIRECT_FIXED_LEN + sizeof(struct in_addr)) {
    587 			    ND_PRINT((ndo, "[Bad OPT_REDIRECT option, length %u != %u + address size]",
    588 			        opt_len, PGM_OPT_REDIRECT_FIXED_LEN));
    589 			    return;
    590 			}
    591 			ND_TCHECK2(*bp, sizeof(struct in_addr));
    592 			addrtostr(bp, nla_buf, sizeof(nla_buf));
    593 			bp += sizeof(struct in_addr);
    594 			opts_len -= PGM_OPT_REDIRECT_FIXED_LEN + sizeof(struct in_addr);
    595 			break;
    596 		    case AFNUM_INET6:
    597 			if (opt_len != PGM_OPT_REDIRECT_FIXED_LEN + sizeof(struct in6_addr)) {
    598 			    ND_PRINT((ndo, "[Bad OPT_REDIRECT option, length %u != %u + address size]",
    599 			        PGM_OPT_REDIRECT_FIXED_LEN, opt_len));
    600 			    return;
    601 			}
    602 			ND_TCHECK2(*bp, sizeof(struct in6_addr));
    603 			addrtostr6(bp, nla_buf, sizeof(nla_buf));
    604 			bp += sizeof(struct in6_addr);
    605 			opts_len -= PGM_OPT_REDIRECT_FIXED_LEN + sizeof(struct in6_addr);
    606 			break;
    607 		    default:
    608 			goto trunc;
    609 			break;
    610 		    }
    611 
    612 		    ND_PRINT((ndo, " REDIRECT %s",  nla_buf));
    613 		    break;
    614 
    615 		case PGM_OPT_PARITY_PRM:
    616 #define PGM_OPT_PARITY_PRM_LEN	(2+2+4)
    617 		    if (opt_len != PGM_OPT_PARITY_PRM_LEN) {
    618 			ND_PRINT((ndo, "[Bad OPT_PARITY_PRM option, length %u != %u]",
    619 			    opt_len, PGM_OPT_PARITY_PRM_LEN));
    620 			return;
    621 		    }
    622 		    bp += 2;
    623 		    len = EXTRACT_32BITS(bp);
    624 		    bp += 4;
    625 		    ND_PRINT((ndo, " PARITY MAXTGS %u", len));
    626 		    opts_len -= PGM_OPT_PARITY_PRM_LEN;
    627 		    break;
    628 
    629 		case PGM_OPT_PARITY_GRP:
    630 #define PGM_OPT_PARITY_GRP_LEN	(2+2+4)
    631 		    if (opt_len != PGM_OPT_PARITY_GRP_LEN) {
    632 			ND_PRINT((ndo, "[Bad OPT_PARITY_GRP option, length %u != %u]",
    633 			    opt_len, PGM_OPT_PARITY_GRP_LEN));
    634 			return;
    635 		    }
    636 		    bp += 2;
    637 		    seq = EXTRACT_32BITS(bp);
    638 		    bp += 4;
    639 		    ND_PRINT((ndo, " PARITY GROUP %u", seq));
    640 		    opts_len -= PGM_OPT_PARITY_GRP_LEN;
    641 		    break;
    642 
    643 		case PGM_OPT_CURR_TGSIZE:
    644 #define PGM_OPT_CURR_TGSIZE_LEN	(2+2+4)
    645 		    if (opt_len != PGM_OPT_CURR_TGSIZE_LEN) {
    646 			ND_PRINT((ndo, "[Bad OPT_CURR_TGSIZE option, length %u != %u]",
    647 			    opt_len, PGM_OPT_CURR_TGSIZE_LEN));
    648 			return;
    649 		    }
    650 		    bp += 2;
    651 		    len = EXTRACT_32BITS(bp);
    652 		    bp += 4;
    653 		    ND_PRINT((ndo, " PARITY ATGS %u", len));
    654 		    opts_len -= PGM_OPT_CURR_TGSIZE_LEN;
    655 		    break;
    656 
    657 		case PGM_OPT_NBR_UNREACH:
    658 #define PGM_OPT_NBR_UNREACH_LEN	(2+2)
    659 		    if (opt_len != PGM_OPT_NBR_UNREACH_LEN) {
    660 			ND_PRINT((ndo, "[Bad OPT_NBR_UNREACH option, length %u != %u]",
    661 			    opt_len, PGM_OPT_NBR_UNREACH_LEN));
    662 			return;
    663 		    }
    664 		    bp += 2;
    665 		    ND_PRINT((ndo, " NBR_UNREACH"));
    666 		    opts_len -= PGM_OPT_NBR_UNREACH_LEN;
    667 		    break;
    668 
    669 		case PGM_OPT_PATH_NLA:
    670 		    ND_PRINT((ndo, " PATH_NLA [%d]", opt_len));
    671 		    bp += opt_len;
    672 		    opts_len -= opt_len;
    673 		    break;
    674 
    675 		case PGM_OPT_SYN:
    676 #define PGM_OPT_SYN_LEN	(2+2)
    677 		    if (opt_len != PGM_OPT_SYN_LEN) {
    678 			ND_PRINT((ndo, "[Bad OPT_SYN option, length %u != %u]",
    679 			    opt_len, PGM_OPT_SYN_LEN));
    680 			return;
    681 		    }
    682 		    bp += 2;
    683 		    ND_PRINT((ndo, " SYN"));
    684 		    opts_len -= PGM_OPT_SYN_LEN;
    685 		    break;
    686 
    687 		case PGM_OPT_FIN:
    688 #define PGM_OPT_FIN_LEN	(2+2)
    689 		    if (opt_len != PGM_OPT_FIN_LEN) {
    690 			ND_PRINT((ndo, "[Bad OPT_FIN option, length %u != %u]",
    691 			    opt_len, PGM_OPT_FIN_LEN));
    692 			return;
    693 		    }
    694 		    bp += 2;
    695 		    ND_PRINT((ndo, " FIN"));
    696 		    opts_len -= PGM_OPT_FIN_LEN;
    697 		    break;
    698 
    699 		case PGM_OPT_RST:
    700 #define PGM_OPT_RST_LEN	(2+2)
    701 		    if (opt_len != PGM_OPT_RST_LEN) {
    702 			ND_PRINT((ndo, "[Bad OPT_RST option, length %u != %u]",
    703 			    opt_len, PGM_OPT_RST_LEN));
    704 			return;
    705 		    }
    706 		    bp += 2;
    707 		    ND_PRINT((ndo, " RST"));
    708 		    opts_len -= PGM_OPT_RST_LEN;
    709 		    break;
    710 
    711 		case PGM_OPT_CR:
    712 		    ND_PRINT((ndo, " CR"));
    713 		    bp += opt_len;
    714 		    opts_len -= opt_len;
    715 		    break;
    716 
    717 		case PGM_OPT_CRQST:
    718 #define PGM_OPT_CRQST_LEN	(2+2)
    719 		    if (opt_len != PGM_OPT_CRQST_LEN) {
    720 			ND_PRINT((ndo, "[Bad OPT_CRQST option, length %u != %u]",
    721 			    opt_len, PGM_OPT_CRQST_LEN));
    722 			return;
    723 		    }
    724 		    bp += 2;
    725 		    ND_PRINT((ndo, " CRQST"));
    726 		    opts_len -= PGM_OPT_CRQST_LEN;
    727 		    break;
    728 
    729 		case PGM_OPT_PGMCC_DATA:
    730 #define PGM_OPT_PGMCC_DATA_FIXED_LEN	(2+2+4+2+2)
    731 		    if (opt_len < PGM_OPT_PGMCC_DATA_FIXED_LEN) {
    732 			ND_PRINT((ndo, "[Bad OPT_PGMCC_DATA option, length %u < %u]",
    733 			    opt_len, PGM_OPT_PGMCC_DATA_FIXED_LEN));
    734 			return;
    735 		    }
    736 		    bp += 2;
    737 		    offset = EXTRACT_32BITS(bp);
    738 		    bp += 4;
    739 		    nla_afnum = EXTRACT_16BITS(bp);
    740 		    bp += 2+2;
    741 		    switch (nla_afnum) {
    742 		    case AFNUM_INET:
    743 			if (opt_len != PGM_OPT_PGMCC_DATA_FIXED_LEN + sizeof(struct in_addr)) {
    744 			    ND_PRINT((ndo, "[Bad OPT_PGMCC_DATA option, length %u != %u + address size]",
    745 			        opt_len, PGM_OPT_PGMCC_DATA_FIXED_LEN));
    746 			    return;
    747 			}
    748 			ND_TCHECK2(*bp, sizeof(struct in_addr));
    749 			addrtostr(bp, nla_buf, sizeof(nla_buf));
    750 			bp += sizeof(struct in_addr);
    751 			opts_len -= PGM_OPT_PGMCC_DATA_FIXED_LEN + sizeof(struct in_addr);
    752 			break;
    753 		    case AFNUM_INET6:
    754 			if (opt_len != PGM_OPT_PGMCC_DATA_FIXED_LEN + sizeof(struct in6_addr)) {
    755 			    ND_PRINT((ndo, "[Bad OPT_PGMCC_DATA option, length %u != %u + address size]",
    756 			        opt_len, PGM_OPT_PGMCC_DATA_FIXED_LEN));
    757 			    return;
    758 			}
    759 			ND_TCHECK2(*bp, sizeof(struct in6_addr));
    760 			addrtostr6(bp, nla_buf, sizeof(nla_buf));
    761 			bp += sizeof(struct in6_addr);
    762 			opts_len -= PGM_OPT_PGMCC_DATA_FIXED_LEN + sizeof(struct in6_addr);
    763 			break;
    764 		    default:
    765 			goto trunc;
    766 			break;
    767 		    }
    768 
    769 		    ND_PRINT((ndo, " PGMCC DATA %u %s", offset, nla_buf));
    770 		    break;
    771 
    772 		case PGM_OPT_PGMCC_FEEDBACK:
    773 #define PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN	(2+2+4+2+2)
    774 		    if (opt_len < PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN) {
    775 			ND_PRINT((ndo, "[Bad PGM_OPT_PGMCC_FEEDBACK option, length %u < %u]",
    776 			    opt_len, PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN));
    777 			return;
    778 		    }
    779 		    bp += 2;
    780 		    offset = EXTRACT_32BITS(bp);
    781 		    bp += 4;
    782 		    nla_afnum = EXTRACT_16BITS(bp);
    783 		    bp += 2+2;
    784 		    switch (nla_afnum) {
    785 		    case AFNUM_INET:
    786 			if (opt_len != PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN + sizeof(struct in_addr)) {
    787 			    ND_PRINT((ndo, "[Bad OPT_PGMCC_FEEDBACK option, length %u != %u + address size]",
    788 			        opt_len, PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN));
    789 			    return;
    790 			}
    791 			ND_TCHECK2(*bp, sizeof(struct in_addr));
    792 			addrtostr(bp, nla_buf, sizeof(nla_buf));
    793 			bp += sizeof(struct in_addr);
    794 			opts_len -= PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN + sizeof(struct in_addr);
    795 			break;
    796 		    case AFNUM_INET6:
    797 			if (opt_len != PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN + sizeof(struct in6_addr)) {
    798 			    ND_PRINT((ndo, "[Bad OPT_PGMCC_FEEDBACK option, length %u != %u + address size]",
    799 			        opt_len, PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN));
    800 			    return;
    801 			}
    802 			ND_TCHECK2(*bp, sizeof(struct in6_addr));
    803 			addrtostr6(bp, nla_buf, sizeof(nla_buf));
    804 			bp += sizeof(struct in6_addr);
    805 			opts_len -= PGM_OPT_PGMCC_FEEDBACK_FIXED_LEN + sizeof(struct in6_addr);
    806 			break;
    807 		    default:
    808 			goto trunc;
    809 			break;
    810 		    }
    811 
    812 		    ND_PRINT((ndo, " PGMCC FEEDBACK %u %s", offset, nla_buf));
    813 		    break;
    814 
    815 		default:
    816 		    ND_PRINT((ndo, " OPT_%02X [%d] ", opt_type, opt_len));
    817 		    bp += opt_len;
    818 		    opts_len -= opt_len;
    819 		    break;
    820 		}
    821 
    822 		if (opt_type & PGM_OPT_END)
    823 		    break;
    824 	     }
    825 	}
    826 
    827 	ND_PRINT((ndo, " [%u]", length));
    828 	if (ndo->ndo_packettype == PT_PGM_ZMTP1 &&
    829 	    (pgm->pgm_type == PGM_ODATA || pgm->pgm_type == PGM_RDATA))
    830 		zmtp1_print_datagram(ndo, bp, EXTRACT_16BITS(&pgm->pgm_length));
    831 
    832 	return;
    833 
    834 trunc:
    835 	ND_PRINT((ndo, "[|pgm]"));
    836 	if (ch != '\0')
    837 		ND_PRINT((ndo, ">"));
    838 }
    839