]> The Tcpdump Group git mirrors - tcpdump/blob - print-isakmp.c
refine some past NDO conversions
[tcpdump] / print-isakmp.c
1 /*
2 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE 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 * 3. Neither the name of the project nor the names of its contributors
14 * may be used to endorse or promote products derived from this software
15 * without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27 * SUCH DAMAGE.
28 *
29 */
30
31 #define NETDISSECT_REWORKED
32 #ifdef HAVE_CONFIG_H
33 #include "config.h"
34 #endif
35
36 /* The functions from print-esp.c used in this file are only defined when both
37 * OpenSSL and evp.h are detected. Employ the same preprocessor device here.
38 */
39 #ifndef HAVE_OPENSSL_EVP_H
40 #undef HAVE_LIBCRYPTO
41 #endif
42
43 #include <tcpdump-stdinc.h>
44
45 #include <string.h>
46
47 #include "interface.h"
48 #include "addrtoname.h"
49 #include "extract.h" /* must come after interface.h */
50
51 #include "ip.h"
52 #ifdef INET6
53 #include "ip6.h"
54 #endif
55
56 /* refer to RFC 2408 */
57
58 typedef u_char cookie_t[8];
59 typedef u_char msgid_t[4];
60
61 #define PORT_ISAKMP 500
62
63 /* 3.1 ISAKMP Header Format (IKEv1 and IKEv2)
64 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
65 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
66 ! Initiator !
67 ! Cookie !
68 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
69 ! Responder !
70 ! Cookie !
71 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
72 ! Next Payload ! MjVer ! MnVer ! Exchange Type ! Flags !
73 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
74 ! Message ID !
75 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
76 ! Length !
77 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
78 */
79 struct isakmp {
80 cookie_t i_ck; /* Initiator Cookie */
81 cookie_t r_ck; /* Responder Cookie */
82 u_int8_t np; /* Next Payload Type */
83 u_int8_t vers;
84 #define ISAKMP_VERS_MAJOR 0xf0
85 #define ISAKMP_VERS_MAJOR_SHIFT 4
86 #define ISAKMP_VERS_MINOR 0x0f
87 #define ISAKMP_VERS_MINOR_SHIFT 0
88 u_int8_t etype; /* Exchange Type */
89 u_int8_t flags; /* Flags */
90 msgid_t msgid;
91 u_int32_t len; /* Length */
92 };
93
94 /* Next Payload Type */
95 #define ISAKMP_NPTYPE_NONE 0 /* NONE*/
96 #define ISAKMP_NPTYPE_SA 1 /* Security Association */
97 #define ISAKMP_NPTYPE_P 2 /* Proposal */
98 #define ISAKMP_NPTYPE_T 3 /* Transform */
99 #define ISAKMP_NPTYPE_KE 4 /* Key Exchange */
100 #define ISAKMP_NPTYPE_ID 5 /* Identification */
101 #define ISAKMP_NPTYPE_CERT 6 /* Certificate */
102 #define ISAKMP_NPTYPE_CR 7 /* Certificate Request */
103 #define ISAKMP_NPTYPE_HASH 8 /* Hash */
104 #define ISAKMP_NPTYPE_SIG 9 /* Signature */
105 #define ISAKMP_NPTYPE_NONCE 10 /* Nonce */
106 #define ISAKMP_NPTYPE_N 11 /* Notification */
107 #define ISAKMP_NPTYPE_D 12 /* Delete */
108 #define ISAKMP_NPTYPE_VID 13 /* Vendor ID */
109 #define ISAKMP_NPTYPE_v2E 46 /* v2 Encrypted payload */
110
111 #define IKEv1_MAJOR_VERSION 1
112 #define IKEv1_MINOR_VERSION 0
113
114 #define IKEv2_MAJOR_VERSION 2
115 #define IKEv2_MINOR_VERSION 0
116
117 /* Flags */
118 #define ISAKMP_FLAG_E 0x01 /* Encryption Bit */
119 #define ISAKMP_FLAG_C 0x02 /* Commit Bit */
120 #define ISAKMP_FLAG_extra 0x04
121
122 /* IKEv2 */
123 #define ISAKMP_FLAG_I (1 << 3) /* (I)nitiator */
124 #define ISAKMP_FLAG_V (1 << 4) /* (V)ersion */
125 #define ISAKMP_FLAG_R (1 << 5) /* (R)esponse */
126
127
128 /* 3.2 Payload Generic Header
129 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
130 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
131 ! Next Payload ! RESERVED ! Payload Length !
132 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
133 */
134 struct isakmp_gen {
135 u_int8_t np; /* Next Payload */
136 u_int8_t critical; /* bit 7 - critical, rest is RESERVED */
137 u_int16_t len; /* Payload Length */
138 };
139
140 /* 3.3 Data Attributes
141 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
142 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
143 !A! Attribute Type ! AF=0 Attribute Length !
144 !F! ! AF=1 Attribute Value !
145 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
146 . AF=0 Attribute Value .
147 . AF=1 Not Transmitted .
148 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
149 */
150 struct isakmp_data {
151 u_int16_t type; /* defined by DOI-spec, and Attribute Format */
152 u_int16_t lorv; /* if f equal 1, Attribute Length */
153 /* if f equal 0, Attribute Value */
154 /* if f equal 1, Attribute Value */
155 };
156
157 /* 3.4 Security Association Payload */
158 /* MAY NOT be used, because of being defined in ipsec-doi. */
159 /*
160 If the current payload is the last in the message,
161 then the value of the next payload field will be 0.
162 This field MUST NOT contain the
163 values for the Proposal or Transform payloads as they are considered
164 part of the security association negotiation. For example, this
165 field would contain the value "10" (Nonce payload) in the first
166 message of a Base Exchange (see Section 4.4) and the value "0" in the
167 first message of an Identity Protect Exchange (see Section 4.5).
168 */
169 struct ikev1_pl_sa {
170 struct isakmp_gen h;
171 u_int32_t doi; /* Domain of Interpretation */
172 u_int32_t sit; /* Situation */
173 };
174
175 /* 3.5 Proposal Payload */
176 /*
177 The value of the next payload field MUST only contain the value "2"
178 or "0". If there are additional Proposal payloads in the message,
179 then this field will be 2. If the current Proposal payload is the
180 last within the security association proposal, then this field will
181 be 0.
182 */
183 struct ikev1_pl_p {
184 struct isakmp_gen h;
185 u_int8_t p_no; /* Proposal # */
186 u_int8_t prot_id; /* Protocol */
187 u_int8_t spi_size; /* SPI Size */
188 u_int8_t num_t; /* Number of Transforms */
189 /* SPI */
190 };
191
192 /* 3.6 Transform Payload */
193 /*
194 The value of the next payload field MUST only contain the value "3"
195 or "0". If there are additional Transform payloads in the proposal,
196 then this field will be 3. If the current Transform payload is the
197 last within the proposal, then this field will be 0.
198 */
199 struct ikev1_pl_t {
200 struct isakmp_gen h;
201 u_int8_t t_no; /* Transform # */
202 u_int8_t t_id; /* Transform-Id */
203 u_int16_t reserved; /* RESERVED2 */
204 /* SA Attributes */
205 };
206
207 /* 3.7 Key Exchange Payload */
208 struct ikev1_pl_ke {
209 struct isakmp_gen h;
210 /* Key Exchange Data */
211 };
212
213 /* 3.8 Identification Payload */
214 /* MUST NOT to be used, because of being defined in ipsec-doi. */
215 struct ikev1_pl_id {
216 struct isakmp_gen h;
217 union {
218 u_int8_t id_type; /* ID Type */
219 u_int32_t doi_data; /* DOI Specific ID Data */
220 } d;
221 /* Identification Data */
222 };
223
224 /* 3.9 Certificate Payload */
225 struct ikev1_pl_cert {
226 struct isakmp_gen h;
227 u_int8_t encode; /* Cert Encoding */
228 char cert; /* Certificate Data */
229 /*
230 This field indicates the type of
231 certificate or certificate-related information contained in the
232 Certificate Data field.
233 */
234 };
235
236 /* 3.10 Certificate Request Payload */
237 struct ikev1_pl_cr {
238 struct isakmp_gen h;
239 u_int8_t num_cert; /* # Cert. Types */
240 /*
241 Certificate Types (variable length)
242 -- Contains a list of the types of certificates requested,
243 sorted in order of preference. Each individual certificate
244 type is 1 octet. This field is NOT requiredo
245 */
246 /* # Certificate Authorities (1 octet) */
247 /* Certificate Authorities (variable length) */
248 };
249
250 /* 3.11 Hash Payload */
251 /* may not be used, because of having only data. */
252 struct ikev1_pl_hash {
253 struct isakmp_gen h;
254 /* Hash Data */
255 };
256
257 /* 3.12 Signature Payload */
258 /* may not be used, because of having only data. */
259 struct ikev1_pl_sig {
260 struct isakmp_gen h;
261 /* Signature Data */
262 };
263
264 /* 3.13 Nonce Payload */
265 /* may not be used, because of having only data. */
266 struct ikev1_pl_nonce {
267 struct isakmp_gen h;
268 /* Nonce Data */
269 };
270
271 /* 3.14 Notification Payload */
272 struct ikev1_pl_n {
273 struct isakmp_gen h;
274 u_int32_t doi; /* Domain of Interpretation */
275 u_int8_t prot_id; /* Protocol-ID */
276 u_int8_t spi_size; /* SPI Size */
277 u_int16_t type; /* Notify Message Type */
278 /* SPI */
279 /* Notification Data */
280 };
281
282 /* 3.14.1 Notify Message Types */
283 /* NOTIFY MESSAGES - ERROR TYPES */
284 #define ISAKMP_NTYPE_INVALID_PAYLOAD_TYPE 1
285 #define ISAKMP_NTYPE_DOI_NOT_SUPPORTED 2
286 #define ISAKMP_NTYPE_SITUATION_NOT_SUPPORTED 3
287 #define ISAKMP_NTYPE_INVALID_COOKIE 4
288 #define ISAKMP_NTYPE_INVALID_MAJOR_VERSION 5
289 #define ISAKMP_NTYPE_INVALID_MINOR_VERSION 6
290 #define ISAKMP_NTYPE_INVALID_EXCHANGE_TYPE 7
291 #define ISAKMP_NTYPE_INVALID_FLAGS 8
292 #define ISAKMP_NTYPE_INVALID_MESSAGE_ID 9
293 #define ISAKMP_NTYPE_INVALID_PROTOCOL_ID 10
294 #define ISAKMP_NTYPE_INVALID_SPI 11
295 #define ISAKMP_NTYPE_INVALID_TRANSFORM_ID 12
296 #define ISAKMP_NTYPE_ATTRIBUTES_NOT_SUPPORTED 13
297 #define ISAKMP_NTYPE_NO_PROPOSAL_CHOSEN 14
298 #define ISAKMP_NTYPE_BAD_PROPOSAL_SYNTAX 15
299 #define ISAKMP_NTYPE_PAYLOAD_MALFORMED 16
300 #define ISAKMP_NTYPE_INVALID_KEY_INFORMATION 17
301 #define ISAKMP_NTYPE_INVALID_ID_INFORMATION 18
302 #define ISAKMP_NTYPE_INVALID_CERT_ENCODING 19
303 #define ISAKMP_NTYPE_INVALID_CERTIFICATE 20
304 #define ISAKMP_NTYPE_BAD_CERT_REQUEST_SYNTAX 21
305 #define ISAKMP_NTYPE_INVALID_CERT_AUTHORITY 22
306 #define ISAKMP_NTYPE_INVALID_HASH_INFORMATION 23
307 #define ISAKMP_NTYPE_AUTHENTICATION_FAILED 24
308 #define ISAKMP_NTYPE_INVALID_SIGNATURE 25
309 #define ISAKMP_NTYPE_ADDRESS_NOTIFICATION 26
310
311 /* 3.15 Delete Payload */
312 struct ikev1_pl_d {
313 struct isakmp_gen h;
314 u_int32_t doi; /* Domain of Interpretation */
315 u_int8_t prot_id; /* Protocol-Id */
316 u_int8_t spi_size; /* SPI Size */
317 u_int16_t num_spi; /* # of SPIs */
318 /* SPI(es) */
319 };
320
321 struct ikev1_ph1tab {
322 struct ikev1_ph1 *head;
323 struct ikev1_ph1 *tail;
324 int len;
325 };
326
327 struct isakmp_ph2tab {
328 struct ikev1_ph2 *head;
329 struct ikev1_ph2 *tail;
330 int len;
331 };
332
333 /* IKEv2 (RFC4306) */
334
335 /* 3.3 Security Association Payload -- generic header */
336 /* 3.3.1. Proposal Substructure */
337 struct ikev2_p {
338 struct isakmp_gen h;
339 u_int8_t p_no; /* Proposal # */
340 u_int8_t prot_id; /* Protocol */
341 u_int8_t spi_size; /* SPI Size */
342 u_int8_t num_t; /* Number of Transforms */
343 };
344
345 /* 3.3.2. Transform Substructure */
346 struct ikev2_t {
347 struct isakmp_gen h;
348 u_int8_t t_type; /* Transform Type (ENCR,PRF,INTEG,etc.*/
349 u_int8_t res2; /* reserved byte */
350 u_int16_t t_id; /* Transform ID */
351 };
352
353 enum ikev2_t_type {
354 IV2_T_ENCR = 1,
355 IV2_T_PRF = 2,
356 IV2_T_INTEG= 3,
357 IV2_T_DH = 4,
358 IV2_T_ESN = 5,
359 };
360
361 /* 3.4. Key Exchange Payload */
362 struct ikev2_ke {
363 struct isakmp_gen h;
364 u_int16_t ke_group;
365 u_int16_t ke_res1;
366 /* KE data */
367 };
368
369
370 /* 3.5. Identification Payloads */
371 enum ikev2_id_type {
372 ID_IPV4_ADDR=1,
373 ID_FQDN=2,
374 ID_RFC822_ADDR=3,
375 ID_IPV6_ADDR=5,
376 ID_DER_ASN1_DN=9,
377 ID_DER_ASN1_GN=10,
378 ID_KEY_ID=11,
379 };
380 struct ikev2_id {
381 struct isakmp_gen h;
382 u_int8_t type; /* ID type */
383 u_int8_t res1;
384 u_int16_t res2;
385 /* SPI */
386 /* Notification Data */
387 };
388
389 /* 3.10 Notification Payload */
390 struct ikev2_n {
391 struct isakmp_gen h;
392 u_int8_t prot_id; /* Protocol-ID */
393 u_int8_t spi_size; /* SPI Size */
394 u_int16_t type; /* Notify Message Type */
395 };
396
397 enum ikev2_n_type {
398 IV2_NOTIFY_UNSUPPORTED_CRITICAL_PAYLOAD = 1,
399 IV2_NOTIFY_INVALID_IKE_SPI = 4,
400 IV2_NOTIFY_INVALID_MAJOR_VERSION = 5,
401 IV2_NOTIFY_INVALID_SYNTAX = 7,
402 IV2_NOTIFY_INVALID_MESSAGE_ID = 9,
403 IV2_NOTIFY_INVALID_SPI =11,
404 IV2_NOTIFY_NO_PROPOSAL_CHOSEN =14,
405 IV2_NOTIFY_INVALID_KE_PAYLOAD =17,
406 IV2_NOTIFY_AUTHENTICATION_FAILED =24,
407 IV2_NOTIFY_SINGLE_PAIR_REQUIRED =34,
408 IV2_NOTIFY_NO_ADDITIONAL_SAS =35,
409 IV2_NOTIFY_INTERNAL_ADDRESS_FAILURE =36,
410 IV2_NOTIFY_FAILED_CP_REQUIRED =37,
411 IV2_NOTIFY_INVALID_SELECTORS =39,
412 IV2_NOTIFY_INITIAL_CONTACT =16384,
413 IV2_NOTIFY_SET_WINDOW_SIZE =16385,
414 IV2_NOTIFY_ADDITIONAL_TS_POSSIBLE =16386,
415 IV2_NOTIFY_IPCOMP_SUPPORTED =16387,
416 IV2_NOTIFY_NAT_DETECTION_SOURCE_IP =16388,
417 IV2_NOTIFY_NAT_DETECTION_DESTINATION_IP =16389,
418 IV2_NOTIFY_COOKIE =16390,
419 IV2_NOTIFY_USE_TRANSPORT_MODE =16391,
420 IV2_NOTIFY_HTTP_CERT_LOOKUP_SUPPORTED =16392,
421 IV2_NOTIFY_REKEY_SA =16393,
422 IV2_NOTIFY_ESP_TFC_PADDING_NOT_SUPPORTED =16394,
423 IV2_NOTIFY_NON_FIRST_FRAGMENTS_ALSO =16395
424 };
425
426 struct notify_messages {
427 u_int16_t type;
428 char *msg;
429 };
430
431 /* 3.8 Notification Payload */
432 struct ikev2_auth {
433 struct isakmp_gen h;
434 u_int8_t auth_method; /* Protocol-ID */
435 u_int8_t reserved[3];
436 /* authentication data */
437 };
438
439 enum ikev2_auth_type {
440 IV2_RSA_SIG = 1,
441 IV2_SHARED = 2,
442 IV2_DSS_SIG = 3,
443 };
444
445 /* refer to RFC 2409 */
446
447 #if 0
448 /* isakmp sa structure */
449 struct oakley_sa {
450 u_int8_t proto_id; /* OAKLEY */
451 vchar_t *spi; /* spi */
452 u_int8_t dhgrp; /* DH; group */
453 u_int8_t auth_t; /* method of authentication */
454 u_int8_t prf_t; /* type of prf */
455 u_int8_t hash_t; /* type of hash */
456 u_int8_t enc_t; /* type of cipher */
457 u_int8_t life_t; /* type of duration of lifetime */
458 u_int32_t ldur; /* life duration */
459 };
460 #endif
461
462 /* refer to RFC 2407 */
463
464 #define IPSEC_DOI 1
465
466 /* 4.2 IPSEC Situation Definition */
467 #define IPSECDOI_SIT_IDENTITY_ONLY 0x00000001
468 #define IPSECDOI_SIT_SECRECY 0x00000002
469 #define IPSECDOI_SIT_INTEGRITY 0x00000004
470
471 /* 4.4.1 IPSEC Security Protocol Identifiers */
472 /* 4.4.2 IPSEC ISAKMP Transform Values */
473 #define IPSECDOI_PROTO_ISAKMP 1
474 #define IPSECDOI_KEY_IKE 1
475
476 /* 4.4.1 IPSEC Security Protocol Identifiers */
477 #define IPSECDOI_PROTO_IPSEC_AH 2
478 /* 4.4.3 IPSEC AH Transform Values */
479 #define IPSECDOI_AH_MD5 2
480 #define IPSECDOI_AH_SHA 3
481 #define IPSECDOI_AH_DES 4
482 #define IPSECDOI_AH_SHA2_256 5
483 #define IPSECDOI_AH_SHA2_384 6
484 #define IPSECDOI_AH_SHA2_512 7
485
486 /* 4.4.1 IPSEC Security Protocol Identifiers */
487 #define IPSECDOI_PROTO_IPSEC_ESP 3
488 /* 4.4.4 IPSEC ESP Transform Identifiers */
489 #define IPSECDOI_ESP_DES_IV64 1
490 #define IPSECDOI_ESP_DES 2
491 #define IPSECDOI_ESP_3DES 3
492 #define IPSECDOI_ESP_RC5 4
493 #define IPSECDOI_ESP_IDEA 5
494 #define IPSECDOI_ESP_CAST 6
495 #define IPSECDOI_ESP_BLOWFISH 7
496 #define IPSECDOI_ESP_3IDEA 8
497 #define IPSECDOI_ESP_DES_IV32 9
498 #define IPSECDOI_ESP_RC4 10
499 #define IPSECDOI_ESP_NULL 11
500 #define IPSECDOI_ESP_RIJNDAEL 12
501 #define IPSECDOI_ESP_AES 12
502
503 /* 4.4.1 IPSEC Security Protocol Identifiers */
504 #define IPSECDOI_PROTO_IPCOMP 4
505 /* 4.4.5 IPSEC IPCOMP Transform Identifiers */
506 #define IPSECDOI_IPCOMP_OUI 1
507 #define IPSECDOI_IPCOMP_DEFLATE 2
508 #define IPSECDOI_IPCOMP_LZS 3
509
510 /* 4.5 IPSEC Security Association Attributes */
511 #define IPSECDOI_ATTR_SA_LTYPE 1 /* B */
512 #define IPSECDOI_ATTR_SA_LTYPE_DEFAULT 1
513 #define IPSECDOI_ATTR_SA_LTYPE_SEC 1
514 #define IPSECDOI_ATTR_SA_LTYPE_KB 2
515 #define IPSECDOI_ATTR_SA_LDUR 2 /* V */
516 #define IPSECDOI_ATTR_SA_LDUR_DEFAULT 28800 /* 8 hours */
517 #define IPSECDOI_ATTR_GRP_DESC 3 /* B */
518 #define IPSECDOI_ATTR_ENC_MODE 4 /* B */
519 /* default value: host dependent */
520 #define IPSECDOI_ATTR_ENC_MODE_TUNNEL 1
521 #define IPSECDOI_ATTR_ENC_MODE_TRNS 2
522 #define IPSECDOI_ATTR_AUTH 5 /* B */
523 /* 0 means not to use authentication. */
524 #define IPSECDOI_ATTR_AUTH_HMAC_MD5 1
525 #define IPSECDOI_ATTR_AUTH_HMAC_SHA1 2
526 #define IPSECDOI_ATTR_AUTH_DES_MAC 3
527 #define IPSECDOI_ATTR_AUTH_KPDK 4 /*RFC-1826(Key/Pad/Data/Key)*/
528 /*
529 * When negotiating ESP without authentication, the Auth
530 * Algorithm attribute MUST NOT be included in the proposal.
531 * When negotiating ESP without confidentiality, the Auth
532 * Algorithm attribute MUST be included in the proposal and
533 * the ESP transform ID must be ESP_NULL.
534 */
535 #define IPSECDOI_ATTR_KEY_LENGTH 6 /* B */
536 #define IPSECDOI_ATTR_KEY_ROUNDS 7 /* B */
537 #define IPSECDOI_ATTR_COMP_DICT_SIZE 8 /* B */
538 #define IPSECDOI_ATTR_COMP_PRIVALG 9 /* V */
539
540 /* 4.6.1 Security Association Payload */
541 struct ipsecdoi_sa {
542 struct isakmp_gen h;
543 u_int32_t doi; /* Domain of Interpretation */
544 u_int32_t sit; /* Situation */
545 };
546
547 struct ipsecdoi_secrecy_h {
548 u_int16_t len;
549 u_int16_t reserved;
550 };
551
552 /* 4.6.2.1 Identification Type Values */
553 struct ipsecdoi_id {
554 struct isakmp_gen h;
555 u_int8_t type; /* ID Type */
556 u_int8_t proto_id; /* Protocol ID */
557 u_int16_t port; /* Port */
558 /* Identification Data */
559 };
560
561 #define IPSECDOI_ID_IPV4_ADDR 1
562 #define IPSECDOI_ID_FQDN 2
563 #define IPSECDOI_ID_USER_FQDN 3
564 #define IPSECDOI_ID_IPV4_ADDR_SUBNET 4
565 #define IPSECDOI_ID_IPV6_ADDR 5
566 #define IPSECDOI_ID_IPV6_ADDR_SUBNET 6
567 #define IPSECDOI_ID_IPV4_ADDR_RANGE 7
568 #define IPSECDOI_ID_IPV6_ADDR_RANGE 8
569 #define IPSECDOI_ID_DER_ASN1_DN 9
570 #define IPSECDOI_ID_DER_ASN1_GN 10
571 #define IPSECDOI_ID_KEY_ID 11
572
573 /* 4.6.3 IPSEC DOI Notify Message Types */
574 /* Notify Messages - Status Types */
575 #define IPSECDOI_NTYPE_RESPONDER_LIFETIME 24576
576 #define IPSECDOI_NTYPE_REPLAY_STATUS 24577
577 #define IPSECDOI_NTYPE_INITIAL_CONTACT 24578
578
579 #define DECLARE_PRINTER(func) static const u_char *ike##func##_print( \
580 netdissect_options *ndo, u_char tpay, \
581 const struct isakmp_gen *ext, \
582 u_int item_len, \
583 const u_char *end_pointer, \
584 u_int32_t phase,\
585 u_int32_t doi0, \
586 u_int32_t proto0, int depth)
587
588 DECLARE_PRINTER(v1_sa);
589 DECLARE_PRINTER(v1_p);
590 DECLARE_PRINTER(v1_t);
591 DECLARE_PRINTER(v1_ke);
592 DECLARE_PRINTER(v1_id);
593 DECLARE_PRINTER(v1_cert);
594 DECLARE_PRINTER(v1_cr);
595 DECLARE_PRINTER(v1_sig);
596 DECLARE_PRINTER(v1_hash);
597 DECLARE_PRINTER(v1_nonce);
598 DECLARE_PRINTER(v1_n);
599 DECLARE_PRINTER(v1_d);
600 DECLARE_PRINTER(v1_vid);
601
602 DECLARE_PRINTER(v2_sa);
603 DECLARE_PRINTER(v2_ke);
604 DECLARE_PRINTER(v2_ID);
605 DECLARE_PRINTER(v2_cert);
606 DECLARE_PRINTER(v2_cr);
607 DECLARE_PRINTER(v2_auth);
608 DECLARE_PRINTER(v2_nonce);
609 DECLARE_PRINTER(v2_n);
610 DECLARE_PRINTER(v2_d);
611 DECLARE_PRINTER(v2_vid);
612 DECLARE_PRINTER(v2_TS);
613 DECLARE_PRINTER(v2_cp);
614 DECLARE_PRINTER(v2_eap);
615
616 static const u_char *ikev2_e_print(netdissect_options *ndo,
617 struct isakmp *base,
618 u_char tpay,
619 const struct isakmp_gen *ext,
620 u_int item_len,
621 const u_char *end_pointer,
622 u_int32_t phase,
623 u_int32_t doi0,
624 u_int32_t proto0, int depth);
625
626
627 static const u_char *ike_sub0_print(netdissect_options *ndo,u_char, const struct isakmp_gen *,
628 const u_char *, u_int32_t, u_int32_t, u_int32_t, int);
629 static const u_char *ikev1_sub_print(netdissect_options *ndo,u_char, const struct isakmp_gen *,
630 const u_char *, u_int32_t, u_int32_t, u_int32_t, int);
631
632 static const u_char *ikev2_sub_print(netdissect_options *ndo,
633 struct isakmp *base,
634 u_char np, const struct isakmp_gen *ext,
635 const u_char *ep, u_int32_t phase,
636 u_int32_t doi, u_int32_t proto,
637 int depth);
638
639
640 static char *numstr(int);
641
642 static void
643 ikev1_print(netdissect_options *ndo,
644 const u_char *bp, u_int length,
645 const u_char *bp2, struct isakmp *base);
646
647 #define MAXINITIATORS 20
648 int ninitiator = 0;
649 union inaddr_u {
650 struct in_addr in4;
651 #ifdef INET6
652 struct in6_addr in6;
653 #endif
654 };
655 struct {
656 cookie_t initiator;
657 u_int version;
658 union inaddr_u iaddr;
659 union inaddr_u raddr;
660 } cookiecache[MAXINITIATORS];
661
662 /* protocol id */
663 static const char *protoidstr[] = {
664 NULL, "isakmp", "ipsec-ah", "ipsec-esp", "ipcomp",
665 };
666
667 /* isakmp->np */
668 static const char *npstr[] = {
669 "none", "sa", "p", "t", "ke", "id", "cert", "cr", "hash", /* 0 - 8 */
670 "sig", "nonce", "n", "d", "vid", /* 9 - 13 */
671 "pay14", "pay15", "pay16", "pay17", "pay18", /* 14- 18 */
672 "pay19", "pay20", "pay21", "pay22", "pay23", /* 19- 23 */
673 "pay24", "pay25", "pay26", "pay27", "pay28", /* 24- 28 */
674 "pay29", "pay30", "pay31", "pay32", /* 29- 32 */
675 "v2sa", "v2ke", "v2IDi", "v2IDr", "v2cert",/* 33- 37 */
676 "v2cr", "v2auth","v2nonce", "v2n", "v2d", /* 38- 42 */
677 "v2vid", "v2TSi", "v2TSr", "v2e", "v2cp", /* 43- 47 */
678 "v2eap", /* 48 */
679
680 };
681
682 /* isakmp->np */
683 static const u_char *(*npfunc[])(netdissect_options *ndo, u_char tpay,
684 const struct isakmp_gen *ext,
685 u_int item_len,
686 const u_char *end_pointer,
687 u_int32_t phase,
688 u_int32_t doi0,
689 u_int32_t proto0, int depth) = {
690 NULL,
691 ikev1_sa_print,
692 ikev1_p_print,
693 ikev1_t_print,
694 ikev1_ke_print,
695 ikev1_id_print,
696 ikev1_cert_print,
697 ikev1_cr_print,
698 ikev1_hash_print,
699 ikev1_sig_print,
700 ikev1_nonce_print,
701 ikev1_n_print,
702 ikev1_d_print,
703 ikev1_vid_print, /* 13 */
704 NULL, NULL, NULL, NULL, NULL, /* 14- 18 */
705 NULL, NULL, NULL, NULL, NULL, /* 19- 23 */
706 NULL, NULL, NULL, NULL, NULL, /* 24- 28 */
707 NULL, NULL, NULL, NULL, /* 29- 32 */
708 ikev2_sa_print, /* 33 */
709 ikev2_ke_print, /* 34 */
710 ikev2_ID_print, /* 35 */
711 ikev2_ID_print, /* 36 */
712 ikev2_cert_print, /* 37 */
713 ikev2_cr_print, /* 38 */
714 ikev2_auth_print, /* 39 */
715 ikev2_nonce_print, /* 40 */
716 ikev2_n_print, /* 41 */
717 ikev2_d_print, /* 42 */
718 ikev2_vid_print, /* 43 */
719 ikev2_TS_print, /* 44 */
720 ikev2_TS_print, /* 45 */
721 NULL, /* ikev2_e_print,*/ /* 46 - special */
722 ikev2_cp_print, /* 47 */
723 ikev2_eap_print, /* 48 */
724 };
725
726 /* isakmp->etype */
727 static const char *etypestr[] = {
728 /* IKEv1 exchange types */
729 "none", "base", "ident", "auth", "agg", "inf", NULL, NULL, /* 0-7 */
730 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, /* 8-15 */
731 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, /* 16-23 */
732 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, /* 24-31 */
733 "oakley-quick", "oakley-newgroup", /* 32-33 */
734 /* IKEv2 exchange types */
735 "ikev2_init", "ikev2_auth", "child_sa", "inf2" /* 34-37 */
736 };
737
738 #define STR_OR_ID(x, tab) \
739 (((x) < sizeof(tab)/sizeof(tab[0]) && tab[(x)]) ? tab[(x)] : numstr(x))
740 #define PROTOIDSTR(x) STR_OR_ID(x, protoidstr)
741 #define NPSTR(x) STR_OR_ID(x, npstr)
742 #define ETYPESTR(x) STR_OR_ID(x, etypestr)
743
744 #define CHECKLEN(p, np) \
745 if (ep < (u_char *)(p)) { \
746 ND_PRINT((ndo," [|%s]", NPSTR(np))); \
747 goto done; \
748 }
749
750
751 #define NPFUNC(x) \
752 (((x) < sizeof(npfunc)/sizeof(npfunc[0]) && npfunc[(x)]) \
753 ? npfunc[(x)] : NULL)
754
755 static int
756 iszero(u_char *p, size_t l)
757 {
758 while (l--) {
759 if (*p++)
760 return 0;
761 }
762 return 1;
763 }
764
765 /* find cookie from initiator cache */
766 static int
767 cookie_find(cookie_t *in)
768 {
769 int i;
770
771 for (i = 0; i < MAXINITIATORS; i++) {
772 if (memcmp(in, &cookiecache[i].initiator, sizeof(*in)) == 0)
773 return i;
774 }
775
776 return -1;
777 }
778
779 /* record initiator */
780 static void
781 cookie_record(cookie_t *in, const u_char *bp2)
782 {
783 int i;
784 struct ip *ip;
785 #ifdef INET6
786 struct ip6_hdr *ip6;
787 #endif
788
789 i = cookie_find(in);
790 if (0 <= i) {
791 ninitiator = (i + 1) % MAXINITIATORS;
792 return;
793 }
794
795 ip = (struct ip *)bp2;
796 switch (IP_V(ip)) {
797 case 4:
798 cookiecache[ninitiator].version = 4;
799 UNALIGNED_MEMCPY(&cookiecache[ninitiator].iaddr.in4, &ip->ip_src, sizeof(struct in_addr));
800 UNALIGNED_MEMCPY(&cookiecache[ninitiator].raddr.in4, &ip->ip_dst, sizeof(struct in_addr));
801 break;
802 #ifdef INET6
803 case 6:
804 ip6 = (struct ip6_hdr *)bp2;
805 cookiecache[ninitiator].version = 6;
806 UNALIGNED_MEMCPY(&cookiecache[ninitiator].iaddr.in6, &ip6->ip6_src, sizeof(struct in6_addr));
807 UNALIGNED_MEMCPY(&cookiecache[ninitiator].raddr.in6, &ip6->ip6_dst, sizeof(struct in6_addr));
808 break;
809 #endif
810 default:
811 return;
812 }
813 UNALIGNED_MEMCPY(&cookiecache[ninitiator].initiator, in, sizeof(*in));
814 ninitiator = (ninitiator + 1) % MAXINITIATORS;
815 }
816
817 #define cookie_isinitiator(x, y) cookie_sidecheck((x), (y), 1)
818 #define cookie_isresponder(x, y) cookie_sidecheck((x), (y), 0)
819 static int
820 cookie_sidecheck(int i, const u_char *bp2, int initiator)
821 {
822 struct ip *ip;
823 #ifdef INET6
824 struct ip6_hdr *ip6;
825 #endif
826
827 ip = (struct ip *)bp2;
828 switch (IP_V(ip)) {
829 case 4:
830 if (cookiecache[i].version != 4)
831 return 0;
832 if (initiator) {
833 if (UNALIGNED_MEMCMP(&ip->ip_src, &cookiecache[i].iaddr.in4, sizeof(struct in_addr)) == 0)
834 return 1;
835 } else {
836 if (UNALIGNED_MEMCMP(&ip->ip_src, &cookiecache[i].raddr.in4, sizeof(struct in_addr)) == 0)
837 return 1;
838 }
839 break;
840 #ifdef INET6
841 case 6:
842 if (cookiecache[i].version != 6)
843 return 0;
844 ip6 = (struct ip6_hdr *)bp2;
845 if (initiator) {
846 if (UNALIGNED_MEMCMP(&ip6->ip6_src, &cookiecache[i].iaddr.in6, sizeof(struct in6_addr)) == 0)
847 return 1;
848 } else {
849 if (UNALIGNED_MEMCMP(&ip6->ip6_src, &cookiecache[i].raddr.in6, sizeof(struct in6_addr)) == 0)
850 return 1;
851 }
852 break;
853 #endif /* INET6 */
854 default:
855 break;
856 }
857
858 return 0;
859 }
860
861 static void
862 hexprint(netdissect_options *ndo, caddr_t loc, size_t len)
863 {
864 u_char *p;
865 size_t i;
866
867 p = (u_char *)loc;
868 for (i = 0; i < len; i++)
869 ND_PRINT((ndo,"%02x", p[i] & 0xff));
870 }
871
872 static int
873 rawprint(netdissect_options *ndo, caddr_t loc, size_t len)
874 {
875 ND_TCHECK2(*loc, len);
876
877 hexprint(ndo, loc, len);
878 return 1;
879 trunc:
880 return 0;
881 }
882
883
884 /*
885 * returns false if we run out of data buffer
886 */
887 static int ike_show_somedata(struct netdissect_options *ndo,
888 const u_char *cp, const u_char *ep)
889 {
890 /* there is too much data, just show some of it */
891 const u_char *end = ep - 20;
892 int elen = 20;
893 int len = ep - cp;
894 if(len > 10) {
895 len = 10;
896 }
897
898 /* really shouldn't happen because of above */
899 if(end < cp + len) {
900 end = cp+len;
901 elen = ep - end;
902 }
903
904 ND_PRINT((ndo," data=("));
905 if(!rawprint(ndo, (caddr_t)(cp), len)) goto trunc;
906 ND_PRINT((ndo, "..."));
907 if(elen) {
908 if(!rawprint(ndo, (caddr_t)(end), elen)) goto trunc;
909 }
910 ND_PRINT((ndo,")"));
911 return 1;
912
913 trunc:
914 return 0;
915 }
916
917 struct attrmap {
918 const char *type;
919 u_int nvalue;
920 const char *value[30]; /*XXX*/
921 };
922
923 static const u_char *
924 ikev1_attrmap_print(netdissect_options *ndo,
925 const u_char *p, const u_char *ep,
926 const struct attrmap *map, size_t nmap)
927 {
928 int totlen;
929 u_int32_t t, v;
930
931 if (p[0] & 0x80)
932 totlen = 4;
933 else
934 totlen = 4 + EXTRACT_16BITS(&p[2]);
935 if (ep < p + totlen) {
936 ND_PRINT((ndo,"[|attr]"));
937 return ep + 1;
938 }
939
940 ND_PRINT((ndo,"("));
941 t = EXTRACT_16BITS(&p[0]) & 0x7fff;
942 if (map && t < nmap && map[t].type)
943 ND_PRINT((ndo,"type=%s ", map[t].type));
944 else
945 ND_PRINT((ndo,"type=#%d ", t));
946 if (p[0] & 0x80) {
947 ND_PRINT((ndo,"value="));
948 v = EXTRACT_16BITS(&p[2]);
949 if (map && t < nmap && v < map[t].nvalue && map[t].value[v])
950 ND_PRINT((ndo,"%s", map[t].value[v]));
951 else
952 rawprint(ndo, (caddr_t)&p[2], 2);
953 } else {
954 ND_PRINT((ndo,"len=%d value=", EXTRACT_16BITS(&p[2])));
955 rawprint(ndo, (caddr_t)&p[4], EXTRACT_16BITS(&p[2]));
956 }
957 ND_PRINT((ndo,")"));
958 return p + totlen;
959 }
960
961 static const u_char *
962 ikev1_attr_print(netdissect_options *ndo, const u_char *p, const u_char *ep)
963 {
964 int totlen;
965 u_int32_t t;
966
967 if (p[0] & 0x80)
968 totlen = 4;
969 else
970 totlen = 4 + EXTRACT_16BITS(&p[2]);
971 if (ep < p + totlen) {
972 ND_PRINT((ndo,"[|attr]"));
973 return ep + 1;
974 }
975
976 ND_PRINT((ndo,"("));
977 t = EXTRACT_16BITS(&p[0]) & 0x7fff;
978 ND_PRINT((ndo,"type=#%d ", t));
979 if (p[0] & 0x80) {
980 ND_PRINT((ndo,"value="));
981 t = p[2];
982 rawprint(ndo, (caddr_t)&p[2], 2);
983 } else {
984 ND_PRINT((ndo,"len=%d value=", EXTRACT_16BITS(&p[2])));
985 rawprint(ndo, (caddr_t)&p[4], EXTRACT_16BITS(&p[2]));
986 }
987 ND_PRINT((ndo,")"));
988 return p + totlen;
989 }
990
991 static const u_char *
992 ikev1_sa_print(netdissect_options *ndo, u_char tpay _U_,
993 const struct isakmp_gen *ext,
994 u_int item_len _U_,
995 const u_char *ep, u_int32_t phase, u_int32_t doi0 _U_,
996 u_int32_t proto0, int depth)
997 {
998 const struct ikev1_pl_sa *p;
999 struct ikev1_pl_sa sa;
1000 u_int32_t doi, sit, ident;
1001 const u_char *cp, *np;
1002 int t;
1003
1004 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_SA)));
1005
1006 p = (struct ikev1_pl_sa *)ext;
1007 ND_TCHECK(*p);
1008 UNALIGNED_MEMCPY(&sa, ext, sizeof(sa));
1009 doi = ntohl(sa.doi);
1010 sit = ntohl(sa.sit);
1011 if (doi != 1) {
1012 ND_PRINT((ndo," doi=%d", doi));
1013 ND_PRINT((ndo," situation=%u", (u_int32_t)ntohl(sa.sit)));
1014 return (u_char *)(p + 1);
1015 }
1016
1017 ND_PRINT((ndo," doi=ipsec"));
1018 ND_PRINT((ndo," situation="));
1019 t = 0;
1020 if (sit & 0x01) {
1021 ND_PRINT((ndo,"identity"));
1022 t++;
1023 }
1024 if (sit & 0x02) {
1025 ND_PRINT((ndo,"%ssecrecy", t ? "+" : ""));
1026 t++;
1027 }
1028 if (sit & 0x04)
1029 ND_PRINT((ndo,"%sintegrity", t ? "+" : ""));
1030
1031 np = (u_char *)ext + sizeof(sa);
1032 if (sit != 0x01) {
1033 ND_TCHECK2(*(ext + 1), sizeof(ident));
1034 UNALIGNED_MEMCPY(&ident, ext + 1, sizeof(ident));
1035 ND_PRINT((ndo," ident=%u", (u_int32_t)ntohl(ident)));
1036 np += sizeof(ident);
1037 }
1038
1039 ext = (struct isakmp_gen *)np;
1040 ND_TCHECK(*ext);
1041
1042 cp = ikev1_sub_print(ndo, ISAKMP_NPTYPE_P, ext, ep, phase, doi, proto0,
1043 depth);
1044
1045 return cp;
1046 trunc:
1047 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_SA)));
1048 return NULL;
1049 }
1050
1051 static const u_char *
1052 ikev1_p_print(netdissect_options *ndo, u_char tpay _U_,
1053 const struct isakmp_gen *ext, u_int item_len _U_,
1054 const u_char *ep, u_int32_t phase, u_int32_t doi0,
1055 u_int32_t proto0 _U_, int depth)
1056 {
1057 const struct ikev1_pl_p *p;
1058 struct ikev1_pl_p prop;
1059 const u_char *cp;
1060
1061 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_P)));
1062
1063 p = (struct ikev1_pl_p *)ext;
1064 ND_TCHECK(*p);
1065 UNALIGNED_MEMCPY(&prop, ext, sizeof(prop));
1066 ND_PRINT((ndo," #%d protoid=%s transform=%d",
1067 prop.p_no, PROTOIDSTR(prop.prot_id), prop.num_t));
1068 if (prop.spi_size) {
1069 ND_PRINT((ndo," spi="));
1070 if (!rawprint(ndo, (caddr_t)(p + 1), prop.spi_size))
1071 goto trunc;
1072 }
1073
1074 ext = (struct isakmp_gen *)((u_char *)(p + 1) + prop.spi_size);
1075 ND_TCHECK(*ext);
1076
1077 cp = ikev1_sub_print(ndo, ISAKMP_NPTYPE_T, ext, ep, phase, doi0,
1078 prop.prot_id, depth);
1079
1080 return cp;
1081 trunc:
1082 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_P)));
1083 return NULL;
1084 }
1085
1086 static const char *ikev1_p_map[] = {
1087 NULL, "ike",
1088 };
1089
1090 static const char *ikev2_t_type_map[]={
1091 NULL, "encr", "prf", "integ", "dh", "esn"
1092 };
1093
1094 static const char *ah_p_map[] = {
1095 NULL, "(reserved)", "md5", "sha", "1des",
1096 "sha2-256", "sha2-384", "sha2-512",
1097 };
1098
1099 static const char *prf_p_map[] = {
1100 NULL, "hmac-md5", "hmac-sha", "hmac-tiger",
1101 "aes128_xcbc"
1102 };
1103
1104 static const char *integ_p_map[] = {
1105 NULL, "hmac-md5", "hmac-sha", "dec-mac",
1106 "kpdk-md5", "aes-xcbc"
1107 };
1108
1109 static const char *esn_p_map[] = {
1110 "no-esn", "esn"
1111 };
1112
1113 static const char *dh_p_map[] = {
1114 NULL, "modp768",
1115 "modp1024", /* group 2 */
1116 "EC2N 2^155", /* group 3 */
1117 "EC2N 2^185", /* group 4 */
1118 "modp1536", /* group 5 */
1119 "iana-grp06", "iana-grp07", /* reserved */
1120 "iana-grp08", "iana-grp09",
1121 "iana-grp10", "iana-grp11",
1122 "iana-grp12", "iana-grp13",
1123 "modp2048", /* group 14 */
1124 "modp3072", /* group 15 */
1125 "modp4096", /* group 16 */
1126 "modp6144", /* group 17 */
1127 "modp8192", /* group 18 */
1128 };
1129
1130 static const char *esp_p_map[] = {
1131 NULL, "1des-iv64", "1des", "3des", "rc5", "idea", "cast",
1132 "blowfish", "3idea", "1des-iv32", "rc4", "null", "aes"
1133 };
1134
1135 static const char *ipcomp_p_map[] = {
1136 NULL, "oui", "deflate", "lzs",
1137 };
1138
1139 static const struct attrmap ipsec_t_map[] = {
1140 { NULL, 0, { NULL } },
1141 { "lifetype", 3, { NULL, "sec", "kb", }, },
1142 { "life", 0, { NULL } },
1143 { "group desc", 18, { NULL, "modp768",
1144 "modp1024", /* group 2 */
1145 "EC2N 2^155", /* group 3 */
1146 "EC2N 2^185", /* group 4 */
1147 "modp1536", /* group 5 */
1148 "iana-grp06", "iana-grp07", /* reserved */
1149 "iana-grp08", "iana-grp09",
1150 "iana-grp10", "iana-grp11",
1151 "iana-grp12", "iana-grp13",
1152 "modp2048", /* group 14 */
1153 "modp3072", /* group 15 */
1154 "modp4096", /* group 16 */
1155 "modp6144", /* group 17 */
1156 "modp8192", /* group 18 */
1157 }, },
1158 { "enc mode", 3, { NULL, "tunnel", "transport", }, },
1159 { "auth", 5, { NULL, "hmac-md5", "hmac-sha1", "1des-mac", "keyed", }, },
1160 { "keylen", 0, { NULL } },
1161 { "rounds", 0, { NULL } },
1162 { "dictsize", 0, { NULL } },
1163 { "privalg", 0, { NULL } },
1164 };
1165
1166 static const struct attrmap encr_t_map[] = {
1167 { NULL, 0, { NULL } }, { NULL, 0, { NULL } }, /* 0, 1 */
1168 { NULL, 0, { NULL } }, { NULL, 0, { NULL } }, /* 2, 3 */
1169 { NULL, 0, { NULL } }, { NULL, 0, { NULL } }, /* 4, 5 */
1170 { NULL, 0, { NULL } }, { NULL, 0, { NULL } }, /* 6, 7 */
1171 { NULL, 0, { NULL } }, { NULL, 0, { NULL } }, /* 8, 9 */
1172 { NULL, 0, { NULL } }, { NULL, 0, { NULL } }, /* 10,11*/
1173 { NULL, 0, { NULL } }, { NULL, 0, { NULL } }, /* 12,13*/
1174 { "keylen", 14, { NULL }},
1175 };
1176
1177 static const struct attrmap oakley_t_map[] = {
1178 { NULL, 0, { NULL } },
1179 { "enc", 8, { NULL, "1des", "idea", "blowfish", "rc5",
1180 "3des", "cast", "aes", }, },
1181 { "hash", 7, { NULL, "md5", "sha1", "tiger",
1182 "sha2-256", "sha2-384", "sha2-512", }, },
1183 { "auth", 6, { NULL, "preshared", "dss", "rsa sig", "rsa enc",
1184 "rsa enc revised", }, },
1185 { "group desc", 18, { NULL, "modp768",
1186 "modp1024", /* group 2 */
1187 "EC2N 2^155", /* group 3 */
1188 "EC2N 2^185", /* group 4 */
1189 "modp1536", /* group 5 */
1190 "iana-grp06", "iana-grp07", /* reserved */
1191 "iana-grp08", "iana-grp09",
1192 "iana-grp10", "iana-grp11",
1193 "iana-grp12", "iana-grp13",
1194 "modp2048", /* group 14 */
1195 "modp3072", /* group 15 */
1196 "modp4096", /* group 16 */
1197 "modp6144", /* group 17 */
1198 "modp8192", /* group 18 */
1199 }, },
1200 { "group type", 4, { NULL, "MODP", "ECP", "EC2N", }, },
1201 { "group prime", 0, { NULL } },
1202 { "group gen1", 0, { NULL } },
1203 { "group gen2", 0, { NULL } },
1204 { "group curve A", 0, { NULL } },
1205 { "group curve B", 0, { NULL } },
1206 { "lifetype", 3, { NULL, "sec", "kb", }, },
1207 { "lifeduration", 0, { NULL } },
1208 { "prf", 0, { NULL } },
1209 { "keylen", 0, { NULL } },
1210 { "field", 0, { NULL } },
1211 { "order", 0, { NULL } },
1212 };
1213
1214 static const u_char *
1215 ikev1_t_print(netdissect_options *ndo, u_char tpay _U_,
1216 const struct isakmp_gen *ext, u_int item_len,
1217 const u_char *ep, u_int32_t phase _U_, u_int32_t doi _U_,
1218 u_int32_t proto, int depth _U_)
1219 {
1220 const struct ikev1_pl_t *p;
1221 struct ikev1_pl_t t;
1222 const u_char *cp;
1223 const char *idstr;
1224 const struct attrmap *map;
1225 size_t nmap;
1226 const u_char *ep2;
1227
1228 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_T)));
1229
1230 p = (struct ikev1_pl_t *)ext;
1231 ND_TCHECK(*p);
1232 UNALIGNED_MEMCPY(&t, ext, sizeof(t));
1233
1234 switch (proto) {
1235 case 1:
1236 idstr = STR_OR_ID(t.t_id, ikev1_p_map);
1237 map = oakley_t_map;
1238 nmap = sizeof(oakley_t_map)/sizeof(oakley_t_map[0]);
1239 break;
1240 case 2:
1241 idstr = STR_OR_ID(t.t_id, ah_p_map);
1242 map = ipsec_t_map;
1243 nmap = sizeof(ipsec_t_map)/sizeof(ipsec_t_map[0]);
1244 break;
1245 case 3:
1246 idstr = STR_OR_ID(t.t_id, esp_p_map);
1247 map = ipsec_t_map;
1248 nmap = sizeof(ipsec_t_map)/sizeof(ipsec_t_map[0]);
1249 break;
1250 case 4:
1251 idstr = STR_OR_ID(t.t_id, ipcomp_p_map);
1252 map = ipsec_t_map;
1253 nmap = sizeof(ipsec_t_map)/sizeof(ipsec_t_map[0]);
1254 break;
1255 default:
1256 idstr = NULL;
1257 map = NULL;
1258 nmap = 0;
1259 break;
1260 }
1261
1262 if (idstr)
1263 ND_PRINT((ndo," #%d id=%s ", t.t_no, idstr));
1264 else
1265 ND_PRINT((ndo," #%d id=%d ", t.t_no, t.t_id));
1266 cp = (u_char *)(p + 1);
1267 ep2 = (u_char *)p + item_len;
1268 while (cp < ep && cp < ep2) {
1269 if (map && nmap) {
1270 cp = ikev1_attrmap_print(ndo, cp, (ep < ep2) ? ep : ep2,
1271 map, nmap);
1272 } else
1273 cp = ikev1_attr_print(ndo, cp, (ep < ep2) ? ep : ep2);
1274 }
1275 if (ep < ep2)
1276 ND_PRINT((ndo,"..."));
1277 return cp;
1278 trunc:
1279 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_T)));
1280 return NULL;
1281 }
1282
1283 static const u_char *
1284 ikev1_ke_print(netdissect_options *ndo, u_char tpay _U_,
1285 const struct isakmp_gen *ext, u_int item_len _U_,
1286 const u_char *ep _U_, u_int32_t phase _U_, u_int32_t doi _U_,
1287 u_int32_t proto _U_, int depth _U_)
1288 {
1289 struct isakmp_gen e;
1290
1291 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_KE)));
1292
1293 ND_TCHECK(*ext);
1294 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
1295 ND_PRINT((ndo," key len=%d", ntohs(e.len) - 4));
1296 if (2 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
1297 ND_PRINT((ndo," "));
1298 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
1299 goto trunc;
1300 }
1301 return (u_char *)ext + ntohs(e.len);
1302 trunc:
1303 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_KE)));
1304 return NULL;
1305 }
1306
1307 static const u_char *
1308 ikev1_id_print(netdissect_options *ndo, u_char tpay _U_,
1309 const struct isakmp_gen *ext, u_int item_len _U_,
1310 const u_char *ep _U_, u_int32_t phase, u_int32_t doi _U_,
1311 u_int32_t proto _U_, int depth _U_)
1312 {
1313 #define USE_IPSECDOI_IN_PHASE1 1
1314 const struct ikev1_pl_id *p;
1315 struct ikev1_pl_id id;
1316 static const char *idtypestr[] = {
1317 "IPv4", "IPv4net", "IPv6", "IPv6net",
1318 };
1319 static const char *ipsecidtypestr[] = {
1320 NULL, "IPv4", "FQDN", "user FQDN", "IPv4net", "IPv6",
1321 "IPv6net", "IPv4range", "IPv6range", "ASN1 DN", "ASN1 GN",
1322 "keyid",
1323 };
1324 int len;
1325 const u_char *data;
1326
1327 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_ID)));
1328
1329 p = (struct ikev1_pl_id *)ext;
1330 ND_TCHECK(*p);
1331 UNALIGNED_MEMCPY(&id, ext, sizeof(id));
1332 if (sizeof(*p) < item_len) {
1333 data = (u_char *)(p + 1);
1334 len = item_len - sizeof(*p);
1335 } else {
1336 data = NULL;
1337 len = 0;
1338 }
1339
1340 #if 0 /*debug*/
1341 ND_PRINT((ndo," [phase=%d doi=%d proto=%d]", phase, doi, proto));
1342 #endif
1343 switch (phase) {
1344 #ifndef USE_IPSECDOI_IN_PHASE1
1345 case 1:
1346 #endif
1347 default:
1348 ND_PRINT((ndo," idtype=%s", STR_OR_ID(id.d.id_type, idtypestr)));
1349 ND_PRINT((ndo," doi_data=%u",
1350 (u_int32_t)(ntohl(id.d.doi_data) & 0xffffff)));
1351 break;
1352
1353 #ifdef USE_IPSECDOI_IN_PHASE1
1354 case 1:
1355 #endif
1356 case 2:
1357 {
1358 const struct ipsecdoi_id *p;
1359 struct ipsecdoi_id id;
1360 struct protoent *pe;
1361
1362 p = (struct ipsecdoi_id *)ext;
1363 ND_TCHECK(*p);
1364 UNALIGNED_MEMCPY(&id, ext, sizeof(id));
1365 ND_PRINT((ndo," idtype=%s", STR_OR_ID(id.type, ipsecidtypestr)));
1366 if (id.proto_id) {
1367 #ifndef WIN32
1368 setprotoent(1);
1369 #endif /* WIN32 */
1370 pe = getprotobynumber(id.proto_id);
1371 if (pe)
1372 ND_PRINT((ndo," protoid=%s", pe->p_name));
1373 #ifndef WIN32
1374 endprotoent();
1375 #endif /* WIN32 */
1376 } else {
1377 /* it DOES NOT mean IPPROTO_IP! */
1378 ND_PRINT((ndo," protoid=%s", "0"));
1379 }
1380 ND_PRINT((ndo," port=%d", ntohs(id.port)));
1381 if (!len)
1382 break;
1383 if (data == NULL)
1384 goto trunc;
1385 ND_TCHECK2(*data, len);
1386 switch (id.type) {
1387 case IPSECDOI_ID_IPV4_ADDR:
1388 if (len < 4)
1389 ND_PRINT((ndo," len=%d [bad: < 4]", len));
1390 else
1391 ND_PRINT((ndo," len=%d %s", len, ipaddr_string(data)));
1392 len = 0;
1393 break;
1394 case IPSECDOI_ID_FQDN:
1395 case IPSECDOI_ID_USER_FQDN:
1396 {
1397 int i;
1398 ND_PRINT((ndo," len=%d ", len));
1399 for (i = 0; i < len; i++)
1400 safeputchar(data[i]);
1401 len = 0;
1402 break;
1403 }
1404 case IPSECDOI_ID_IPV4_ADDR_SUBNET:
1405 {
1406 const u_char *mask;
1407 if (len < 8)
1408 ND_PRINT((ndo," len=%d [bad: < 8]", len));
1409 else {
1410 mask = data + sizeof(struct in_addr);
1411 ND_PRINT((ndo," len=%d %s/%u.%u.%u.%u", len,
1412 ipaddr_string(data),
1413 mask[0], mask[1], mask[2], mask[3]));
1414 }
1415 len = 0;
1416 break;
1417 }
1418 #ifdef INET6
1419 case IPSECDOI_ID_IPV6_ADDR:
1420 if (len < 16)
1421 ND_PRINT((ndo," len=%d [bad: < 16]", len));
1422 else
1423 ND_PRINT((ndo," len=%d %s", len, ip6addr_string(data)));
1424 len = 0;
1425 break;
1426 case IPSECDOI_ID_IPV6_ADDR_SUBNET:
1427 {
1428 const u_char *mask;
1429 if (len < 20)
1430 ND_PRINT((ndo," len=%d [bad: < 20]", len));
1431 else {
1432 mask = (u_char *)(data + sizeof(struct in6_addr));
1433 /*XXX*/
1434 ND_PRINT((ndo," len=%d %s/0x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x", len,
1435 ip6addr_string(data),
1436 mask[0], mask[1], mask[2], mask[3],
1437 mask[4], mask[5], mask[6], mask[7],
1438 mask[8], mask[9], mask[10], mask[11],
1439 mask[12], mask[13], mask[14], mask[15]));
1440 }
1441 len = 0;
1442 break;
1443 }
1444 #endif /*INET6*/
1445 case IPSECDOI_ID_IPV4_ADDR_RANGE:
1446 if (len < 8)
1447 ND_PRINT((ndo," len=%d [bad: < 8]", len));
1448 else {
1449 ND_PRINT((ndo," len=%d %s-%s", len,
1450 ipaddr_string(data),
1451 ipaddr_string(data + sizeof(struct in_addr))));
1452 }
1453 len = 0;
1454 break;
1455 #ifdef INET6
1456 case IPSECDOI_ID_IPV6_ADDR_RANGE:
1457 if (len < 32)
1458 ND_PRINT((ndo," len=%d [bad: < 32]", len));
1459 else {
1460 ND_PRINT((ndo," len=%d %s-%s", len,
1461 ip6addr_string(data),
1462 ip6addr_string(data + sizeof(struct in6_addr))));
1463 }
1464 len = 0;
1465 break;
1466 #endif /*INET6*/
1467 case IPSECDOI_ID_DER_ASN1_DN:
1468 case IPSECDOI_ID_DER_ASN1_GN:
1469 case IPSECDOI_ID_KEY_ID:
1470 break;
1471 }
1472 break;
1473 }
1474 }
1475 if (data && len) {
1476 ND_PRINT((ndo," len=%d", len));
1477 if (2 < ndo->ndo_vflag) {
1478 ND_PRINT((ndo," "));
1479 if (!rawprint(ndo, (caddr_t)data, len))
1480 goto trunc;
1481 }
1482 }
1483 return (u_char *)ext + item_len;
1484 trunc:
1485 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_ID)));
1486 return NULL;
1487 }
1488
1489 static const u_char *
1490 ikev1_cert_print(netdissect_options *ndo, u_char tpay _U_,
1491 const struct isakmp_gen *ext, u_int item_len _U_,
1492 const u_char *ep _U_, u_int32_t phase _U_,
1493 u_int32_t doi0 _U_,
1494 u_int32_t proto0 _U_, int depth _U_)
1495 {
1496 const struct ikev1_pl_cert *p;
1497 struct ikev1_pl_cert cert;
1498 static const char *certstr[] = {
1499 "none", "pkcs7", "pgp", "dns",
1500 "x509sign", "x509ke", "kerberos", "crl",
1501 "arl", "spki", "x509attr",
1502 };
1503
1504 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_CERT)));
1505
1506 p = (struct ikev1_pl_cert *)ext;
1507 ND_TCHECK(*p);
1508 UNALIGNED_MEMCPY(&cert, ext, sizeof(cert));
1509 ND_PRINT((ndo," len=%d", item_len - 4));
1510 ND_PRINT((ndo," type=%s", STR_OR_ID((cert.encode), certstr)));
1511 if (2 < ndo->ndo_vflag && 4 < item_len) {
1512 ND_PRINT((ndo," "));
1513 if (!rawprint(ndo, (caddr_t)(ext + 1), item_len - 4))
1514 goto trunc;
1515 }
1516 return (u_char *)ext + item_len;
1517 trunc:
1518 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_CERT)));
1519 return NULL;
1520 }
1521
1522 static const u_char *
1523 ikev1_cr_print(netdissect_options *ndo, u_char tpay _U_,
1524 const struct isakmp_gen *ext, u_int item_len _U_,
1525 const u_char *ep _U_, u_int32_t phase _U_, u_int32_t doi0 _U_,
1526 u_int32_t proto0 _U_, int depth _U_)
1527 {
1528 const struct ikev1_pl_cert *p;
1529 struct ikev1_pl_cert cert;
1530 static const char *certstr[] = {
1531 "none", "pkcs7", "pgp", "dns",
1532 "x509sign", "x509ke", "kerberos", "crl",
1533 "arl", "spki", "x509attr",
1534 };
1535
1536 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_CR)));
1537
1538 p = (struct ikev1_pl_cert *)ext;
1539 ND_TCHECK(*p);
1540 UNALIGNED_MEMCPY(&cert, ext, sizeof(cert));
1541 ND_PRINT((ndo," len=%d", item_len - 4));
1542 ND_PRINT((ndo," type=%s", STR_OR_ID((cert.encode), certstr)));
1543 if (2 < ndo->ndo_vflag && 4 < item_len) {
1544 ND_PRINT((ndo," "));
1545 if (!rawprint(ndo, (caddr_t)(ext + 1), item_len - 4))
1546 goto trunc;
1547 }
1548 return (u_char *)ext + item_len;
1549 trunc:
1550 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_CR)));
1551 return NULL;
1552 }
1553
1554 static const u_char *
1555 ikev1_hash_print(netdissect_options *ndo, u_char tpay _U_,
1556 const struct isakmp_gen *ext, u_int item_len _U_,
1557 const u_char *ep _U_, u_int32_t phase _U_, u_int32_t doi _U_,
1558 u_int32_t proto _U_, int depth _U_)
1559 {
1560 struct isakmp_gen e;
1561
1562 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_HASH)));
1563
1564 ND_TCHECK(*ext);
1565 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
1566 ND_PRINT((ndo," len=%d", ntohs(e.len) - 4));
1567 if (2 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
1568 ND_PRINT((ndo," "));
1569 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
1570 goto trunc;
1571 }
1572 return (u_char *)ext + ntohs(e.len);
1573 trunc:
1574 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_HASH)));
1575 return NULL;
1576 }
1577
1578 static const u_char *
1579 ikev1_sig_print(netdissect_options *ndo, u_char tpay _U_,
1580 const struct isakmp_gen *ext, u_int item_len _U_,
1581 const u_char *ep _U_, u_int32_t phase _U_, u_int32_t doi _U_,
1582 u_int32_t proto _U_, int depth _U_)
1583 {
1584 struct isakmp_gen e;
1585
1586 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_SIG)));
1587
1588 ND_TCHECK(*ext);
1589 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
1590 ND_PRINT((ndo," len=%d", ntohs(e.len) - 4));
1591 if (2 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
1592 ND_PRINT((ndo," "));
1593 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
1594 goto trunc;
1595 }
1596 return (u_char *)ext + ntohs(e.len);
1597 trunc:
1598 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_SIG)));
1599 return NULL;
1600 }
1601
1602 static const u_char *
1603 ikev1_nonce_print(netdissect_options *ndo, u_char tpay _U_,
1604 const struct isakmp_gen *ext,
1605 u_int item_len _U_,
1606 const u_char *ep _U_,
1607 u_int32_t phase _U_, u_int32_t doi _U_,
1608 u_int32_t proto _U_, int depth _U_)
1609 {
1610 struct isakmp_gen e;
1611
1612 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_NONCE)));
1613
1614 ND_TCHECK(*ext);
1615 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
1616 ND_PRINT((ndo," n len=%d", ntohs(e.len) - 4));
1617 if (2 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
1618 ND_PRINT((ndo," "));
1619 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
1620 goto trunc;
1621 } else if (1 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
1622 ND_PRINT((ndo," "));
1623 if (!ike_show_somedata(ndo, (u_char *)(caddr_t)(ext + 1), ep))
1624 goto trunc;
1625 }
1626 return (u_char *)ext + ntohs(e.len);
1627 trunc:
1628 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_NONCE)));
1629 return NULL;
1630 }
1631
1632 static const u_char *
1633 ikev1_n_print(netdissect_options *ndo, u_char tpay _U_,
1634 const struct isakmp_gen *ext, u_int item_len,
1635 const u_char *ep, u_int32_t phase, u_int32_t doi0 _U_,
1636 u_int32_t proto0 _U_, int depth)
1637 {
1638 struct ikev1_pl_n *p, n;
1639 const u_char *cp;
1640 u_char *ep2;
1641 u_int32_t doi;
1642 u_int32_t proto;
1643 static const char *notify_error_str[] = {
1644 NULL, "INVALID-PAYLOAD-TYPE",
1645 "DOI-NOT-SUPPORTED", "SITUATION-NOT-SUPPORTED",
1646 "INVALID-COOKIE", "INVALID-MAJOR-VERSION",
1647 "INVALID-MINOR-VERSION", "INVALID-EXCHANGE-TYPE",
1648 "INVALID-FLAGS", "INVALID-MESSAGE-ID",
1649 "INVALID-PROTOCOL-ID", "INVALID-SPI",
1650 "INVALID-TRANSFORM-ID", "ATTRIBUTES-NOT-SUPPORTED",
1651 "NO-PROPOSAL-CHOSEN", "BAD-PROPOSAL-SYNTAX",
1652 "PAYLOAD-MALFORMED", "INVALID-KEY-INFORMATION",
1653 "INVALID-ID-INFORMATION", "INVALID-CERT-ENCODING",
1654 "INVALID-CERTIFICATE", "CERT-TYPE-UNSUPPORTED",
1655 "INVALID-CERT-AUTHORITY", "INVALID-HASH-INFORMATION",
1656 "AUTHENTICATION-FAILED", "INVALID-SIGNATURE",
1657 "ADDRESS-NOTIFICATION", "NOTIFY-SA-LIFETIME",
1658 "CERTIFICATE-UNAVAILABLE", "UNSUPPORTED-EXCHANGE-TYPE",
1659 "UNEQUAL-PAYLOAD-LENGTHS",
1660 };
1661 static const char *ipsec_notify_error_str[] = {
1662 "RESERVED",
1663 };
1664 static const char *notify_status_str[] = {
1665 "CONNECTED",
1666 };
1667 static const char *ipsec_notify_status_str[] = {
1668 "RESPONDER-LIFETIME", "REPLAY-STATUS",
1669 "INITIAL-CONTACT",
1670 };
1671 /* NOTE: these macro must be called with x in proper range */
1672
1673 /* 0 - 8191 */
1674 #define NOTIFY_ERROR_STR(x) \
1675 STR_OR_ID((x), notify_error_str)
1676
1677 /* 8192 - 16383 */
1678 #define IPSEC_NOTIFY_ERROR_STR(x) \
1679 STR_OR_ID((u_int)((x) - 8192), ipsec_notify_error_str)
1680
1681 /* 16384 - 24575 */
1682 #define NOTIFY_STATUS_STR(x) \
1683 STR_OR_ID((u_int)((x) - 16384), notify_status_str)
1684
1685 /* 24576 - 32767 */
1686 #define IPSEC_NOTIFY_STATUS_STR(x) \
1687 STR_OR_ID((u_int)((x) - 24576), ipsec_notify_status_str)
1688
1689 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_N)));
1690
1691 p = (struct ikev1_pl_n *)ext;
1692 ND_TCHECK(*p);
1693 UNALIGNED_MEMCPY(&n, ext, sizeof(n));
1694 doi = ntohl(n.doi);
1695 proto = n.prot_id;
1696 if (doi != 1) {
1697 ND_PRINT((ndo," doi=%d", doi));
1698 ND_PRINT((ndo," proto=%d", proto));
1699 if (ntohs(n.type) < 8192)
1700 ND_PRINT((ndo," type=%s", NOTIFY_ERROR_STR(ntohs(n.type))));
1701 else if (ntohs(n.type) < 16384)
1702 ND_PRINT((ndo," type=%s", numstr(ntohs(n.type))));
1703 else if (ntohs(n.type) < 24576)
1704 ND_PRINT((ndo," type=%s", NOTIFY_STATUS_STR(ntohs(n.type))));
1705 else
1706 ND_PRINT((ndo," type=%s", numstr(ntohs(n.type))));
1707 if (n.spi_size) {
1708 ND_PRINT((ndo," spi="));
1709 if (!rawprint(ndo, (caddr_t)(p + 1), n.spi_size))
1710 goto trunc;
1711 }
1712 return (u_char *)(p + 1) + n.spi_size;
1713 }
1714
1715 ND_PRINT((ndo," doi=ipsec"));
1716 ND_PRINT((ndo," proto=%s", PROTOIDSTR(proto)));
1717 if (ntohs(n.type) < 8192)
1718 ND_PRINT((ndo," type=%s", NOTIFY_ERROR_STR(ntohs(n.type))));
1719 else if (ntohs(n.type) < 16384)
1720 ND_PRINT((ndo," type=%s", IPSEC_NOTIFY_ERROR_STR(ntohs(n.type))));
1721 else if (ntohs(n.type) < 24576)
1722 ND_PRINT((ndo," type=%s", NOTIFY_STATUS_STR(ntohs(n.type))));
1723 else if (ntohs(n.type) < 32768)
1724 ND_PRINT((ndo," type=%s", IPSEC_NOTIFY_STATUS_STR(ntohs(n.type))));
1725 else
1726 ND_PRINT((ndo," type=%s", numstr(ntohs(n.type))));
1727 if (n.spi_size) {
1728 ND_PRINT((ndo," spi="));
1729 if (!rawprint(ndo, (caddr_t)(p + 1), n.spi_size))
1730 goto trunc;
1731 }
1732
1733 cp = (u_char *)(p + 1) + n.spi_size;
1734 ep2 = (u_char *)p + item_len;
1735
1736 if (cp < ep) {
1737 ND_PRINT((ndo," orig=("));
1738 switch (ntohs(n.type)) {
1739 case IPSECDOI_NTYPE_RESPONDER_LIFETIME:
1740 {
1741 const struct attrmap *map = oakley_t_map;
1742 size_t nmap = sizeof(oakley_t_map)/sizeof(oakley_t_map[0]);
1743 while (cp < ep && cp < ep2) {
1744 cp = ikev1_attrmap_print(ndo, cp,
1745 (ep < ep2) ? ep : ep2, map, nmap);
1746 }
1747 break;
1748 }
1749 case IPSECDOI_NTYPE_REPLAY_STATUS:
1750 ND_PRINT((ndo,"replay detection %sabled",
1751 EXTRACT_32BITS(cp) ? "en" : "dis"));
1752 break;
1753 case ISAKMP_NTYPE_NO_PROPOSAL_CHOSEN:
1754 if (ikev1_sub_print(ndo, ISAKMP_NPTYPE_SA,
1755 (struct isakmp_gen *)cp, ep, phase, doi, proto,
1756 depth) == NULL)
1757 return NULL;
1758 break;
1759 default:
1760 /* NULL is dummy */
1761 isakmp_print(ndo, cp,
1762 item_len - sizeof(*p) - n.spi_size,
1763 NULL);
1764 }
1765 ND_PRINT((ndo,")"));
1766 }
1767 return (u_char *)ext + item_len;
1768 trunc:
1769 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_N)));
1770 return NULL;
1771 }
1772
1773 static const u_char *
1774 ikev1_d_print(netdissect_options *ndo, u_char tpay _U_,
1775 const struct isakmp_gen *ext, u_int item_len _U_,
1776 const u_char *ep _U_, u_int32_t phase _U_, u_int32_t doi0 _U_,
1777 u_int32_t proto0 _U_, int depth _U_)
1778 {
1779 const struct ikev1_pl_d *p;
1780 struct ikev1_pl_d d;
1781 const u_int8_t *q;
1782 u_int32_t doi;
1783 u_int32_t proto;
1784 int i;
1785
1786 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_D)));
1787
1788 p = (struct ikev1_pl_d *)ext;
1789 ND_TCHECK(*p);
1790 UNALIGNED_MEMCPY(&d, ext, sizeof(d));
1791 doi = ntohl(d.doi);
1792 proto = d.prot_id;
1793 if (doi != 1) {
1794 ND_PRINT((ndo," doi=%u", doi));
1795 ND_PRINT((ndo," proto=%u", proto));
1796 } else {
1797 ND_PRINT((ndo," doi=ipsec"));
1798 ND_PRINT((ndo," proto=%s", PROTOIDSTR(proto)));
1799 }
1800 ND_PRINT((ndo," spilen=%u", d.spi_size));
1801 ND_PRINT((ndo," nspi=%u", ntohs(d.num_spi)));
1802 ND_PRINT((ndo," spi="));
1803 q = (u_int8_t *)(p + 1);
1804 for (i = 0; i < ntohs(d.num_spi); i++) {
1805 if (i != 0)
1806 ND_PRINT((ndo,","));
1807 if (!rawprint(ndo, (caddr_t)q, d.spi_size))
1808 goto trunc;
1809 q += d.spi_size;
1810 }
1811 return q;
1812 trunc:
1813 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_D)));
1814 return NULL;
1815 }
1816
1817 static const u_char *
1818 ikev1_vid_print(netdissect_options *ndo, u_char tpay _U_,
1819 const struct isakmp_gen *ext,
1820 u_int item_len _U_, const u_char *ep _U_,
1821 u_int32_t phase _U_, u_int32_t doi _U_,
1822 u_int32_t proto _U_, int depth _U_)
1823 {
1824 struct isakmp_gen e;
1825
1826 ND_PRINT((ndo,"%s:", NPSTR(ISAKMP_NPTYPE_VID)));
1827
1828 ND_TCHECK(*ext);
1829 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
1830 ND_PRINT((ndo," len=%d", ntohs(e.len) - 4));
1831 if (2 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
1832 ND_PRINT((ndo," "));
1833 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
1834 goto trunc;
1835 }
1836 return (u_char *)ext + ntohs(e.len);
1837 trunc:
1838 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_VID)));
1839 return NULL;
1840 }
1841
1842 /************************************************************/
1843 /* */
1844 /* IKE v2 - rfc4306 - dissector */
1845 /* */
1846 /************************************************************/
1847
1848 static void
1849 ikev2_pay_print(netdissect_options *ndo, const char *payname, int critical)
1850 {
1851 ND_PRINT((ndo,"%s%s:", payname, critical&0x80 ? "[C]" : ""));
1852 }
1853
1854 static const u_char *
1855 ikev2_gen_print(netdissect_options *ndo, u_char tpay,
1856 const struct isakmp_gen *ext)
1857 {
1858 struct isakmp_gen e;
1859
1860 ND_TCHECK(*ext);
1861 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
1862 ikev2_pay_print(ndo, NPSTR(tpay), e.critical);
1863
1864 ND_PRINT((ndo," len=%d", ntohs(e.len) - 4));
1865 if (2 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
1866 ND_PRINT((ndo," "));
1867 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
1868 goto trunc;
1869 }
1870 return (u_char *)ext + ntohs(e.len);
1871 trunc:
1872 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
1873 return NULL;
1874 }
1875
1876 static const u_char *
1877 ikev2_t_print(netdissect_options *ndo, u_char tpay _U_, int pcount,
1878 const struct isakmp_gen *ext, u_int item_len,
1879 const u_char *ep, u_int32_t phase _U_, u_int32_t doi _U_,
1880 u_int32_t proto _U_, int depth _U_)
1881 {
1882 const struct ikev2_t *p;
1883 struct ikev2_t t;
1884 u_int16_t t_id;
1885 const u_char *cp;
1886 const char *idstr;
1887 const struct attrmap *map;
1888 size_t nmap;
1889 const u_char *ep2;
1890
1891 p = (struct ikev2_t *)ext;
1892 ND_TCHECK(*p);
1893 UNALIGNED_MEMCPY(&t, ext, sizeof(t));
1894 ikev2_pay_print(ndo, NPSTR(ISAKMP_NPTYPE_T), t.h.critical);
1895
1896 t_id = ntohs(t.t_id);
1897
1898 map = NULL;
1899 nmap = 0;
1900
1901 switch (t.t_type) {
1902 case IV2_T_ENCR:
1903 idstr = STR_OR_ID(t_id, esp_p_map);
1904 map = encr_t_map;
1905 nmap = sizeof(encr_t_map)/sizeof(encr_t_map[0]);
1906 break;
1907
1908 case IV2_T_PRF:
1909 idstr = STR_OR_ID(t_id, prf_p_map);
1910 break;
1911
1912 case IV2_T_INTEG:
1913 idstr = STR_OR_ID(t_id, integ_p_map);
1914 break;
1915
1916 case IV2_T_DH:
1917 idstr = STR_OR_ID(t_id, dh_p_map);
1918 break;
1919
1920 case IV2_T_ESN:
1921 idstr = STR_OR_ID(t_id, esn_p_map);
1922 break;
1923
1924 default:
1925 idstr = NULL;
1926 break;
1927 }
1928
1929 if (idstr)
1930 ND_PRINT((ndo," #%u type=%s id=%s ", pcount,
1931 STR_OR_ID(t.t_type, ikev2_t_type_map),
1932 idstr));
1933 else
1934 ND_PRINT((ndo," #%u type=%s id=%u ", pcount,
1935 STR_OR_ID(t.t_type, ikev2_t_type_map),
1936 t.t_id));
1937 cp = (u_char *)(p + 1);
1938 ep2 = (u_char *)p + item_len;
1939 while (cp < ep && cp < ep2) {
1940 if (map && nmap) {
1941 cp = ikev1_attrmap_print(ndo, cp, (ep < ep2) ? ep : ep2,
1942 map, nmap);
1943 } else
1944 cp = ikev1_attr_print(ndo, cp, (ep < ep2) ? ep : ep2);
1945 }
1946 if (ep < ep2)
1947 ND_PRINT((ndo,"..."));
1948 return cp;
1949 trunc:
1950 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_T)));
1951 return NULL;
1952 }
1953
1954 static const u_char *
1955 ikev2_p_print(netdissect_options *ndo, u_char tpay _U_, int pcount _U_,
1956 const struct isakmp_gen *ext, u_int item_len _U_,
1957 const u_char *ep, u_int32_t phase, u_int32_t doi0,
1958 u_int32_t proto0 _U_, int depth)
1959 {
1960 const struct ikev2_p *p;
1961 struct ikev2_p prop;
1962 const u_char *cp;
1963
1964 p = (struct ikev2_p *)ext;
1965 ND_TCHECK(*p);
1966 UNALIGNED_MEMCPY(&prop, ext, sizeof(prop));
1967 ikev2_pay_print(ndo, NPSTR(ISAKMP_NPTYPE_P), prop.h.critical);
1968
1969 ND_PRINT((ndo," #%u protoid=%s transform=%d len=%u",
1970 prop.p_no, PROTOIDSTR(prop.prot_id),
1971 prop.num_t, ntohs(prop.h.len)));
1972 if (prop.spi_size) {
1973 ND_PRINT((ndo," spi="));
1974 if (!rawprint(ndo, (caddr_t)(p + 1), prop.spi_size))
1975 goto trunc;
1976 }
1977
1978 ext = (struct isakmp_gen *)((u_char *)(p + 1) + prop.spi_size);
1979 ND_TCHECK(*ext);
1980
1981 cp = ikev2_sub_print(ndo, NULL, ISAKMP_NPTYPE_T, ext, ep, phase, doi0,
1982 prop.prot_id, depth);
1983
1984 return cp;
1985 trunc:
1986 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_P)));
1987 return NULL;
1988 }
1989
1990 static const u_char *
1991 ikev2_sa_print(netdissect_options *ndo, u_char tpay,
1992 const struct isakmp_gen *ext1,
1993 u_int item_len _U_, const u_char *ep _U_,
1994 u_int32_t phase _U_, u_int32_t doi _U_,
1995 u_int32_t proto _U_, int depth _U_)
1996 {
1997 struct isakmp_gen e;
1998 int osa_length, sa_length;
1999
2000 ND_TCHECK(*ext1);
2001 UNALIGNED_MEMCPY(&e, ext1, sizeof(e));
2002 ikev2_pay_print(ndo, "sa", e.critical);
2003
2004 osa_length= ntohs(e.len);
2005 sa_length = osa_length - 4;
2006 ND_PRINT((ndo," len=%d", sa_length));
2007
2008 ikev2_sub_print(ndo, NULL, ISAKMP_NPTYPE_P,
2009 ext1+1, ep,
2010 0, 0, 0, depth);
2011
2012 return (u_char *)ext1 + osa_length;
2013 trunc:
2014 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
2015 return NULL;
2016 }
2017
2018 static const u_char *
2019 ikev2_ke_print(netdissect_options *ndo, u_char tpay,
2020 const struct isakmp_gen *ext,
2021 u_int item_len _U_, const u_char *ep _U_,
2022 u_int32_t phase _U_, u_int32_t doi _U_,
2023 u_int32_t proto _U_, int depth _U_)
2024 {
2025 struct ikev2_ke ke;
2026 struct ikev2_ke *k;
2027
2028 k = (struct ikev2_ke *)ext;
2029 ND_TCHECK(*ext);
2030 UNALIGNED_MEMCPY(&ke, ext, sizeof(ke));
2031 ikev2_pay_print(ndo, NPSTR(tpay), ke.h.critical);
2032
2033 ND_PRINT((ndo," len=%u group=%s", ntohs(ke.h.len) - 8,
2034 STR_OR_ID(ntohs(ke.ke_group), dh_p_map)));
2035
2036 if (2 < ndo->ndo_vflag && 8 < ntohs(ke.h.len)) {
2037 ND_PRINT((ndo," "));
2038 if (!rawprint(ndo, (caddr_t)(k + 1), ntohs(ke.h.len) - 8))
2039 goto trunc;
2040 }
2041 return (u_char *)ext + ntohs(ke.h.len);
2042 trunc:
2043 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
2044 return NULL;
2045 }
2046
2047 static const u_char *
2048 ikev2_ID_print(netdissect_options *ndo, u_char tpay,
2049 const struct isakmp_gen *ext,
2050 u_int item_len _U_, const u_char *ep _U_,
2051 u_int32_t phase _U_, u_int32_t doi _U_,
2052 u_int32_t proto _U_, int depth _U_)
2053 {
2054 struct ikev2_id id;
2055 int id_len, idtype_len, i;
2056 unsigned int dumpascii, dumphex;
2057 unsigned char *typedata;
2058
2059 ND_TCHECK(*ext);
2060 UNALIGNED_MEMCPY(&id, ext, sizeof(id));
2061 ikev2_pay_print(ndo, NPSTR(tpay), id.h.critical);
2062
2063 id_len = ntohs(id.h.len);
2064
2065 ND_PRINT((ndo," len=%d", id_len - 4));
2066 if (2 < ndo->ndo_vflag && 4 < id_len) {
2067 ND_PRINT((ndo," "));
2068 if (!rawprint(ndo, (caddr_t)(ext + 1), id_len - 4))
2069 goto trunc;
2070 }
2071
2072 idtype_len =id_len - sizeof(struct ikev2_id);
2073 dumpascii = 0;
2074 dumphex = 0;
2075 typedata = (unsigned char *)(ext)+sizeof(struct ikev2_id);
2076
2077 switch(id.type) {
2078 case ID_IPV4_ADDR:
2079 ND_PRINT((ndo, " ipv4:"));
2080 dumphex=1;
2081 break;
2082 case ID_FQDN:
2083 ND_PRINT((ndo, " fqdn:"));
2084 dumpascii=1;
2085 break;
2086 case ID_RFC822_ADDR:
2087 ND_PRINT((ndo, " rfc822:"));
2088 dumpascii=1;
2089 break;
2090 case ID_IPV6_ADDR:
2091 ND_PRINT((ndo, " ipv6:"));
2092 dumphex=1;
2093 break;
2094 case ID_DER_ASN1_DN:
2095 ND_PRINT((ndo, " dn:"));
2096 dumphex=1;
2097 break;
2098 case ID_DER_ASN1_GN:
2099 ND_PRINT((ndo, " gn:"));
2100 dumphex=1;
2101 break;
2102 case ID_KEY_ID:
2103 ND_PRINT((ndo, " keyid:"));
2104 dumphex=1;
2105 break;
2106 }
2107
2108 if(dumpascii) {
2109 ND_TCHECK2(*typedata, idtype_len);
2110 for(i=0; i<idtype_len; i++) {
2111 if(ND_ISPRINT(typedata[i])) {
2112 ND_PRINT((ndo, "%c", typedata[i]));
2113 } else {
2114 ND_PRINT((ndo, "."));
2115 }
2116 }
2117 }
2118 if(dumphex) {
2119 if (!rawprint(ndo, (caddr_t)typedata, idtype_len))
2120 goto trunc;
2121 }
2122
2123 return (u_char *)ext + id_len;
2124 trunc:
2125 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
2126 return NULL;
2127 }
2128
2129 static const u_char *
2130 ikev2_cert_print(netdissect_options *ndo, u_char tpay,
2131 const struct isakmp_gen *ext,
2132 u_int item_len _U_, const u_char *ep _U_,
2133 u_int32_t phase _U_, u_int32_t doi _U_,
2134 u_int32_t proto _U_, int depth _U_)
2135 {
2136 return ikev2_gen_print(ndo, tpay, ext);
2137 }
2138
2139 static const u_char *
2140 ikev2_cr_print(netdissect_options *ndo, u_char tpay,
2141 const struct isakmp_gen *ext,
2142 u_int item_len _U_, const u_char *ep _U_,
2143 u_int32_t phase _U_, u_int32_t doi _U_,
2144 u_int32_t proto _U_, int depth _U_)
2145 {
2146 return ikev2_gen_print(ndo, tpay, ext);
2147 }
2148
2149 static const u_char *
2150 ikev2_auth_print(netdissect_options *ndo, u_char tpay,
2151 const struct isakmp_gen *ext,
2152 u_int item_len _U_, const u_char *ep _U_,
2153 u_int32_t phase _U_, u_int32_t doi _U_,
2154 u_int32_t proto _U_, int depth _U_)
2155 {
2156 struct ikev2_auth a;
2157 const char *v2_auth[]={ "invalid", "rsasig",
2158 "shared-secret", "dsssig" };
2159 u_char *authdata = (u_char*)ext + sizeof(a);
2160 unsigned int len;
2161
2162 ND_TCHECK(*ext);
2163 UNALIGNED_MEMCPY(&a, ext, sizeof(a));
2164 ikev2_pay_print(ndo, NPSTR(tpay), a.h.critical);
2165 len = ntohs(a.h.len);
2166
2167 ND_PRINT((ndo," len=%d method=%s", len-4,
2168 STR_OR_ID(a.auth_method, v2_auth)));
2169
2170 if (1 < ndo->ndo_vflag && 4 < len) {
2171 ND_PRINT((ndo," authdata=("));
2172 if (!rawprint(ndo, (caddr_t)authdata, len - sizeof(a)))
2173 goto trunc;
2174 ND_PRINT((ndo,") "));
2175 } else if(ndo->ndo_vflag && 4 < len) {
2176 if(!ike_show_somedata(ndo, authdata, ep)) goto trunc;
2177 }
2178
2179 return (u_char *)ext + len;
2180 trunc:
2181 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
2182 return NULL;
2183 }
2184
2185 static const u_char *
2186 ikev2_nonce_print(netdissect_options *ndo, u_char tpay,
2187 const struct isakmp_gen *ext,
2188 u_int item_len _U_, const u_char *ep _U_,
2189 u_int32_t phase _U_, u_int32_t doi _U_,
2190 u_int32_t proto _U_, int depth _U_)
2191 {
2192 struct isakmp_gen e;
2193
2194 ND_TCHECK(*ext);
2195 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
2196 ikev2_pay_print(ndo, "nonce", e.critical);
2197
2198 ND_PRINT((ndo," len=%d", ntohs(e.len) - 4));
2199 if (1 < ndo->ndo_vflag && 4 < ntohs(e.len)) {
2200 ND_PRINT((ndo," nonce=("));
2201 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
2202 goto trunc;
2203 ND_PRINT((ndo,") "));
2204 } else if(ndo->ndo_vflag && 4 < ntohs(e.len)) {
2205 if(!ike_show_somedata(ndo, (const u_char *)(ext+1), ep)) goto trunc;
2206 }
2207
2208 return (u_char *)ext + ntohs(e.len);
2209 trunc:
2210 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
2211 return NULL;
2212 }
2213
2214 /* notify payloads */
2215 static const u_char *
2216 ikev2_n_print(netdissect_options *ndo, u_char tpay _U_,
2217 const struct isakmp_gen *ext,
2218 u_int item_len _U_, const u_char *ep _U_,
2219 u_int32_t phase _U_, u_int32_t doi _U_,
2220 u_int32_t proto _U_, int depth _U_)
2221 {
2222 struct ikev2_n *p, n;
2223 const u_char *cp;
2224 u_char showspi, showdata, showsomedata;
2225 const char *notify_name;
2226 u_int32_t type;
2227
2228 p = (struct ikev2_n *)ext;
2229 ND_TCHECK(*p);
2230 UNALIGNED_MEMCPY(&n, ext, sizeof(n));
2231 ikev2_pay_print(ndo, NPSTR(ISAKMP_NPTYPE_N), n.h.critical);
2232
2233 showspi = 1;
2234 showdata = 0;
2235 showsomedata=0;
2236 notify_name=NULL;
2237
2238 ND_PRINT((ndo," prot_id=%s", PROTOIDSTR(n.prot_id)));
2239
2240 type = ntohs(n.type);
2241
2242 /* notify space is annoying sparse */
2243 switch(type) {
2244 case IV2_NOTIFY_UNSUPPORTED_CRITICAL_PAYLOAD:
2245 notify_name = "unsupported_critical_payload";
2246 showspi = 0;
2247 break;
2248
2249 case IV2_NOTIFY_INVALID_IKE_SPI:
2250 notify_name = "invalid_ike_spi";
2251 showspi = 1;
2252 break;
2253
2254 case IV2_NOTIFY_INVALID_MAJOR_VERSION:
2255 notify_name = "invalid_major_version";
2256 showspi = 0;
2257 break;
2258
2259 case IV2_NOTIFY_INVALID_SYNTAX:
2260 notify_name = "invalid_syntax";
2261 showspi = 1;
2262 break;
2263
2264 case IV2_NOTIFY_INVALID_MESSAGE_ID:
2265 notify_name = "invalid_message_id";
2266 showspi = 1;
2267 break;
2268
2269 case IV2_NOTIFY_INVALID_SPI:
2270 notify_name = "invalid_spi";
2271 showspi = 1;
2272 break;
2273
2274 case IV2_NOTIFY_NO_PROPOSAL_CHOSEN:
2275 notify_name = "no_protocol_chosen";
2276 showspi = 1;
2277 break;
2278
2279 case IV2_NOTIFY_INVALID_KE_PAYLOAD:
2280 notify_name = "invalid_ke_payload";
2281 showspi = 1;
2282 break;
2283
2284 case IV2_NOTIFY_AUTHENTICATION_FAILED:
2285 notify_name = "authentication_failed";
2286 showspi = 1;
2287 break;
2288
2289 case IV2_NOTIFY_SINGLE_PAIR_REQUIRED:
2290 notify_name = "single_pair_required";
2291 showspi = 1;
2292 break;
2293
2294 case IV2_NOTIFY_NO_ADDITIONAL_SAS:
2295 notify_name = "no_additional_sas";
2296 showspi = 0;
2297 break;
2298
2299 case IV2_NOTIFY_INTERNAL_ADDRESS_FAILURE:
2300 notify_name = "internal_address_failure";
2301 showspi = 0;
2302 break;
2303
2304 case IV2_NOTIFY_FAILED_CP_REQUIRED:
2305 notify_name = "failed:cp_required";
2306 showspi = 0;
2307 break;
2308
2309 case IV2_NOTIFY_INVALID_SELECTORS:
2310 notify_name = "invalid_selectors";
2311 showspi = 0;
2312 break;
2313
2314 case IV2_NOTIFY_INITIAL_CONTACT:
2315 notify_name = "initial_contact";
2316 showspi = 0;
2317 break;
2318
2319 case IV2_NOTIFY_SET_WINDOW_SIZE:
2320 notify_name = "set_window_size";
2321 showspi = 0;
2322 break;
2323
2324 case IV2_NOTIFY_ADDITIONAL_TS_POSSIBLE:
2325 notify_name = "additional_ts_possible";
2326 showspi = 0;
2327 break;
2328
2329 case IV2_NOTIFY_IPCOMP_SUPPORTED:
2330 notify_name = "ipcomp_supported";
2331 showspi = 0;
2332 break;
2333
2334 case IV2_NOTIFY_NAT_DETECTION_SOURCE_IP:
2335 notify_name = "nat_detection_source_ip";
2336 showspi = 1;
2337 break;
2338
2339 case IV2_NOTIFY_NAT_DETECTION_DESTINATION_IP:
2340 notify_name = "nat_detection_destination_ip";
2341 showspi = 1;
2342 break;
2343
2344 case IV2_NOTIFY_COOKIE:
2345 notify_name = "cookie";
2346 showspi = 1;
2347 showsomedata= 1;
2348 showdata= 0;
2349 break;
2350
2351 case IV2_NOTIFY_USE_TRANSPORT_MODE:
2352 notify_name = "use_transport_mode";
2353 showspi = 0;
2354 break;
2355
2356 case IV2_NOTIFY_HTTP_CERT_LOOKUP_SUPPORTED:
2357 notify_name = "http_cert_lookup_supported";
2358 showspi = 0;
2359 break;
2360
2361 case IV2_NOTIFY_REKEY_SA:
2362 notify_name = "rekey_sa";
2363 showspi = 1;
2364 break;
2365
2366 case IV2_NOTIFY_ESP_TFC_PADDING_NOT_SUPPORTED:
2367 notify_name = "tfc_padding_not_supported";
2368 showspi = 0;
2369 break;
2370
2371 case IV2_NOTIFY_NON_FIRST_FRAGMENTS_ALSO:
2372 notify_name = "non_first_fragment_also";
2373 showspi = 0;
2374 break;
2375
2376 default:
2377 if (type < 8192) {
2378 notify_name="error";
2379 } else if(type < 16384) {
2380 notify_name="private-error";
2381 } else if(type < 40960) {
2382 notify_name="status";
2383 } else {
2384 notify_name="private-status";
2385 }
2386 }
2387
2388 if(notify_name) {
2389 ND_PRINT((ndo," type=%u(%s)", type, notify_name));
2390 }
2391
2392
2393 if (showspi && n.spi_size) {
2394 ND_PRINT((ndo," spi="));
2395 if (!rawprint(ndo, (caddr_t)(p + 1), n.spi_size))
2396 goto trunc;
2397 }
2398
2399 cp = (u_char *)(p + 1) + n.spi_size;
2400
2401 if(3 < ndo->ndo_vflag) {
2402 showdata = 1;
2403 }
2404
2405 if ((showdata || (showsomedata && ep-cp < 30)) && cp < ep) {
2406 ND_PRINT((ndo," data=("));
2407 if (!rawprint(ndo, (caddr_t)(cp), ep - cp))
2408 goto trunc;
2409
2410 ND_PRINT((ndo,")"));
2411
2412 } else if(showsomedata && cp < ep) {
2413 if(!ike_show_somedata(ndo, cp, ep)) goto trunc;
2414 }
2415
2416 return (u_char *)ext + item_len;
2417 trunc:
2418 ND_PRINT((ndo," [|%s]", NPSTR(ISAKMP_NPTYPE_N)));
2419 return NULL;
2420 }
2421
2422 static const u_char *
2423 ikev2_d_print(netdissect_options *ndo, u_char tpay,
2424 const struct isakmp_gen *ext,
2425 u_int item_len _U_, const u_char *ep _U_,
2426 u_int32_t phase _U_, u_int32_t doi _U_,
2427 u_int32_t proto _U_, int depth _U_)
2428 {
2429 return ikev2_gen_print(ndo, tpay, ext);
2430 }
2431
2432 static const u_char *
2433 ikev2_vid_print(netdissect_options *ndo, u_char tpay,
2434 const struct isakmp_gen *ext,
2435 u_int item_len _U_, const u_char *ep _U_,
2436 u_int32_t phase _U_, u_int32_t doi _U_,
2437 u_int32_t proto _U_, int depth _U_)
2438 {
2439 struct isakmp_gen e;
2440 const u_char *vid;
2441 int i, len;
2442
2443 ND_TCHECK(*ext);
2444 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
2445 ikev2_pay_print(ndo, NPSTR(tpay), e.critical);
2446 ND_PRINT((ndo," len=%d vid=", ntohs(e.len) - 4));
2447
2448 vid = (const u_char *)(ext+1);
2449 len = ntohs(e.len) - 4;
2450 ND_TCHECK2(*vid, len);
2451 for(i=0; i<len; i++) {
2452 if(ND_ISPRINT(vid[i])) ND_PRINT((ndo, "%c", vid[i]));
2453 else ND_PRINT((ndo, "."));
2454 }
2455 if (2 < ndo->ndo_vflag && 4 < len) {
2456 ND_PRINT((ndo," "));
2457 if (!rawprint(ndo, (caddr_t)(ext + 1), ntohs(e.len) - 4))
2458 goto trunc;
2459 }
2460 return (u_char *)ext + ntohs(e.len);
2461 trunc:
2462 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
2463 return NULL;
2464 }
2465
2466 static const u_char *
2467 ikev2_TS_print(netdissect_options *ndo, u_char tpay,
2468 const struct isakmp_gen *ext,
2469 u_int item_len _U_, const u_char *ep _U_,
2470 u_int32_t phase _U_, u_int32_t doi _U_,
2471 u_int32_t proto _U_, int depth _U_)
2472 {
2473 return ikev2_gen_print(ndo, tpay, ext);
2474 }
2475
2476 static const u_char *
2477 ikev2_e_print(netdissect_options *ndo,
2478 #ifndef HAVE_LIBCRYPTO
2479 _U_
2480 #endif
2481 struct isakmp *base,
2482 u_char tpay,
2483 const struct isakmp_gen *ext,
2484 u_int item_len _U_, const u_char *ep _U_,
2485 #ifndef HAVE_LIBCRYPTO
2486 _U_
2487 #endif
2488 u_int32_t phase,
2489 #ifndef HAVE_LIBCRYPTO
2490 _U_
2491 #endif
2492 u_int32_t doi,
2493 #ifndef HAVE_LIBCRYPTO
2494 _U_
2495 #endif
2496 u_int32_t proto,
2497 #ifndef HAVE_LIBCRYPTO
2498 _U_
2499 #endif
2500 int depth)
2501 {
2502 struct isakmp_gen e;
2503 u_char *dat;
2504 volatile int dlen;
2505
2506 ND_TCHECK(*ext);
2507 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
2508 ikev2_pay_print(ndo, NPSTR(tpay), e.critical);
2509
2510 dlen = ntohs(e.len)-4;
2511
2512 ND_PRINT((ndo," len=%d", dlen));
2513 if (2 < ndo->ndo_vflag && 4 < dlen) {
2514 ND_PRINT((ndo," "));
2515 if (!rawprint(ndo, (caddr_t)(ext + 1), dlen))
2516 goto trunc;
2517 }
2518
2519 dat = (u_char *)(ext+1);
2520 ND_TCHECK2(*dat, dlen);
2521
2522 #ifdef HAVE_LIBCRYPTO
2523 /* try to decypt it! */
2524 if(esp_print_decrypt_buffer_by_ikev2(ndo,
2525 base->flags & ISAKMP_FLAG_I,
2526 base->i_ck, base->r_ck,
2527 dat, dat+dlen)) {
2528
2529 ext = (const struct isakmp_gen *)ndo->ndo_packetp;
2530
2531 /* got it decrypted, print stuff inside. */
2532 ikev2_sub_print(ndo, base, e.np, ext, ndo->ndo_snapend,
2533 phase, doi, proto, depth+1);
2534 }
2535 #endif
2536
2537
2538 /* always return NULL, because E must be at end, and NP refers
2539 * to what was inside.
2540 */
2541 return NULL;
2542 trunc:
2543 ND_PRINT((ndo," [|%s]", NPSTR(tpay)));
2544 return NULL;
2545 }
2546
2547 static const u_char *
2548 ikev2_cp_print(netdissect_options *ndo, u_char tpay,
2549 const struct isakmp_gen *ext,
2550 u_int item_len _U_, const u_char *ep _U_,
2551 u_int32_t phase _U_, u_int32_t doi _U_,
2552 u_int32_t proto _U_, int depth _U_)
2553 {
2554 return ikev2_gen_print(ndo, tpay, ext);
2555 }
2556
2557 static const u_char *
2558 ikev2_eap_print(netdissect_options *ndo, u_char tpay,
2559 const struct isakmp_gen *ext,
2560 u_int item_len _U_, const u_char *ep _U_,
2561 u_int32_t phase _U_, u_int32_t doi _U_,
2562 u_int32_t proto _U_, int depth _U_)
2563 {
2564 return ikev2_gen_print(ndo, tpay, ext);
2565 }
2566
2567 static const u_char *
2568 ike_sub0_print(netdissect_options *ndo,
2569 u_char np, const struct isakmp_gen *ext, const u_char *ep,
2570
2571 u_int32_t phase, u_int32_t doi, u_int32_t proto, int depth)
2572 {
2573 const u_char *cp;
2574 struct isakmp_gen e;
2575 u_int item_len;
2576
2577 cp = (u_char *)ext;
2578 ND_TCHECK(*ext);
2579 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
2580
2581 /*
2582 * Since we can't have a payload length of less than 4 bytes,
2583 * we need to bail out here if the generic header is nonsensical
2584 * or truncated, otherwise we could loop forever processing
2585 * zero-length items or otherwise misdissect the packet.
2586 */
2587 item_len = ntohs(e.len);
2588 if (item_len <= 4)
2589 return NULL;
2590
2591 if (NPFUNC(np)) {
2592 /*
2593 * XXX - what if item_len is too short, or too long,
2594 * for this payload type?
2595 */
2596 cp = (*npfunc[np])(ndo, np, ext, item_len, ep, phase, doi, proto, depth);
2597 } else {
2598 ND_PRINT((ndo,"%s", NPSTR(np)));
2599 cp += item_len;
2600 }
2601
2602 return cp;
2603 trunc:
2604 ND_PRINT((ndo," [|isakmp]"));
2605 return NULL;
2606 }
2607
2608 static const u_char *
2609 ikev1_sub_print(netdissect_options *ndo,
2610 u_char np, const struct isakmp_gen *ext, const u_char *ep,
2611 u_int32_t phase, u_int32_t doi, u_int32_t proto, int depth)
2612 {
2613 const u_char *cp;
2614 int i;
2615 struct isakmp_gen e;
2616
2617 cp = (const u_char *)ext;
2618
2619 while (np) {
2620 ND_TCHECK(*ext);
2621
2622 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
2623
2624 ND_TCHECK2(*ext, ntohs(e.len));
2625
2626 depth++;
2627 ND_PRINT((ndo,"\n"));
2628 for (i = 0; i < depth; i++)
2629 ND_PRINT((ndo," "));
2630 ND_PRINT((ndo,"("));
2631 cp = ike_sub0_print(ndo, np, ext, ep, phase, doi, proto, depth);
2632 ND_PRINT((ndo,")"));
2633 depth--;
2634
2635 if (cp == NULL) {
2636 /* Zero-length subitem */
2637 return NULL;
2638 }
2639
2640 np = e.np;
2641 ext = (struct isakmp_gen *)cp;
2642 }
2643 return cp;
2644 trunc:
2645 ND_PRINT((ndo," [|%s]", NPSTR(np)));
2646 return NULL;
2647 }
2648
2649 static char *
2650 numstr(int x)
2651 {
2652 static char buf[20];
2653 snprintf(buf, sizeof(buf), "#%d", x);
2654 return buf;
2655 }
2656
2657 static void
2658 ikev1_print(netdissect_options *ndo,
2659 const u_char *bp, u_int length,
2660 const u_char *bp2, struct isakmp *base)
2661 {
2662 const struct isakmp *p;
2663 const u_char *ep;
2664 u_char np;
2665 int i;
2666 int phase;
2667
2668 p = (const struct isakmp *)bp;
2669 ep = ndo->ndo_snapend;
2670
2671 phase = (EXTRACT_32BITS(base->msgid) == 0) ? 1 : 2;
2672 if (phase == 1)
2673 ND_PRINT((ndo," phase %d", phase));
2674 else
2675 ND_PRINT((ndo," phase %d/others", phase));
2676
2677 i = cookie_find(&base->i_ck);
2678 if (i < 0) {
2679 if (iszero((u_char *)&base->r_ck, sizeof(base->r_ck))) {
2680 /* the first packet */
2681 ND_PRINT((ndo," I"));
2682 if (bp2)
2683 cookie_record(&base->i_ck, bp2);
2684 } else
2685 ND_PRINT((ndo," ?"));
2686 } else {
2687 if (bp2 && cookie_isinitiator(i, bp2))
2688 ND_PRINT((ndo," I"));
2689 else if (bp2 && cookie_isresponder(i, bp2))
2690 ND_PRINT((ndo," R"));
2691 else
2692 ND_PRINT((ndo," ?"));
2693 }
2694
2695 ND_PRINT((ndo," %s", ETYPESTR(base->etype)));
2696 if (base->flags) {
2697 ND_PRINT((ndo,"[%s%s]", base->flags & ISAKMP_FLAG_E ? "E" : "",
2698 base->flags & ISAKMP_FLAG_C ? "C" : ""));
2699 }
2700
2701 if (ndo->ndo_vflag) {
2702 const struct isakmp_gen *ext;
2703
2704 ND_PRINT((ndo,":"));
2705
2706 /* regardless of phase... */
2707 if (base->flags & ISAKMP_FLAG_E) {
2708 /*
2709 * encrypted, nothing we can do right now.
2710 * we hope to decrypt the packet in the future...
2711 */
2712 ND_PRINT((ndo," [encrypted %s]", NPSTR(base->np)));
2713 goto done;
2714 }
2715
2716 CHECKLEN(p + 1, base->np);
2717 np = base->np;
2718 ext = (struct isakmp_gen *)(p + 1);
2719 ikev1_sub_print(ndo, np, ext, ep, phase, 0, 0, 0);
2720 }
2721
2722 done:
2723 if (ndo->ndo_vflag) {
2724 if (ntohl(base->len) != length) {
2725 ND_PRINT((ndo," (len mismatch: isakmp %u/ip %u)",
2726 (u_int32_t)ntohl(base->len), length));
2727 }
2728 }
2729 }
2730
2731 static const u_char *
2732 ikev2_sub0_print(netdissect_options *ndo, struct isakmp *base,
2733 u_char np, int pcount,
2734 const struct isakmp_gen *ext, const u_char *ep,
2735 u_int32_t phase, u_int32_t doi, u_int32_t proto, int depth)
2736 {
2737 const u_char *cp;
2738 struct isakmp_gen e;
2739 u_int item_len;
2740
2741 cp = (u_char *)ext;
2742 ND_TCHECK(*ext);
2743 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
2744
2745 /*
2746 * Since we can't have a payload length of less than 4 bytes,
2747 * we need to bail out here if the generic header is nonsensical
2748 * or truncated, otherwise we could loop forever processing
2749 * zero-length items or otherwise misdissect the packet.
2750 */
2751 item_len = ntohs(e.len);
2752 if (item_len <= 4)
2753 return NULL;
2754
2755 if(np == ISAKMP_NPTYPE_P) {
2756 cp = ikev2_p_print(ndo, np, pcount, ext, item_len,
2757 ep, phase, doi, proto, depth);
2758 } else if(np == ISAKMP_NPTYPE_T) {
2759 cp = ikev2_t_print(ndo, np, pcount, ext, item_len,
2760 ep, phase, doi, proto, depth);
2761 } else if(np == ISAKMP_NPTYPE_v2E) {
2762 cp = ikev2_e_print(ndo, base, np, ext, item_len,
2763 ep, phase, doi, proto, depth);
2764 } else if (NPFUNC(np)) {
2765 /*
2766 * XXX - what if item_len is too short, or too long,
2767 * for this payload type?
2768 */
2769 cp = (*npfunc[np])(ndo, np, /*pcount,*/ ext, item_len,
2770 ep, phase, doi, proto, depth);
2771 } else {
2772 ND_PRINT((ndo,"%s", NPSTR(np)));
2773 cp += item_len;
2774 }
2775
2776 return cp;
2777 trunc:
2778 ND_PRINT((ndo," [|isakmp]"));
2779 return NULL;
2780 }
2781
2782 static const u_char *
2783 ikev2_sub_print(netdissect_options *ndo,
2784 struct isakmp *base,
2785 u_char np, const struct isakmp_gen *ext, const u_char *ep,
2786 u_int32_t phase, u_int32_t doi, u_int32_t proto, int depth)
2787 {
2788 const u_char *cp;
2789 int i;
2790 int pcount;
2791 struct isakmp_gen e;
2792
2793 cp = (const u_char *)ext;
2794 pcount = 0;
2795 while (np) {
2796 pcount++;
2797 ND_TCHECK(*ext);
2798
2799 UNALIGNED_MEMCPY(&e, ext, sizeof(e));
2800
2801 ND_TCHECK2(*ext, ntohs(e.len));
2802
2803 depth++;
2804 ND_PRINT((ndo,"\n"));
2805 for (i = 0; i < depth; i++)
2806 ND_PRINT((ndo," "));
2807 ND_PRINT((ndo,"("));
2808 cp = ikev2_sub0_print(ndo, base, np, pcount,
2809 ext, ep, phase, doi, proto, depth);
2810 ND_PRINT((ndo,")"));
2811 depth--;
2812
2813 if (cp == NULL) {
2814 /* Zero-length subitem */
2815 return NULL;
2816 }
2817
2818 np = e.np;
2819 ext = (struct isakmp_gen *)cp;
2820 }
2821 return cp;
2822 trunc:
2823 ND_PRINT((ndo," [|%s]", NPSTR(np)));
2824 return NULL;
2825 }
2826
2827 static void
2828 ikev2_print(netdissect_options *ndo,
2829 const u_char *bp, u_int length,
2830 const u_char *bp2 _U_, struct isakmp *base)
2831 {
2832 const struct isakmp *p;
2833 const u_char *ep;
2834 u_char np;
2835 int phase;
2836
2837 p = (const struct isakmp *)bp;
2838 ep = ndo->ndo_snapend;
2839
2840 phase = (EXTRACT_32BITS(base->msgid) == 0) ? 1 : 2;
2841 if (phase == 1)
2842 ND_PRINT((ndo, " parent_sa"));
2843 else
2844 ND_PRINT((ndo, " child_sa "));
2845
2846 ND_PRINT((ndo, " %s", ETYPESTR(base->etype)));
2847 if (base->flags) {
2848 ND_PRINT((ndo, "[%s%s%s]",
2849 base->flags & ISAKMP_FLAG_I ? "I" : "",
2850 base->flags & ISAKMP_FLAG_V ? "V" : "",
2851 base->flags & ISAKMP_FLAG_R ? "R" : ""));
2852 }
2853
2854 if (ndo->ndo_vflag) {
2855 const struct isakmp_gen *ext;
2856
2857 ND_PRINT((ndo, ":"));
2858
2859 /* regardless of phase... */
2860 if (base->flags & ISAKMP_FLAG_E) {
2861 /*
2862 * encrypted, nothing we can do right now.
2863 * we hope to decrypt the packet in the future...
2864 */
2865 ND_PRINT((ndo, " [encrypted %s]", NPSTR(base->np)));
2866 goto done;
2867 }
2868
2869 CHECKLEN(p + 1, base->np)
2870
2871 np = base->np;
2872 ext = (struct isakmp_gen *)(p + 1);
2873 ikev2_sub_print(ndo, base, np, ext, ep, phase, 0, 0, 0);
2874 }
2875
2876 done:
2877 if (ndo->ndo_vflag) {
2878 if (ntohl(base->len) != length) {
2879 ND_PRINT((ndo, " (len mismatch: isakmp %u/ip %u)",
2880 (u_int32_t)ntohl(base->len), length));
2881 }
2882 }
2883 }
2884
2885 void
2886 isakmp_print(netdissect_options *ndo,
2887 const u_char *bp, u_int length,
2888 const u_char *bp2)
2889 {
2890 const struct isakmp *p;
2891 struct isakmp base;
2892 const u_char *ep;
2893 int major, minor;
2894
2895 #ifdef HAVE_LIBCRYPTO
2896 /* initialize SAs */
2897 if (ndo->ndo_sa_list_head == NULL) {
2898 if (ndo->ndo_espsecret)
2899 esp_print_decodesecret(ndo);
2900 }
2901 #endif
2902
2903 p = (const struct isakmp *)bp;
2904 ep = ndo->ndo_snapend;
2905
2906 if ((struct isakmp *)ep < p + 1) {
2907 ND_PRINT((ndo,"[|isakmp]"));
2908 return;
2909 }
2910
2911 UNALIGNED_MEMCPY(&base, p, sizeof(base));
2912
2913 ND_PRINT((ndo,"isakmp"));
2914 major = (base.vers & ISAKMP_VERS_MAJOR)
2915 >> ISAKMP_VERS_MAJOR_SHIFT;
2916 minor = (base.vers & ISAKMP_VERS_MINOR)
2917 >> ISAKMP_VERS_MINOR_SHIFT;
2918
2919 if (ndo->ndo_vflag) {
2920 ND_PRINT((ndo," %d.%d", major, minor));
2921 }
2922
2923 if (ndo->ndo_vflag) {
2924 ND_PRINT((ndo," msgid "));
2925 hexprint(ndo, (caddr_t)&base.msgid, sizeof(base.msgid));
2926 }
2927
2928 if (1 < ndo->ndo_vflag) {
2929 ND_PRINT((ndo," cookie "));
2930 hexprint(ndo, (caddr_t)&base.i_ck, sizeof(base.i_ck));
2931 ND_PRINT((ndo,"->"));
2932 hexprint(ndo, (caddr_t)&base.r_ck, sizeof(base.r_ck));
2933 }
2934 ND_PRINT((ndo,":"));
2935
2936 switch(major) {
2937 case IKEv1_MAJOR_VERSION:
2938 ikev1_print(ndo, bp, length, bp2, &base);
2939 break;
2940
2941 case IKEv2_MAJOR_VERSION:
2942 ikev2_print(ndo, bp, length, bp2, &base);
2943 break;
2944 }
2945 }
2946
2947 void
2948 isakmp_rfc3948_print(netdissect_options *ndo,
2949 const u_char *bp, u_int length,
2950 const u_char *bp2)
2951 {
2952
2953 if(length == 1 && bp[0]==0xff) {
2954 ND_PRINT((ndo, "isakmp-nat-keep-alive"));
2955 return;
2956 }
2957
2958 if(length < 4) {
2959 goto trunc;
2960 }
2961
2962 /*
2963 * see if this is an IKE packet
2964 */
2965 if(bp[0]==0 && bp[1]==0 && bp[2]==0 && bp[3]==0) {
2966 ND_PRINT((ndo, "NONESP-encap: "));
2967 isakmp_print(ndo, bp+4, length-4, bp2);
2968 return;
2969 }
2970
2971 /* must be an ESP packet */
2972 {
2973 int nh, enh, padlen;
2974 int advance;
2975
2976 ND_PRINT((ndo, "UDP-encap: "));
2977
2978 advance = esp_print(ndo, bp, length, bp2, &enh, &padlen);
2979 if(advance <= 0)
2980 return;
2981
2982 bp += advance;
2983 length -= advance + padlen;
2984 nh = enh & 0xff;
2985
2986 ip_print_inner(ndo, bp, length, nh, bp2);
2987 return;
2988 }
2989
2990 trunc:
2991 ND_PRINT((ndo,"[|isakmp]"));
2992 return;
2993 }
2994
2995 /*
2996 * Local Variables:
2997 * c-style: whitesmith
2998 * c-basic-offset: 8
2999 * End:
3000 */
3001
3002
3003
3004