+ if (family == 0) {
+ ND_PRINT("\n\t AFI 0, %s, metric: %u",
+ GET_IPADDR_STRING(ni->rip_dest),
+ GET_BE_U_4(ni->rip_metric));
+ return (RIP_ROUTELEN);
+ } /* BSD_AF_INET */
+ ND_PRINT("\n\t %s, metric: %u",
+ GET_IPADDR_STRING(ni->rip_dest),
+ GET_BE_U_4(ni->rip_metric));
+ return (RIP_ROUTELEN);
+invalid:
+ return 0;
+}
+
+static unsigned
+rip_entry_print_v2(netdissect_options *ndo, const u_char *p,
+ unsigned remaining)
+{
+ const struct rip_entry_header *eh = (const struct rip_entry_header *)p;
+ u_short family;
+ const struct rip_netinfo_v2 *ni;
+
+ ND_ICHECKMSG_ZU("remaining data length", remaining, <, sizeof(*eh));
+ ND_TCHECK_SIZE(eh);
+ family = GET_BE_U_2(eh->rip_family);
+ if (family == 0xFFFF) { /* variable-sized authentication structures */
+ uint16_t auth_type = GET_BE_U_2(eh->rip_tag);
+
+ p += sizeof(*eh);
+ remaining -= sizeof(*eh);
+ if (auth_type == 2) {
+ ND_PRINT("\n\t Simple Text Authentication data: ");
+ nd_printjnp(ndo, p, RIP_AUTHLEN);
+ } else if (auth_type == 3) {
+ const struct rip_auth_crypto_v2 *ch;
+
+ ch = (const struct rip_auth_crypto_v2 *)p;
+ ND_ICHECKMSG_ZU("remaining data length", remaining,
+ <, sizeof(*ch));
+ ND_PRINT("\n\t Auth header:");
+ ND_PRINT(" Packet Len %u,",
+ GET_BE_U_2(ch->rip_packet_len));
+ ND_PRINT(" Key-ID %u,", GET_U_1(ch->rip_key_id));
+ ND_PRINT(" Auth Data Len %u,",
+ GET_U_1(ch->rip_auth_data_len));
+ ND_PRINT(" SeqNo %u,", GET_BE_U_4(ch->rip_seq_num));
+ ND_PRINT(" MBZ %u,", GET_BE_U_4(ch->rip_mbz1));
+ ND_PRINT(" MBZ %u", GET_BE_U_4(ch->rip_mbz2));
+ } else if (auth_type == 1) {
+ ND_PRINT("\n\t Auth trailer:");
+ print_unknown_data(ndo, p, "\n\t ", remaining);
+ return (sizeof(*eh) + remaining); /* AT spans till the packet end */
+ } else {
+ ND_PRINT("\n\t Unknown (%u) Authentication data:",
+ auth_type);
+ print_unknown_data(ndo, p, "\n\t ", remaining);
+ return (sizeof(*eh) + remaining); /* we don't know how long this is, so we go to the packet end */
+ }
+ } else if (family != BSD_AF_INET && family != 0) {
+ ND_PRINT("\n\t AFI %s", tok2str(bsd_af_values, "Unknown (%u)", family));
+ print_unknown_data(ndo, p + sizeof(*eh), "\n\t ", RIP_ROUTELEN - sizeof(*eh));
+ } else { /* BSD_AF_INET or AFI 0 */
+ ni = (const struct rip_netinfo_v2 *)p;
+ ND_ICHECKMSG_ZU("remaining data length", remaining, <,
+ sizeof(*ni));
+ ND_PRINT("\n\t AFI %s, %15s/%-2d, tag 0x%04x, metric: %u, next-hop: ",
+ tok2str(bsd_af_values, "%u", family),
+ GET_IPADDR_STRING(ni->rip_dest),
+ mask2plen(GET_BE_U_4(ni->rip_dest_mask)),
+ GET_BE_U_2(ni->rip_tag),
+ GET_BE_U_4(ni->rip_metric));
+ if (GET_BE_U_4(ni->rip_router))
+ ND_PRINT("%s", GET_IPADDR_STRING(ni->rip_router));
+ else
+ ND_PRINT("self");
+ }
+ return (RIP_ROUTELEN);
+invalid:
+ return 0;