blob: 9859f76009d5953efffb8a0d9c2c60d4bcd23879 [file] [log] [blame]
Elliott Hughes892a68b2015-10-19 14:43:53 -07001/*
Elliott Hughes892a68b2015-10-19 14:43:53 -07002 * Copyright (c) 2013 The TCPDUMP project
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 *
14 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
15 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
16 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
17 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
18 * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
19 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
20 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
21 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
22 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
24 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25 * POSSIBILITY OF SUCH DAMAGE.
26 */
27
Elliott Hughese2e3bd12017-05-15 10:59:29 -070028/* \summary: Ad Hoc Configuration Protocol (AHCP) printer */
29
30/* Based on draft-chroboczek-ahcp-00 and source code of ahcpd-0.53 */
31
Elliott Hughes892a68b2015-10-19 14:43:53 -070032#ifdef HAVE_CONFIG_H
Elliott Hughes820eced2021-08-20 18:00:50 -070033#include <config.h>
Elliott Hughes892a68b2015-10-19 14:43:53 -070034#endif
35
Elliott Hughes820eced2021-08-20 18:00:50 -070036#include "netdissect-stdinc.h"
Elliott Hughes892a68b2015-10-19 14:43:53 -070037
Elliott Hughes820eced2021-08-20 18:00:50 -070038#define ND_LONGJMP_FROM_TCHECK
Elliott Hughese2e3bd12017-05-15 10:59:29 -070039#include "netdissect.h"
Elliott Hughes892a68b2015-10-19 14:43:53 -070040#include "extract.h"
41#include "addrtoname.h"
42
Elliott Hughes892a68b2015-10-19 14:43:53 -070043
44#define AHCP_MAGIC_NUMBER 43
45#define AHCP_VERSION_1 1
46#define AHCP1_HEADER_FIX_LEN 24
47#define AHCP1_BODY_MIN_LEN 4
48
49#define AHCP1_MSG_DISCOVER 0
50#define AHCP1_MSG_OFFER 1
51#define AHCP1_MSG_REQUEST 2
52#define AHCP1_MSG_ACK 3
53#define AHCP1_MSG_NACK 4
54#define AHCP1_MSG_RELEASE 5
55
56static const struct tok ahcp1_msg_str[] = {
57 { AHCP1_MSG_DISCOVER, "Discover" },
58 { AHCP1_MSG_OFFER, "Offer" },
59 { AHCP1_MSG_REQUEST, "Request" },
60 { AHCP1_MSG_ACK, "Ack" },
61 { AHCP1_MSG_NACK, "Nack" },
62 { AHCP1_MSG_RELEASE, "Release" },
63 { 0, NULL }
64};
65
66#define AHCP1_OPT_PAD 0
67#define AHCP1_OPT_MANDATORY 1
68#define AHCP1_OPT_ORIGIN_TIME 2
69#define AHCP1_OPT_EXPIRES 3
70#define AHCP1_OPT_MY_IPV6_ADDRESS 4
71#define AHCP1_OPT_MY_IPV4_ADDRESS 5
72#define AHCP1_OPT_IPV6_PREFIX 6
73#define AHCP1_OPT_IPV4_PREFIX 7
74#define AHCP1_OPT_IPV6_ADDRESS 8
75#define AHCP1_OPT_IPV4_ADDRESS 9
76#define AHCP1_OPT_IPV6_PREFIX_DELEGATION 10
77#define AHCP1_OPT_IPV4_PREFIX_DELEGATION 11
78#define AHCP1_OPT_NAME_SERVER 12
79#define AHCP1_OPT_NTP_SERVER 13
80#define AHCP1_OPT_MAX 13
81
82static const struct tok ahcp1_opt_str[] = {
83 { AHCP1_OPT_PAD, "Pad" },
84 { AHCP1_OPT_MANDATORY, "Mandatory" },
85 { AHCP1_OPT_ORIGIN_TIME, "Origin Time" },
86 { AHCP1_OPT_EXPIRES, "Expires" },
87 { AHCP1_OPT_MY_IPV6_ADDRESS, "My-IPv6-Address" },
88 { AHCP1_OPT_MY_IPV4_ADDRESS, "My-IPv4-Address" },
89 { AHCP1_OPT_IPV6_PREFIX, "IPv6 Prefix" },
90 { AHCP1_OPT_IPV4_PREFIX, "IPv4 Prefix" },
91 { AHCP1_OPT_IPV6_ADDRESS, "IPv6 Address" },
92 { AHCP1_OPT_IPV4_ADDRESS, "IPv4 Address" },
93 { AHCP1_OPT_IPV6_PREFIX_DELEGATION, "IPv6 Prefix Delegation" },
94 { AHCP1_OPT_IPV4_PREFIX_DELEGATION, "IPv4 Prefix Delegation" },
95 { AHCP1_OPT_NAME_SERVER, "Name Server" },
96 { AHCP1_OPT_NTP_SERVER, "NTP Server" },
97 { 0, NULL }
98};
99
Elliott Hughes820eced2021-08-20 18:00:50 -0700100static void
101ahcp_time_print(netdissect_options *ndo,
102 const u_char *cp, uint8_t len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700103{
104 time_t t;
105 struct tm *tm;
106 char buf[BUFSIZE];
107
Elliott Hughes820eced2021-08-20 18:00:50 -0700108 if (len != 4)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700109 goto invalid;
Elliott Hughes820eced2021-08-20 18:00:50 -0700110 t = GET_BE_U_4(cp);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700111 if (NULL == (tm = gmtime(&t)))
Elliott Hughes820eced2021-08-20 18:00:50 -0700112 ND_PRINT(": gmtime() error");
Elliott Hughes892a68b2015-10-19 14:43:53 -0700113 else if (0 == strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", tm))
Elliott Hughes820eced2021-08-20 18:00:50 -0700114 ND_PRINT(": strftime() error");
Elliott Hughes892a68b2015-10-19 14:43:53 -0700115 else
Elliott Hughes820eced2021-08-20 18:00:50 -0700116 ND_PRINT(": %s UTC", buf);
117 return;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700118
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700119invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700120 nd_print_invalid(ndo);
121 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700122}
123
Elliott Hughes820eced2021-08-20 18:00:50 -0700124static void
125ahcp_seconds_print(netdissect_options *ndo,
126 const u_char *cp, uint8_t len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700127{
Elliott Hughes820eced2021-08-20 18:00:50 -0700128 if (len != 4)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700129 goto invalid;
Elliott Hughes820eced2021-08-20 18:00:50 -0700130 ND_PRINT(": %us", GET_BE_U_4(cp));
131 return;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700132
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700133invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700134 nd_print_invalid(ndo);
135 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700136}
137
Elliott Hughes820eced2021-08-20 18:00:50 -0700138static void
139ahcp_ipv6_addresses_print(netdissect_options *ndo,
140 const u_char *cp, uint8_t len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700141{
142 const char *sep = ": ";
143
Elliott Hughes820eced2021-08-20 18:00:50 -0700144 while (len) {
145 if (len < 16)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700146 goto invalid;
Elliott Hughes820eced2021-08-20 18:00:50 -0700147 ND_PRINT("%s%s", sep, GET_IP6ADDR_STRING(cp));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700148 cp += 16;
Elliott Hughes820eced2021-08-20 18:00:50 -0700149 len -= 16;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700150 sep = ", ";
151 }
Elliott Hughes820eced2021-08-20 18:00:50 -0700152 return;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700153
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700154invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700155 nd_print_invalid(ndo);
156 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700157}
158
Elliott Hughes820eced2021-08-20 18:00:50 -0700159static void
160ahcp_ipv4_addresses_print(netdissect_options *ndo,
161 const u_char *cp, uint8_t len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700162{
163 const char *sep = ": ";
164
Elliott Hughes820eced2021-08-20 18:00:50 -0700165 while (len) {
166 if (len < 4)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700167 goto invalid;
Elliott Hughes820eced2021-08-20 18:00:50 -0700168 ND_PRINT("%s%s", sep, GET_IPADDR_STRING(cp));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700169 cp += 4;
Elliott Hughes820eced2021-08-20 18:00:50 -0700170 len -= 4;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700171 sep = ", ";
172 }
Elliott Hughes820eced2021-08-20 18:00:50 -0700173 return;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700174
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700175invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700176 nd_print_invalid(ndo);
177 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700178}
179
Elliott Hughes820eced2021-08-20 18:00:50 -0700180static void
181ahcp_ipv6_prefixes_print(netdissect_options *ndo,
182 const u_char *cp, uint8_t len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700183{
184 const char *sep = ": ";
185
Elliott Hughes820eced2021-08-20 18:00:50 -0700186 while (len) {
187 if (len < 17)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700188 goto invalid;
Elliott Hughes820eced2021-08-20 18:00:50 -0700189 ND_PRINT("%s%s/%u", sep, GET_IP6ADDR_STRING(cp), GET_U_1(cp + 16));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700190 cp += 17;
Elliott Hughes820eced2021-08-20 18:00:50 -0700191 len -= 17;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700192 sep = ", ";
193 }
Elliott Hughes820eced2021-08-20 18:00:50 -0700194 return;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700195
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700196invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700197 nd_print_invalid(ndo);
198 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700199}
200
Elliott Hughes820eced2021-08-20 18:00:50 -0700201static void
202ahcp_ipv4_prefixes_print(netdissect_options *ndo,
203 const u_char *cp, uint8_t len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700204{
205 const char *sep = ": ";
206
Elliott Hughes820eced2021-08-20 18:00:50 -0700207 while (len) {
208 if (len < 5)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700209 goto invalid;
Elliott Hughes820eced2021-08-20 18:00:50 -0700210 ND_PRINT("%s%s/%u", sep, GET_IPADDR_STRING(cp), GET_U_1(cp + 4));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700211 cp += 5;
Elliott Hughes820eced2021-08-20 18:00:50 -0700212 len -= 5;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700213 sep = ", ";
214 }
Elliott Hughes820eced2021-08-20 18:00:50 -0700215 return;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700216
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700217invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700218 nd_print_invalid(ndo);
219 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700220}
221
Elliott Hughes820eced2021-08-20 18:00:50 -0700222static void
223(* const data_decoders[AHCP1_OPT_MAX + 1])(netdissect_options *, const u_char *, uint8_t) = {
Elliott Hughes892a68b2015-10-19 14:43:53 -0700224 /* [AHCP1_OPT_PAD] = */ NULL,
225 /* [AHCP1_OPT_MANDATORY] = */ NULL,
226 /* [AHCP1_OPT_ORIGIN_TIME] = */ ahcp_time_print,
227 /* [AHCP1_OPT_EXPIRES] = */ ahcp_seconds_print,
228 /* [AHCP1_OPT_MY_IPV6_ADDRESS] = */ ahcp_ipv6_addresses_print,
229 /* [AHCP1_OPT_MY_IPV4_ADDRESS] = */ ahcp_ipv4_addresses_print,
230 /* [AHCP1_OPT_IPV6_PREFIX] = */ ahcp_ipv6_prefixes_print,
231 /* [AHCP1_OPT_IPV4_PREFIX] = */ NULL,
232 /* [AHCP1_OPT_IPV6_ADDRESS] = */ ahcp_ipv6_addresses_print,
233 /* [AHCP1_OPT_IPV4_ADDRESS] = */ ahcp_ipv4_addresses_print,
234 /* [AHCP1_OPT_IPV6_PREFIX_DELEGATION] = */ ahcp_ipv6_prefixes_print,
235 /* [AHCP1_OPT_IPV4_PREFIX_DELEGATION] = */ ahcp_ipv4_prefixes_print,
236 /* [AHCP1_OPT_NAME_SERVER] = */ ahcp_ipv6_addresses_print,
237 /* [AHCP1_OPT_NTP_SERVER] = */ ahcp_ipv6_addresses_print,
238};
239
240static void
Elliott Hughes820eced2021-08-20 18:00:50 -0700241ahcp1_options_print(netdissect_options *ndo,
242 const u_char *cp, uint16_t len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700243{
Elliott Hughes820eced2021-08-20 18:00:50 -0700244 while (len) {
245 uint8_t option_no, option_len;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700246
Elliott Hughes892a68b2015-10-19 14:43:53 -0700247 /* Option no */
Elliott Hughes820eced2021-08-20 18:00:50 -0700248 option_no = GET_U_1(cp);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700249 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700250 len -= 1;
251 ND_PRINT("\n\t %s", tok2str(ahcp1_opt_str, "Unknown-%u", option_no));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700252 if (option_no == AHCP1_OPT_PAD || option_no == AHCP1_OPT_MANDATORY)
253 continue;
254 /* Length */
Elliott Hughes820eced2021-08-20 18:00:50 -0700255 if (!len)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700256 goto invalid;
Elliott Hughes820eced2021-08-20 18:00:50 -0700257 option_len = GET_U_1(cp);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700258 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700259 len -= 1;
260 if (option_len > len)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700261 goto invalid;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700262 /* Value */
263 if (option_no <= AHCP1_OPT_MAX && data_decoders[option_no] != NULL) {
Elliott Hughes820eced2021-08-20 18:00:50 -0700264 data_decoders[option_no](ndo, cp, option_len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700265 } else {
Elliott Hughes820eced2021-08-20 18:00:50 -0700266 ND_PRINT(" (Length %u)", option_len);
267 ND_TCHECK_LEN(cp, option_len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700268 }
269 cp += option_len;
Elliott Hughes820eced2021-08-20 18:00:50 -0700270 len -= option_len;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700271 }
272 return;
273
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700274invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700275 nd_print_invalid(ndo);
276 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700277}
278
279static void
Elliott Hughes820eced2021-08-20 18:00:50 -0700280ahcp1_body_print(netdissect_options *ndo,
281 const u_char *cp, u_int len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700282{
283 uint8_t type, mbz;
284 uint16_t body_len;
285
Elliott Hughes820eced2021-08-20 18:00:50 -0700286 if (len < AHCP1_BODY_MIN_LEN)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700287 goto invalid;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700288 /* Type */
Elliott Hughes820eced2021-08-20 18:00:50 -0700289 type = GET_U_1(cp);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700290 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700291 len -= 1;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700292 /* MBZ */
Elliott Hughes820eced2021-08-20 18:00:50 -0700293 mbz = GET_U_1(cp);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700294 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700295 len -= 1;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700296 /* Length */
Elliott Hughes820eced2021-08-20 18:00:50 -0700297 body_len = GET_BE_U_2(cp);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700298 cp += 2;
Elliott Hughes820eced2021-08-20 18:00:50 -0700299 len -= 2;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700300
301 if (ndo->ndo_vflag) {
Elliott Hughes820eced2021-08-20 18:00:50 -0700302 ND_PRINT("\n\t%s", tok2str(ahcp1_msg_str, "Unknown-%u", type));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700303 if (mbz != 0)
Elliott Hughes820eced2021-08-20 18:00:50 -0700304 ND_PRINT(", MBZ %u", mbz);
305 ND_PRINT(", Length %u", body_len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700306 }
Elliott Hughes820eced2021-08-20 18:00:50 -0700307 if (body_len > len)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700308 goto invalid;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700309
310 /* Options */
Elliott Hughes820eced2021-08-20 18:00:50 -0700311 /* Here use "body_len", not "len" (ignore any extra data). */
Elliott Hughes892a68b2015-10-19 14:43:53 -0700312 if (ndo->ndo_vflag >= 2)
Elliott Hughes820eced2021-08-20 18:00:50 -0700313 ahcp1_options_print(ndo, cp, body_len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700314 else
Elliott Hughes820eced2021-08-20 18:00:50 -0700315 ND_TCHECK_LEN(cp, body_len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700316 return;
317
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700318invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700319 nd_print_invalid(ndo);
320 ND_TCHECK_LEN(cp, len);
321
Elliott Hughes892a68b2015-10-19 14:43:53 -0700322}
323
324void
Elliott Hughes820eced2021-08-20 18:00:50 -0700325ahcp_print(netdissect_options *ndo,
326 const u_char *cp, u_int len)
Elliott Hughes892a68b2015-10-19 14:43:53 -0700327{
Elliott Hughes892a68b2015-10-19 14:43:53 -0700328 uint8_t version;
329
Elliott Hughes820eced2021-08-20 18:00:50 -0700330 ndo->ndo_protocol = "ahcp";
331 nd_print_protocol_caps(ndo);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700332 if (len < 2)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700333 goto invalid;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700334 /* Magic */
Elliott Hughes820eced2021-08-20 18:00:50 -0700335 if (GET_U_1(cp) != AHCP_MAGIC_NUMBER)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700336 goto invalid;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700337 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700338 len -= 1;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700339 /* Version */
Elliott Hughes820eced2021-08-20 18:00:50 -0700340 version = GET_U_1(cp);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700341 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700342 len -= 1;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700343 switch (version) {
344 case AHCP_VERSION_1: {
Elliott Hughes820eced2021-08-20 18:00:50 -0700345 ND_PRINT(" Version 1");
346 if (len < AHCP1_HEADER_FIX_LEN - 2)
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700347 goto invalid;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700348 if (!ndo->ndo_vflag) {
Elliott Hughes820eced2021-08-20 18:00:50 -0700349 ND_TCHECK_LEN(cp, AHCP1_HEADER_FIX_LEN - 2);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700350 cp += AHCP1_HEADER_FIX_LEN - 2;
Elliott Hughes820eced2021-08-20 18:00:50 -0700351 len -= AHCP1_HEADER_FIX_LEN - 2;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700352 } else {
353 /* Hopcount */
Elliott Hughes820eced2021-08-20 18:00:50 -0700354 ND_PRINT("\n\tHopcount %u", GET_U_1(cp));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700355 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700356 len -= 1;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700357 /* Original Hopcount */
Elliott Hughes820eced2021-08-20 18:00:50 -0700358 ND_PRINT(", Original Hopcount %u", GET_U_1(cp));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700359 cp += 1;
Elliott Hughes820eced2021-08-20 18:00:50 -0700360 len -= 1;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700361 /* Nonce */
Elliott Hughes820eced2021-08-20 18:00:50 -0700362 ND_PRINT(", Nonce 0x%08x", GET_BE_U_4(cp));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700363 cp += 4;
Elliott Hughes820eced2021-08-20 18:00:50 -0700364 len -= 4;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700365 /* Source Id */
Elliott Hughes820eced2021-08-20 18:00:50 -0700366 ND_PRINT(", Source Id %s", GET_LINKADDR_STRING(cp, LINKADDR_OTHER, 8));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700367 cp += 8;
Elliott Hughes820eced2021-08-20 18:00:50 -0700368 len -= 8;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700369 /* Destination Id */
Elliott Hughes820eced2021-08-20 18:00:50 -0700370 ND_PRINT(", Destination Id %s", GET_LINKADDR_STRING(cp, LINKADDR_OTHER, 8));
Elliott Hughes892a68b2015-10-19 14:43:53 -0700371 cp += 8;
Elliott Hughes820eced2021-08-20 18:00:50 -0700372 len -= 8;
Elliott Hughes892a68b2015-10-19 14:43:53 -0700373 }
374 /* Body */
Elliott Hughes820eced2021-08-20 18:00:50 -0700375 ahcp1_body_print(ndo, cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700376 break;
377 }
378 default:
Elliott Hughes820eced2021-08-20 18:00:50 -0700379 ND_PRINT(" Version %u (unknown)", version);
380 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700381 break;
382 }
383 return;
384
Elliott Hughese2e3bd12017-05-15 10:59:29 -0700385invalid:
Elliott Hughes820eced2021-08-20 18:00:50 -0700386 nd_print_invalid(ndo);
387 ND_TCHECK_LEN(cp, len);
Elliott Hughes892a68b2015-10-19 14:43:53 -0700388}