1b0453382SBill Fenner /* 2b0453382SBill Fenner * Copyright (C) 1998 and 1999 WIDE Project. 3b0453382SBill Fenner * All rights reserved. 4b0453382SBill Fenner * 5b0453382SBill Fenner * Redistribution and use in source and binary forms, with or without 6b0453382SBill Fenner * modification, are permitted provided that the following conditions 7b0453382SBill Fenner * are met: 8b0453382SBill Fenner * 1. Redistributions of source code must retain the above copyright 9b0453382SBill Fenner * notice, this list of conditions and the following disclaimer. 10b0453382SBill Fenner * 2. Redistributions in binary form must reproduce the above copyright 11b0453382SBill Fenner * notice, this list of conditions and the following disclaimer in the 12b0453382SBill Fenner * documentation and/or other materials provided with the distribution. 13b0453382SBill Fenner * 3. Neither the name of the project nor the names of its contributors 14b0453382SBill Fenner * may be used to endorse or promote products derived from this software 15b0453382SBill Fenner * without specific prior written permission. 16b0453382SBill Fenner * 17b0453382SBill Fenner * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 18b0453382SBill Fenner * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19b0453382SBill Fenner * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20b0453382SBill Fenner * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 21b0453382SBill Fenner * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22b0453382SBill Fenner * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23b0453382SBill Fenner * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24b0453382SBill Fenner * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25b0453382SBill Fenner * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26b0453382SBill Fenner * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27b0453382SBill Fenner * SUCH DAMAGE. 28b0453382SBill Fenner */ 299afd0c29SBill Fenner /* 305b0fe478SBruce M Simpson * RFC3315: DHCPv6 315b0fe478SBruce M Simpson * supported DHCPv6 options: 325b0fe478SBruce M Simpson * RFC3319, 331de50e9fSSam Leffler * RFC3633, 341de50e9fSSam Leffler * RFC3646, 351de50e9fSSam Leffler * draft-ietf-dhc-dhcpv6-opt-timeconfig-03.txt, 361de50e9fSSam Leffler * draft-ietf-dhc-lifetime-00.txt, 379afd0c29SBill Fenner */ 38b0453382SBill Fenner 39b0453382SBill Fenner #ifndef lint 405b0fe478SBruce M Simpson static const char rcsid[] _U_ = 411de50e9fSSam Leffler "@(#) $Header: /tcpdump/master/tcpdump/print-dhcp6.c,v 1.35 2004/07/06 22:16:03 guy Exp $"; 42b0453382SBill Fenner #endif 43b0453382SBill Fenner 44b0453382SBill Fenner #ifdef HAVE_CONFIG_H 45b0453382SBill Fenner #include "config.h" 46b0453382SBill Fenner #endif 47b0453382SBill Fenner 485b0fe478SBruce M Simpson #include <tcpdump-stdinc.h> 49b0453382SBill Fenner 50b0453382SBill Fenner #include <stdio.h> 51b0453382SBill Fenner #include <string.h> 52b0453382SBill Fenner 53b0453382SBill Fenner #include "interface.h" 54b0453382SBill Fenner #include "addrtoname.h" 555b0fe478SBruce M Simpson #include "extract.h" 565b0fe478SBruce M Simpson 575b0fe478SBruce M Simpson /* lease duration */ 585b0fe478SBruce M Simpson #define DHCP6_DURATITION_INFINITE 0xffffffff 59b0453382SBill Fenner 609afd0c29SBill Fenner /* Error Values */ 619afd0c29SBill Fenner #define DH6ERR_FAILURE 16 629afd0c29SBill Fenner #define DH6ERR_AUTHFAIL 17 639afd0c29SBill Fenner #define DH6ERR_POORLYFORMED 18 649afd0c29SBill Fenner #define DH6ERR_UNAVAIL 19 659afd0c29SBill Fenner #define DH6ERR_OPTUNAVAIL 20 66b0453382SBill Fenner 679afd0c29SBill Fenner /* Message type */ 685b0fe478SBruce M Simpson #define DH6_SOLICIT 1 695b0fe478SBruce M Simpson #define DH6_ADVERTISE 2 705b0fe478SBruce M Simpson #define DH6_REQUEST 3 715b0fe478SBruce M Simpson #define DH6_CONFIRM 4 725b0fe478SBruce M Simpson #define DH6_RENEW 5 735b0fe478SBruce M Simpson #define DH6_REBIND 6 749afd0c29SBill Fenner #define DH6_REPLY 7 755b0fe478SBruce M Simpson #define DH6_RELEASE 8 765b0fe478SBruce M Simpson #define DH6_DECLINE 9 775b0fe478SBruce M Simpson #define DH6_RECONFIGURE 10 789afd0c29SBill Fenner #define DH6_INFORM_REQ 11 795b0fe478SBruce M Simpson #define DH6_RELAY_FORW 12 805b0fe478SBruce M Simpson #define DH6_RELAY_REPLY 13 81b0453382SBill Fenner 829afd0c29SBill Fenner /* DHCP6 base packet format */ 839afd0c29SBill Fenner struct dhcp6 { 849afd0c29SBill Fenner union { 859afd0c29SBill Fenner u_int8_t m; 869afd0c29SBill Fenner u_int32_t x; 879afd0c29SBill Fenner } dh6_msgtypexid; 889afd0c29SBill Fenner /* options follow */ 895b0fe478SBruce M Simpson }; 909afd0c29SBill Fenner #define dh6_msgtype dh6_msgtypexid.m 919afd0c29SBill Fenner #define dh6_xid dh6_msgtypexid.x 929afd0c29SBill Fenner #define DH6_XIDMASK 0x00ffffff 93b0453382SBill Fenner 945b0fe478SBruce M Simpson /* DHCPv6 relay messages */ 955b0fe478SBruce M Simpson struct dhcp6_relay { 965b0fe478SBruce M Simpson u_int8_t dh6relay_msgtype; 975b0fe478SBruce M Simpson u_int8_t dh6relay_hcnt; 985b0fe478SBruce M Simpson u_int8_t dh6relay_linkaddr[16]; /* XXX: badly aligned */ 995b0fe478SBruce M Simpson u_int8_t dh6relay_peeraddr[16]; 1005b0fe478SBruce M Simpson /* options follow */ 1015b0fe478SBruce M Simpson }; 1025b0fe478SBruce M Simpson 1035b0fe478SBruce M Simpson /* options */ 1045b0fe478SBruce M Simpson #define DH6OPT_CLIENTID 1 1055b0fe478SBruce M Simpson #define DH6OPT_SERVERID 2 1065b0fe478SBruce M Simpson #define DH6OPT_IA_NA 3 1075b0fe478SBruce M Simpson #define DH6OPT_IA_TMP 4 1085b0fe478SBruce M Simpson #define DH6OPT_IADDR 5 1095b0fe478SBruce M Simpson #define DH6OPT_ORO 6 1105b0fe478SBruce M Simpson #define DH6OPT_PREFERENCE 7 1115b0fe478SBruce M Simpson # define DH6OPT_PREF_MAX 255 1125b0fe478SBruce M Simpson #define DH6OPT_ELAPSED_TIME 8 1135b0fe478SBruce M Simpson #define DH6OPT_RELAY_MSG 9 1145b0fe478SBruce M Simpson /*#define DH6OPT_SERVER_MSG 10 deprecated */ 1155b0fe478SBruce M Simpson #define DH6OPT_AUTH 11 1161de50e9fSSam Leffler # define DH6OPT_AUTHPROTO_DELAYED 2 1171de50e9fSSam Leffler # define DH6OPT_AUTHPROTO_RECONFIG 3 1181de50e9fSSam Leffler # define DH6OPT_AUTHALG_HMACMD5 1 1191de50e9fSSam Leffler # define DH6OPT_AUTHRDM_MONOCOUNTER 0 1201de50e9fSSam Leffler # define DH6OPT_AUTHRECONFIG_KEY 1 1211de50e9fSSam Leffler # define DH6OPT_AUTHRECONFIG_HMACMD5 2 1225b0fe478SBruce M Simpson #define DH6OPT_UNICAST 12 1235b0fe478SBruce M Simpson #define DH6OPT_STATUS_CODE 13 1245b0fe478SBruce M Simpson # define DH6OPT_STCODE_SUCCESS 0 1255b0fe478SBruce M Simpson # define DH6OPT_STCODE_UNSPECFAIL 1 1265b0fe478SBruce M Simpson # define DH6OPT_STCODE_NOADDRAVAIL 2 1275b0fe478SBruce M Simpson # define DH6OPT_STCODE_NOBINDING 3 1285b0fe478SBruce M Simpson # define DH6OPT_STCODE_NOTONLINK 4 1295b0fe478SBruce M Simpson # define DH6OPT_STCODE_USEMULTICAST 5 1305b0fe478SBruce M Simpson # define DH6OPT_STCODE_NOPREFIXAVAIL 6 1315b0fe478SBruce M Simpson #define DH6OPT_RAPID_COMMIT 14 1325b0fe478SBruce M Simpson #define DH6OPT_USER_CLASS 15 1335b0fe478SBruce M Simpson #define DH6OPT_VENDOR_CLASS 16 1345b0fe478SBruce M Simpson #define DH6OPT_VENDOR_OPTS 17 1355b0fe478SBruce M Simpson #define DH6OPT_INTERFACE_ID 18 1365b0fe478SBruce M Simpson #define DH6OPT_RECONF_MSG 19 1375b0fe478SBruce M Simpson #define DH6OPT_RECONF_ACCEPT 20 1385b0fe478SBruce M Simpson #define DH6OPT_SIP_SERVER_D 21 1395b0fe478SBruce M Simpson #define DH6OPT_SIP_SERVER_A 22 1405b0fe478SBruce M Simpson #define DH6OPT_DNS 23 1415b0fe478SBruce M Simpson #define DH6OPT_DNSNAME 24 1421de50e9fSSam Leffler #define DH6OPT_IA_PD 25 1431de50e9fSSam Leffler #define DH6OPT_IA_PD_PREFIX 26 1445b0fe478SBruce M Simpson 1455b0fe478SBruce M Simpson /* 1461de50e9fSSam Leffler * The old prefix delegation option used in the service specification document 1475b0fe478SBruce M Simpson * (200206xx version) by NTT Communications. 1485b0fe478SBruce M Simpson */ 1495b0fe478SBruce M Simpson #define DH6OPT_PREFIX_DELEGATION 30 1505b0fe478SBruce M Simpson #define DH6OPT_PREFIX_INFORMATION 31 1515b0fe478SBruce M Simpson #define DH6OPT_PREFIX_REQUEST 32 1525b0fe478SBruce M Simpson 1535b0fe478SBruce M Simpson /* 1541de50e9fSSam Leffler * The following one is an unassigned number. 1551de50e9fSSam Leffler * We temporarily use values as of KAME snap 20040322. 1565b0fe478SBruce M Simpson */ 1575b0fe478SBruce M Simpson #define DH6OPT_NTP_SERVERS 35 1581de50e9fSSam Leffler #define DH6OPT_LIFETIME 36 1595b0fe478SBruce M Simpson 1609afd0c29SBill Fenner struct dhcp6opt { 1619afd0c29SBill Fenner u_int16_t dh6opt_type; 1629afd0c29SBill Fenner u_int16_t dh6opt_len; 1639afd0c29SBill Fenner /* type-dependent data follows */ 1645b0fe478SBruce M Simpson }; 1655b0fe478SBruce M Simpson 1665b0fe478SBruce M Simpson struct dhcp6_ia { 1675b0fe478SBruce M Simpson u_int16_t dh6opt_ia_type; 1685b0fe478SBruce M Simpson u_int16_t dh6opt_ia_len; 1695b0fe478SBruce M Simpson u_int32_t dh6opt_ia_iaid; 1705b0fe478SBruce M Simpson u_int32_t dh6opt_ia_t1; 1715b0fe478SBruce M Simpson u_int32_t dh6opt_ia_t2; 1725b0fe478SBruce M Simpson }; 1735b0fe478SBruce M Simpson 1745b0fe478SBruce M Simpson struct dhcp6_ia_prefix { 1755b0fe478SBruce M Simpson u_int16_t dh6opt_ia_prefix_type; 1765b0fe478SBruce M Simpson u_int16_t dh6opt_ia_prefix_len; 1775b0fe478SBruce M Simpson u_int32_t dh6opt_ia_prefix_pltime; 1785b0fe478SBruce M Simpson u_int32_t dh6opt_ia_prefix_vltime; 1795b0fe478SBruce M Simpson u_int8_t dh6opt_ia_prefix_plen; 1805b0fe478SBruce M Simpson struct in6_addr dh6opt_ia_prefix_addr; 1819afd0c29SBill Fenner } __attribute__ ((__packed__)); 182b0453382SBill Fenner 1831de50e9fSSam Leffler struct dhcp6_auth { 1841de50e9fSSam Leffler u_int16_t dh6opt_auth_type; 1851de50e9fSSam Leffler u_int16_t dh6opt_auth_len; 1861de50e9fSSam Leffler u_int8_t dh6opt_auth_proto; 1871de50e9fSSam Leffler u_int8_t dh6opt_auth_alg; 1881de50e9fSSam Leffler u_int8_t dh6opt_auth_rdm; 1891de50e9fSSam Leffler u_int8_t dh6opt_auth_rdinfo[8]; 1901de50e9fSSam Leffler /* authentication information follows */ 1911de50e9fSSam Leffler } __attribute__ ((__packed__)); 1921de50e9fSSam Leffler 1935b0fe478SBruce M Simpson static const char * 1945b0fe478SBruce M Simpson dhcp6opt_name(int type) 1955b0fe478SBruce M Simpson { 1965b0fe478SBruce M Simpson static char genstr[sizeof("opt_65535") + 1]; /* XXX thread unsafe */ 1975b0fe478SBruce M Simpson 1985b0fe478SBruce M Simpson if (type > 65535) 1995b0fe478SBruce M Simpson return "INVALID option"; 2005b0fe478SBruce M Simpson 2015b0fe478SBruce M Simpson switch(type) { 2025b0fe478SBruce M Simpson case DH6OPT_CLIENTID: 2035b0fe478SBruce M Simpson return "client ID"; 2045b0fe478SBruce M Simpson case DH6OPT_SERVERID: 2055b0fe478SBruce M Simpson return "server ID"; 2065b0fe478SBruce M Simpson case DH6OPT_IA_NA: 2075b0fe478SBruce M Simpson return "IA_NA"; 2085b0fe478SBruce M Simpson case DH6OPT_ORO: 2095b0fe478SBruce M Simpson return "option request"; 2105b0fe478SBruce M Simpson case DH6OPT_PREFERENCE: 2115b0fe478SBruce M Simpson return "preference"; 2125b0fe478SBruce M Simpson case DH6OPT_ELAPSED_TIME: 2135b0fe478SBruce M Simpson return "elapsed time"; 2145b0fe478SBruce M Simpson case DH6OPT_RELAY_MSG: 2155b0fe478SBruce M Simpson return "relay message"; 2161de50e9fSSam Leffler case DH6OPT_AUTH: 2171de50e9fSSam Leffler return "authentication"; 2181de50e9fSSam Leffler case DH6OPT_UNICAST: 2191de50e9fSSam Leffler return "server unicast"; 2205b0fe478SBruce M Simpson case DH6OPT_STATUS_CODE: 2215b0fe478SBruce M Simpson return "status code"; 2225b0fe478SBruce M Simpson case DH6OPT_RAPID_COMMIT: 2235b0fe478SBruce M Simpson return "rapid commit"; 2241de50e9fSSam Leffler case DH6OPT_USER_CLASS: 2251de50e9fSSam Leffler return "user class"; 2261de50e9fSSam Leffler case DH6OPT_VENDOR_CLASS: 2271de50e9fSSam Leffler return "vendor class"; 2281de50e9fSSam Leffler case DH6OPT_VENDOR_OPTS: 2291de50e9fSSam Leffler return "vendor-specific info"; 2305b0fe478SBruce M Simpson case DH6OPT_INTERFACE_ID: 2315b0fe478SBruce M Simpson return "interface ID"; 2325b0fe478SBruce M Simpson case DH6OPT_RECONF_MSG: 2335b0fe478SBruce M Simpson return "reconfigure message"; 2345b0fe478SBruce M Simpson case DH6OPT_RECONF_ACCEPT: 2355b0fe478SBruce M Simpson return "reconfigure accept"; 2365b0fe478SBruce M Simpson case DH6OPT_SIP_SERVER_D: 2371de50e9fSSam Leffler return "SIP servers domain"; 2385b0fe478SBruce M Simpson case DH6OPT_SIP_SERVER_A: 2391de50e9fSSam Leffler return "SIP servers address"; 2405b0fe478SBruce M Simpson case DH6OPT_DNS: 2415b0fe478SBruce M Simpson return "DNS"; 2421de50e9fSSam Leffler case DH6OPT_DNSNAME: 2431de50e9fSSam Leffler return "DNS name"; 2445b0fe478SBruce M Simpson case DH6OPT_PREFIX_DELEGATION: 2455b0fe478SBruce M Simpson return "prefix delegation"; 2465b0fe478SBruce M Simpson case DH6OPT_PREFIX_INFORMATION: 2475b0fe478SBruce M Simpson return "prefix information"; 2485b0fe478SBruce M Simpson case DH6OPT_IA_PD: 2495b0fe478SBruce M Simpson return "IA_PD"; 2505b0fe478SBruce M Simpson case DH6OPT_IA_PD_PREFIX: 2515b0fe478SBruce M Simpson return "IA_PD prefix"; 2525b0fe478SBruce M Simpson case DH6OPT_NTP_SERVERS: 2535b0fe478SBruce M Simpson return "NTP Server"; 2541de50e9fSSam Leffler case DH6OPT_LIFETIME: 2551de50e9fSSam Leffler return "lifetime"; 2565b0fe478SBruce M Simpson default: 2575b0fe478SBruce M Simpson snprintf(genstr, sizeof(genstr), "opt_%d", type); 2585b0fe478SBruce M Simpson return(genstr); 2595b0fe478SBruce M Simpson } 2605b0fe478SBruce M Simpson } 2615b0fe478SBruce M Simpson 2625b0fe478SBruce M Simpson static const char * 2635b0fe478SBruce M Simpson dhcp6stcode(int code) 2645b0fe478SBruce M Simpson { 2655b0fe478SBruce M Simpson static char genstr[sizeof("code255") + 1]; /* XXX thread unsafe */ 2665b0fe478SBruce M Simpson 2675b0fe478SBruce M Simpson if (code > 255) 2685b0fe478SBruce M Simpson return "INVALID code"; 2695b0fe478SBruce M Simpson 2705b0fe478SBruce M Simpson switch(code) { 2715b0fe478SBruce M Simpson case DH6OPT_STCODE_SUCCESS: 2725b0fe478SBruce M Simpson return "success"; 2735b0fe478SBruce M Simpson case DH6OPT_STCODE_UNSPECFAIL: 2745b0fe478SBruce M Simpson return "unspec failure"; 2755b0fe478SBruce M Simpson case DH6OPT_STCODE_NOADDRAVAIL: 2765b0fe478SBruce M Simpson return "no addresses"; 2775b0fe478SBruce M Simpson case DH6OPT_STCODE_NOBINDING: 2785b0fe478SBruce M Simpson return "no binding"; 2795b0fe478SBruce M Simpson case DH6OPT_STCODE_NOTONLINK: 2805b0fe478SBruce M Simpson return "not on-link"; 2815b0fe478SBruce M Simpson case DH6OPT_STCODE_USEMULTICAST: 2825b0fe478SBruce M Simpson return "use multicast"; 2835b0fe478SBruce M Simpson case DH6OPT_STCODE_NOPREFIXAVAIL: 2845b0fe478SBruce M Simpson return "no prefixes"; 2855b0fe478SBruce M Simpson default: 2865b0fe478SBruce M Simpson snprintf(genstr, sizeof(genstr), "code%d", code); 2875b0fe478SBruce M Simpson return(genstr); 2885b0fe478SBruce M Simpson } 2895b0fe478SBruce M Simpson } 2905b0fe478SBruce M Simpson 291b0453382SBill Fenner static void 2925b0fe478SBruce M Simpson dhcp6opt_print(const u_char *cp, const u_char *ep) 293b0453382SBill Fenner { 2949afd0c29SBill Fenner struct dhcp6opt *dh6o; 2959afd0c29SBill Fenner u_char *tp; 2965b0fe478SBruce M Simpson size_t i; 2975b0fe478SBruce M Simpson u_int16_t opttype; 2989afd0c29SBill Fenner size_t optlen; 2995b0fe478SBruce M Simpson u_int16_t val16; 3005b0fe478SBruce M Simpson u_int32_t val32; 3015b0fe478SBruce M Simpson struct in6_addr addr6; 3025b0fe478SBruce M Simpson struct dhcp6_ia ia; 3035b0fe478SBruce M Simpson struct dhcp6_ia_prefix ia_prefix; 3041de50e9fSSam Leffler struct dhcp6_auth authopt; 3051de50e9fSSam Leffler u_int authinfolen, authrealmlen; 306b0453382SBill Fenner 307b0453382SBill Fenner if (cp == ep) 308b0453382SBill Fenner return; 309b0453382SBill Fenner while (cp < ep) { 3105b0fe478SBruce M Simpson if (ep < cp + sizeof(*dh6o)) 311b0453382SBill Fenner goto trunc; 3129afd0c29SBill Fenner dh6o = (struct dhcp6opt *)cp; 3135b0fe478SBruce M Simpson optlen = EXTRACT_16BITS(&dh6o->dh6opt_len); 3145b0fe478SBruce M Simpson if (ep < cp + sizeof(*dh6o) + optlen) 315b0453382SBill Fenner goto trunc; 3165b0fe478SBruce M Simpson opttype = EXTRACT_16BITS(&dh6o->dh6opt_type); 3175b0fe478SBruce M Simpson printf(" (%s", dhcp6opt_name(opttype)); 3185b0fe478SBruce M Simpson switch (opttype) { 3195b0fe478SBruce M Simpson case DH6OPT_CLIENTID: 3205b0fe478SBruce M Simpson case DH6OPT_SERVERID: 3219afd0c29SBill Fenner if (optlen < 2) { 3229afd0c29SBill Fenner /*(*/ 3235b0fe478SBruce M Simpson printf(" ?)"); 324b0453382SBill Fenner break; 325b0453382SBill Fenner } 3269afd0c29SBill Fenner tp = (u_char *)(dh6o + 1); 3275b0fe478SBruce M Simpson switch (EXTRACT_16BITS(tp)) { 3289afd0c29SBill Fenner case 1: 3299afd0c29SBill Fenner if (optlen >= 2 + 6) { 3305b0fe478SBruce M Simpson printf(" hwaddr/time type %u time %u ", 3315b0fe478SBruce M Simpson EXTRACT_16BITS(&tp[2]), 3325b0fe478SBruce M Simpson EXTRACT_32BITS(&tp[4])); 3339afd0c29SBill Fenner for (i = 8; i < optlen; i++) 3349afd0c29SBill Fenner printf("%02x", tp[i]); 3359afd0c29SBill Fenner /*(*/ 336b0453382SBill Fenner printf(")"); 3379afd0c29SBill Fenner } else { 3389afd0c29SBill Fenner /*(*/ 3395b0fe478SBruce M Simpson printf(" ?)"); 3409afd0c29SBill Fenner } 3419afd0c29SBill Fenner break; 3429afd0c29SBill Fenner case 2: 3439afd0c29SBill Fenner if (optlen >= 2 + 8) { 3449afd0c29SBill Fenner printf(" vid "); 3459afd0c29SBill Fenner for (i = 2; i < 2 + 8; i++) 3469afd0c29SBill Fenner printf("%02x", tp[i]); 3479afd0c29SBill Fenner /*(*/ 3489afd0c29SBill Fenner printf(")"); 3499afd0c29SBill Fenner } else { 3509afd0c29SBill Fenner /*(*/ 3515b0fe478SBruce M Simpson printf(" ?)"); 3529afd0c29SBill Fenner } 3539afd0c29SBill Fenner break; 3549afd0c29SBill Fenner case 3: 3559afd0c29SBill Fenner if (optlen >= 2 + 2) { 3569afd0c29SBill Fenner printf(" hwaddr type %u ", 3575b0fe478SBruce M Simpson EXTRACT_16BITS(&tp[2])); 3589afd0c29SBill Fenner for (i = 4; i < optlen; i++) 3599afd0c29SBill Fenner printf("%02x", tp[i]); 3609afd0c29SBill Fenner /*(*/ 3619afd0c29SBill Fenner printf(")"); 3629afd0c29SBill Fenner } else { 3639afd0c29SBill Fenner /*(*/ 3645b0fe478SBruce M Simpson printf(" ?)"); 3659afd0c29SBill Fenner } 3669afd0c29SBill Fenner break; 3675b0fe478SBruce M Simpson default: 3685b0fe478SBruce M Simpson printf(" type %d)", EXTRACT_16BITS(tp)); 3695b0fe478SBruce M Simpson break; 3705b0fe478SBruce M Simpson } 3715b0fe478SBruce M Simpson break; 3725b0fe478SBruce M Simpson case DH6OPT_ORO: 3735b0fe478SBruce M Simpson if (optlen % 2) { 3745b0fe478SBruce M Simpson printf(" ?)"); 3755b0fe478SBruce M Simpson break; 3765b0fe478SBruce M Simpson } 3775b0fe478SBruce M Simpson tp = (u_char *)(dh6o + 1); 3785b0fe478SBruce M Simpson for (i = 0; i < optlen; i += 2) { 3795b0fe478SBruce M Simpson u_int16_t opt; 3805b0fe478SBruce M Simpson 3815b0fe478SBruce M Simpson memcpy(&opt, &tp[i], sizeof(opt)); 3825b0fe478SBruce M Simpson printf(" %s", dhcp6opt_name(ntohs(opt))); 3835b0fe478SBruce M Simpson } 3845b0fe478SBruce M Simpson printf(")"); 3855b0fe478SBruce M Simpson break; 3865b0fe478SBruce M Simpson case DH6OPT_PREFERENCE: 3875b0fe478SBruce M Simpson if (optlen != 1) { 3885b0fe478SBruce M Simpson printf(" ?)"); 3895b0fe478SBruce M Simpson break; 3905b0fe478SBruce M Simpson } 3915b0fe478SBruce M Simpson printf(" %d)", *((u_char *)(dh6o + 1) + 1)); 3925b0fe478SBruce M Simpson break; 3935b0fe478SBruce M Simpson case DH6OPT_ELAPSED_TIME: 3945b0fe478SBruce M Simpson if (optlen != 2) { 3955b0fe478SBruce M Simpson printf(" ?)"); 3965b0fe478SBruce M Simpson break; 3975b0fe478SBruce M Simpson } 3985b0fe478SBruce M Simpson memcpy(&val16, dh6o + 1, sizeof(val16)); 3995b0fe478SBruce M Simpson val16 = ntohs(val16); 4005b0fe478SBruce M Simpson printf(" %d)", (int)val16); 4015b0fe478SBruce M Simpson break; 4025b0fe478SBruce M Simpson case DH6OPT_RELAY_MSG: 4035b0fe478SBruce M Simpson printf(" ("); 4045b0fe478SBruce M Simpson dhcp6_print((const u_char *)(dh6o + 1), optlen); 4055b0fe478SBruce M Simpson printf(")"); 4065b0fe478SBruce M Simpson break; 4071de50e9fSSam Leffler case DH6OPT_AUTH: 4081de50e9fSSam Leffler if (optlen < sizeof(authopt) - sizeof(*dh6o)) { 4091de50e9fSSam Leffler printf(" ?)"); 4101de50e9fSSam Leffler break; 4111de50e9fSSam Leffler } 4121de50e9fSSam Leffler memcpy(&authopt, dh6o, sizeof(authopt)); 4131de50e9fSSam Leffler switch (authopt.dh6opt_auth_proto) { 4141de50e9fSSam Leffler case DH6OPT_AUTHPROTO_DELAYED: 4151de50e9fSSam Leffler printf(" proto: delayed"); 4161de50e9fSSam Leffler break; 4171de50e9fSSam Leffler case DH6OPT_AUTHPROTO_RECONFIG: 4181de50e9fSSam Leffler printf(" proto: reconfigure"); 4191de50e9fSSam Leffler break; 4201de50e9fSSam Leffler default: 4211de50e9fSSam Leffler printf(" proto: %d", 4221de50e9fSSam Leffler authopt.dh6opt_auth_proto); 4231de50e9fSSam Leffler break; 4241de50e9fSSam Leffler } 4251de50e9fSSam Leffler switch (authopt.dh6opt_auth_alg) { 4261de50e9fSSam Leffler case DH6OPT_AUTHALG_HMACMD5: 4271de50e9fSSam Leffler /* XXX: may depend on the protocol */ 4281de50e9fSSam Leffler printf(", alg: HMAC-MD5"); 4291de50e9fSSam Leffler break; 4301de50e9fSSam Leffler default: 4311de50e9fSSam Leffler printf(", alg: %d", authopt.dh6opt_auth_alg); 4321de50e9fSSam Leffler break; 4331de50e9fSSam Leffler } 4341de50e9fSSam Leffler switch (authopt.dh6opt_auth_rdm) { 4351de50e9fSSam Leffler case DH6OPT_AUTHRDM_MONOCOUNTER: 4361de50e9fSSam Leffler printf(", RDM: mono"); 4371de50e9fSSam Leffler break; 4381de50e9fSSam Leffler default: 4391de50e9fSSam Leffler printf(", RDM: %d", authopt.dh6opt_auth_rdm); 4401de50e9fSSam Leffler break; 4411de50e9fSSam Leffler } 4421de50e9fSSam Leffler tp = (u_char *)&authopt.dh6opt_auth_rdinfo; 4431de50e9fSSam Leffler printf(", RD:"); 4441de50e9fSSam Leffler for (i = 0; i < 4; i++, tp += sizeof(val16)) 4451de50e9fSSam Leffler printf(" %04x", EXTRACT_16BITS(tp)); 4461de50e9fSSam Leffler 4471de50e9fSSam Leffler /* protocol dependent part */ 4481de50e9fSSam Leffler tp = (u_char *)dh6o + sizeof(authopt); 4491de50e9fSSam Leffler authinfolen = 4501de50e9fSSam Leffler optlen + sizeof(*dh6o) - sizeof(authopt); 4511de50e9fSSam Leffler switch (authopt.dh6opt_auth_proto) { 4521de50e9fSSam Leffler case DH6OPT_AUTHPROTO_DELAYED: 4531de50e9fSSam Leffler if (authinfolen == 0) 4541de50e9fSSam Leffler break; 4551de50e9fSSam Leffler if (authinfolen < 20) { 4561de50e9fSSam Leffler printf(" ??"); 4571de50e9fSSam Leffler break; 4581de50e9fSSam Leffler } 4591de50e9fSSam Leffler authrealmlen = authinfolen - 20; 4601de50e9fSSam Leffler if (authrealmlen > 0) { 4611de50e9fSSam Leffler printf(", realm: "); 4621de50e9fSSam Leffler } 4631de50e9fSSam Leffler for (i = 0; i < authrealmlen; i++, tp++) 4641de50e9fSSam Leffler printf("%02x", *tp); 4651de50e9fSSam Leffler printf(", key ID: %08x", EXTRACT_32BITS(tp)); 4661de50e9fSSam Leffler tp += 4; 4671de50e9fSSam Leffler printf(", HMAC-MD5:"); 4681de50e9fSSam Leffler for (i = 0; i < 4; i++, tp+= 4) 4691de50e9fSSam Leffler printf(" %08x", EXTRACT_32BITS(tp)); 4701de50e9fSSam Leffler break; 4711de50e9fSSam Leffler case DH6OPT_AUTHPROTO_RECONFIG: 4721de50e9fSSam Leffler if (authinfolen != 17) { 4731de50e9fSSam Leffler printf(" ??"); 4741de50e9fSSam Leffler break; 4751de50e9fSSam Leffler } 4761de50e9fSSam Leffler switch (*tp++) { 4771de50e9fSSam Leffler case DH6OPT_AUTHRECONFIG_KEY: 4781de50e9fSSam Leffler printf(" reconfig-key"); 4791de50e9fSSam Leffler break; 4801de50e9fSSam Leffler case DH6OPT_AUTHRECONFIG_HMACMD5: 4811de50e9fSSam Leffler printf(" type: HMAC-MD5"); 4821de50e9fSSam Leffler break; 4831de50e9fSSam Leffler default: 4841de50e9fSSam Leffler printf(" type: ??"); 4851de50e9fSSam Leffler break; 4861de50e9fSSam Leffler } 4871de50e9fSSam Leffler printf(" value:"); 4881de50e9fSSam Leffler for (i = 0; i < 4; i++, tp+= 4) 4891de50e9fSSam Leffler printf(" %08x", EXTRACT_32BITS(tp)); 4901de50e9fSSam Leffler break; 4911de50e9fSSam Leffler default: 4921de50e9fSSam Leffler printf(" ??"); 4931de50e9fSSam Leffler break; 4941de50e9fSSam Leffler } 4951de50e9fSSam Leffler 4961de50e9fSSam Leffler printf(")"); 4971de50e9fSSam Leffler break; 4985b0fe478SBruce M Simpson case DH6OPT_RAPID_COMMIT: /* nothing todo */ 4995b0fe478SBruce M Simpson printf(")"); 5005b0fe478SBruce M Simpson break; 5015b0fe478SBruce M Simpson case DH6OPT_INTERFACE_ID: 5025b0fe478SBruce M Simpson /* 5035b0fe478SBruce M Simpson * Since we cannot predict the encoding, print hex dump 5045b0fe478SBruce M Simpson * at most 10 characters. 5055b0fe478SBruce M Simpson */ 5065b0fe478SBruce M Simpson for (i = 0; i < optlen && i < 10; i++) 5075b0fe478SBruce M Simpson printf("%02x", ((u_char *)(dh6o + 1))[i]); 5085b0fe478SBruce M Simpson break; 5095b0fe478SBruce M Simpson case DH6OPT_RECONF_MSG: 5105b0fe478SBruce M Simpson tp = (u_char *)(dh6o + 1); 5115b0fe478SBruce M Simpson switch (*tp) { 5125b0fe478SBruce M Simpson case DH6_RENEW: 5135b0fe478SBruce M Simpson printf(" for renew)"); 5145b0fe478SBruce M Simpson break; 5155b0fe478SBruce M Simpson case DH6_INFORM_REQ: 5165b0fe478SBruce M Simpson printf(" for inf-req)"); 5175b0fe478SBruce M Simpson break; 5185b0fe478SBruce M Simpson default: 5195b0fe478SBruce M Simpson printf(" for ?\?\?(%02x))", *tp); 5205b0fe478SBruce M Simpson break; 5215b0fe478SBruce M Simpson } 5225b0fe478SBruce M Simpson break; 5235b0fe478SBruce M Simpson case DH6OPT_RECONF_ACCEPT: /* nothing todo */ 5245b0fe478SBruce M Simpson printf(")"); 5255b0fe478SBruce M Simpson break; 5265b0fe478SBruce M Simpson case DH6OPT_SIP_SERVER_A: 5279afd0c29SBill Fenner case DH6OPT_DNS: 5285b0fe478SBruce M Simpson case DH6OPT_NTP_SERVERS: 5299afd0c29SBill Fenner if (optlen % 16) { 5305b0fe478SBruce M Simpson printf(" ?)"); 5319afd0c29SBill Fenner break; 5329afd0c29SBill Fenner } 5339afd0c29SBill Fenner tp = (u_char *)(dh6o + 1); 5349afd0c29SBill Fenner for (i = 0; i < optlen; i += 16) 5359afd0c29SBill Fenner printf(" %s", ip6addr_string(&tp[i])); 5369afd0c29SBill Fenner printf(")"); 5375b0fe478SBruce M Simpson break; 5385b0fe478SBruce M Simpson case DH6OPT_PREFIX_DELEGATION: 5395b0fe478SBruce M Simpson dhcp6opt_print((u_char *)(dh6o + 1), 5405b0fe478SBruce M Simpson (u_char *)(dh6o + 1) + optlen); 5415b0fe478SBruce M Simpson printf(")"); 5425b0fe478SBruce M Simpson break; 5435b0fe478SBruce M Simpson case DH6OPT_PREFIX_INFORMATION: 5445b0fe478SBruce M Simpson if (optlen % 21) 5455b0fe478SBruce M Simpson printf(" ?)"); 5465b0fe478SBruce M Simpson memcpy(&addr6, (u_char *)(dh6o + 1) + 5, 5475b0fe478SBruce M Simpson sizeof(addr6)); 5485b0fe478SBruce M Simpson printf(" %s/%d", ip6addr_string(&addr6), 5495b0fe478SBruce M Simpson (int)*((u_char *)(dh6o + 1) + 4)); 5505b0fe478SBruce M Simpson memcpy(&val32, dh6o + 1, sizeof(val32)); 5515b0fe478SBruce M Simpson val32 = ntohl(val32); 5525b0fe478SBruce M Simpson if (val32 == DHCP6_DURATITION_INFINITE) 5535b0fe478SBruce M Simpson printf(" lease-duration: infinite)"); 5545b0fe478SBruce M Simpson else 5555b0fe478SBruce M Simpson printf(" lease-duration: %u)", val32); 5565b0fe478SBruce M Simpson break; 5575b0fe478SBruce M Simpson case DH6OPT_STATUS_CODE: 5585b0fe478SBruce M Simpson if (optlen < 2) { 5595b0fe478SBruce M Simpson printf(" ?)"); 5605b0fe478SBruce M Simpson break; 5615b0fe478SBruce M Simpson } 5625b0fe478SBruce M Simpson memcpy(&val16, (u_char *)(dh6o + 1), sizeof(val16)); 5635b0fe478SBruce M Simpson val16 = ntohs(val16); 5645b0fe478SBruce M Simpson printf(" %s)", dhcp6stcode(val16)); 5655b0fe478SBruce M Simpson break; 5665b0fe478SBruce M Simpson case DH6OPT_IA_NA: 5675b0fe478SBruce M Simpson case DH6OPT_IA_PD: 5685b0fe478SBruce M Simpson if (optlen < sizeof(ia) - 4) { 5695b0fe478SBruce M Simpson printf(" ?)"); 5705b0fe478SBruce M Simpson break; 5715b0fe478SBruce M Simpson } 5725b0fe478SBruce M Simpson memcpy(&ia, (u_char *)dh6o, sizeof(ia)); 5735b0fe478SBruce M Simpson ia.dh6opt_ia_iaid = ntohl(ia.dh6opt_ia_iaid); 5745b0fe478SBruce M Simpson ia.dh6opt_ia_t1 = ntohl(ia.dh6opt_ia_t1); 5755b0fe478SBruce M Simpson ia.dh6opt_ia_t2 = ntohl(ia.dh6opt_ia_t2); 5765b0fe478SBruce M Simpson printf(" IAID:%lu T1:%lu T2:%lu", 5775b0fe478SBruce M Simpson (unsigned long)ia.dh6opt_ia_iaid, 5785b0fe478SBruce M Simpson (unsigned long)ia.dh6opt_ia_t1, 5795b0fe478SBruce M Simpson (unsigned long)ia.dh6opt_ia_t2); 5805b0fe478SBruce M Simpson if (optlen > sizeof(ia) - 4) { 5815b0fe478SBruce M Simpson /* there are sub-options */ 5825b0fe478SBruce M Simpson dhcp6opt_print((u_char *)dh6o + sizeof(ia), 5835b0fe478SBruce M Simpson (u_char *)(dh6o + 1) + optlen); 5845b0fe478SBruce M Simpson } 5855b0fe478SBruce M Simpson printf(")"); 5865b0fe478SBruce M Simpson break; 5875b0fe478SBruce M Simpson case DH6OPT_IA_PD_PREFIX: 5885b0fe478SBruce M Simpson if (optlen < sizeof(ia_prefix) - 4) { 5895b0fe478SBruce M Simpson printf(" ?)"); 5905b0fe478SBruce M Simpson break; 5915b0fe478SBruce M Simpson } 5925b0fe478SBruce M Simpson memcpy(&ia_prefix, (u_char *)dh6o, sizeof(ia_prefix)); 5935b0fe478SBruce M Simpson printf(" %s/%d", 5945b0fe478SBruce M Simpson ip6addr_string(&ia_prefix.dh6opt_ia_prefix_addr), 5955b0fe478SBruce M Simpson ia_prefix.dh6opt_ia_prefix_plen); 5965b0fe478SBruce M Simpson ia_prefix.dh6opt_ia_prefix_pltime = 5975b0fe478SBruce M Simpson ntohl(ia_prefix.dh6opt_ia_prefix_pltime); 5985b0fe478SBruce M Simpson ia_prefix.dh6opt_ia_prefix_vltime = 5995b0fe478SBruce M Simpson ntohl(ia_prefix.dh6opt_ia_prefix_vltime); 6005b0fe478SBruce M Simpson printf(" pltime:%lu vltime:%lu", 6015b0fe478SBruce M Simpson (unsigned long)ia_prefix.dh6opt_ia_prefix_pltime, 6025b0fe478SBruce M Simpson (unsigned long)ia_prefix.dh6opt_ia_prefix_vltime); 6035b0fe478SBruce M Simpson if (optlen > sizeof(ia_prefix) - 4) { 6045b0fe478SBruce M Simpson /* there are sub-options */ 6055b0fe478SBruce M Simpson dhcp6opt_print((u_char *)dh6o + 6065b0fe478SBruce M Simpson sizeof(ia_prefix), 6075b0fe478SBruce M Simpson (u_char *)(dh6o + 1) + optlen); 6085b0fe478SBruce M Simpson } 6095b0fe478SBruce M Simpson printf(")"); 6105b0fe478SBruce M Simpson break; 6111de50e9fSSam Leffler case DH6OPT_LIFETIME: 6121de50e9fSSam Leffler if (optlen != 4) { 6131de50e9fSSam Leffler printf(" ?)"); 6141de50e9fSSam Leffler break; 6151de50e9fSSam Leffler } 6161de50e9fSSam Leffler memcpy(&val32, dh6o + 1, sizeof(val32)); 6171de50e9fSSam Leffler val32 = ntohl(val32); 6181de50e9fSSam Leffler printf(" %d)", (int)val32); 6191de50e9fSSam Leffler break; 6209afd0c29SBill Fenner default: 6215b0fe478SBruce M Simpson printf(")"); 6229afd0c29SBill Fenner break; 6239afd0c29SBill Fenner } 6249afd0c29SBill Fenner 6259afd0c29SBill Fenner cp += sizeof(*dh6o) + optlen; 626b0453382SBill Fenner } 627b0453382SBill Fenner return; 628b0453382SBill Fenner 629b0453382SBill Fenner trunc: 630b0453382SBill Fenner printf("[|dhcp6ext]"); 631b0453382SBill Fenner } 632b0453382SBill Fenner 633b0453382SBill Fenner /* 6349afd0c29SBill Fenner * Print dhcp6 packets 635b0453382SBill Fenner */ 636b0453382SBill Fenner void 6375b0fe478SBruce M Simpson dhcp6_print(const u_char *cp, u_int length) 638b0453382SBill Fenner { 6399afd0c29SBill Fenner struct dhcp6 *dh6; 6405b0fe478SBruce M Simpson struct dhcp6_relay *dh6relay; 6415b0fe478SBruce M Simpson const u_char *ep; 642b0453382SBill Fenner u_char *extp; 6439afd0c29SBill Fenner const char *name; 644b0453382SBill Fenner 645b0453382SBill Fenner printf("dhcp6"); 646b0453382SBill Fenner 647b0453382SBill Fenner ep = (u_char *)snapend; 6485b0fe478SBruce M Simpson if (cp + length < ep) 6495b0fe478SBruce M Simpson ep = cp + length; 650b0453382SBill Fenner 6519afd0c29SBill Fenner dh6 = (struct dhcp6 *)cp; 6525b0fe478SBruce M Simpson dh6relay = (struct dhcp6_relay *)cp; 6535b0fe478SBruce M Simpson TCHECK(dh6->dh6_xid); 654b0453382SBill Fenner switch (dh6->dh6_msgtype) { 6555b0fe478SBruce M Simpson case DH6_SOLICIT: 6565b0fe478SBruce M Simpson name = "solicit"; 6575b0fe478SBruce M Simpson break; 6585b0fe478SBruce M Simpson case DH6_ADVERTISE: 6595b0fe478SBruce M Simpson name = "advertise"; 6605b0fe478SBruce M Simpson break; 6615b0fe478SBruce M Simpson case DH6_REQUEST: 6625b0fe478SBruce M Simpson name = "request"; 6635b0fe478SBruce M Simpson break; 6645b0fe478SBruce M Simpson case DH6_CONFIRM: 6655b0fe478SBruce M Simpson name = "confirm"; 6665b0fe478SBruce M Simpson break; 6675b0fe478SBruce M Simpson case DH6_RENEW: 6685b0fe478SBruce M Simpson name = "renew"; 6695b0fe478SBruce M Simpson break; 6705b0fe478SBruce M Simpson case DH6_REBIND: 6715b0fe478SBruce M Simpson name = "rebind"; 6725b0fe478SBruce M Simpson break; 673b0453382SBill Fenner case DH6_REPLY: 6749afd0c29SBill Fenner name = "reply"; 6759afd0c29SBill Fenner break; 6765b0fe478SBruce M Simpson case DH6_RELEASE: 6775b0fe478SBruce M Simpson name = "release"; 6785b0fe478SBruce M Simpson break; 6795b0fe478SBruce M Simpson case DH6_DECLINE: 6805b0fe478SBruce M Simpson name = "decline"; 6815b0fe478SBruce M Simpson break; 6825b0fe478SBruce M Simpson case DH6_RECONFIGURE: 6835b0fe478SBruce M Simpson name = "reconfigure"; 6845b0fe478SBruce M Simpson break; 6859afd0c29SBill Fenner case DH6_INFORM_REQ: 6869afd0c29SBill Fenner name= "inf-req"; 6879afd0c29SBill Fenner break; 6885b0fe478SBruce M Simpson case DH6_RELAY_FORW: 6895b0fe478SBruce M Simpson name= "relay-fwd"; 6905b0fe478SBruce M Simpson break; 6915b0fe478SBruce M Simpson case DH6_RELAY_REPLY: 6925b0fe478SBruce M Simpson name= "relay-reply"; 6935b0fe478SBruce M Simpson break; 6949afd0c29SBill Fenner default: 6959afd0c29SBill Fenner name = NULL; 696b0453382SBill Fenner break; 697b0453382SBill Fenner } 6989afd0c29SBill Fenner 6999afd0c29SBill Fenner if (!vflag) { 7009afd0c29SBill Fenner if (name) 7019afd0c29SBill Fenner printf(" %s", name); 7025b0fe478SBruce M Simpson else if (dh6->dh6_msgtype != DH6_RELAY_FORW && 7035b0fe478SBruce M Simpson dh6->dh6_msgtype != DH6_RELAY_REPLY) { 7049afd0c29SBill Fenner printf(" msgtype-%u", dh6->dh6_msgtype); 7055b0fe478SBruce M Simpson } 7069afd0c29SBill Fenner return; 707b0453382SBill Fenner } 7089afd0c29SBill Fenner 7099afd0c29SBill Fenner /* XXX relay agent messages have to be handled differently */ 7109afd0c29SBill Fenner 7119afd0c29SBill Fenner if (name) 7129afd0c29SBill Fenner printf(" %s (", name); /*)*/ 7139afd0c29SBill Fenner else 7149afd0c29SBill Fenner printf(" msgtype-%u (", dh6->dh6_msgtype); /*)*/ 7155b0fe478SBruce M Simpson if (dh6->dh6_msgtype != DH6_RELAY_FORW && 7165b0fe478SBruce M Simpson dh6->dh6_msgtype != DH6_RELAY_REPLY) { 7175b0fe478SBruce M Simpson printf("xid=%x", EXTRACT_32BITS(&dh6->dh6_xid) & DH6_XIDMASK); 7189afd0c29SBill Fenner extp = (u_char *)(dh6 + 1); 7199afd0c29SBill Fenner dhcp6opt_print(extp, ep); 7205b0fe478SBruce M Simpson } else { /* relay messages */ 7215b0fe478SBruce M Simpson struct in6_addr addr6; 7225b0fe478SBruce M Simpson 7235b0fe478SBruce M Simpson TCHECK(dh6relay->dh6relay_peeraddr); 7245b0fe478SBruce M Simpson 7255b0fe478SBruce M Simpson memcpy(&addr6, dh6relay->dh6relay_linkaddr, sizeof (addr6)); 7265b0fe478SBruce M Simpson printf("linkaddr=%s", ip6addr_string(&addr6)); 7275b0fe478SBruce M Simpson 7285b0fe478SBruce M Simpson memcpy(&addr6, dh6relay->dh6relay_peeraddr, sizeof (addr6)); 7295b0fe478SBruce M Simpson printf(" peeraddr=%s", ip6addr_string(&addr6)); 7305b0fe478SBruce M Simpson 7315b0fe478SBruce M Simpson dhcp6opt_print((u_char *)(dh6relay + 1), ep); 7325b0fe478SBruce M Simpson } 733685295f4SBill Fenner /*(*/ 734b0453382SBill Fenner printf(")"); 735b0453382SBill Fenner return; 736b0453382SBill Fenner 737b0453382SBill Fenner trunc: 7389afd0c29SBill Fenner printf("[|dhcp6]"); 739b0453382SBill Fenner } 740