1 /* NetBSD: print-ah.c,v 1.4 1996/05/20 00:41:16 fvdl Exp */ 2 3 /* 4 * Copyright (c) 1988, 1989, 1990, 1991, 1992, 1993, 1994 5 * The Regents of the University of California. All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that: (1) source code distributions 9 * retain the above copyright notice and this paragraph in its entirety, (2) 10 * distributions including binary code include the above copyright notice and 11 * this paragraph in its entirety in the documentation or other materials 12 * provided with the distribution, and (3) all advertising materials mentioning 13 * features or use of this software display the following acknowledgement: 14 * ``This product includes software developed by the University of California, 15 * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of 16 * the University nor the names of its contributors may be used to endorse 17 * or promote products derived from this software without specific prior 18 * written permission. 19 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED 20 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF 21 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 22 */ 23 24 #include <sys/cdefs.h> 25 #ifndef lint 26 __RCSID("$NetBSD: print-esp.c,v 1.9 2017/09/08 14:01:13 christos Exp $"); 27 #endif 28 29 /* \summary: IPSEC Encapsulating Security Payload (ESP) printer */ 30 31 #ifdef HAVE_CONFIG_H 32 #include "config.h" 33 #endif 34 35 #include <netdissect-stdinc.h> 36 37 #include <string.h> 38 #include <stdlib.h> 39 40 /* Any code in this file that depends on HAVE_LIBCRYPTO depends on 41 * HAVE_OPENSSL_EVP_H too. Undefining the former when the latter isn't defined 42 * is the simplest way of handling the dependency. 43 */ 44 #ifdef HAVE_LIBCRYPTO 45 #ifdef HAVE_OPENSSL_EVP_H 46 #include <openssl/evp.h> 47 #else 48 #undef HAVE_LIBCRYPTO 49 #endif 50 #endif 51 52 #include "netdissect.h" 53 #include "strtoaddr.h" 54 #include "extract.h" 55 56 #include "ascii_strcasecmp.h" 57 58 #include "ip.h" 59 #include "ip6.h" 60 61 /* 62 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. 63 * All rights reserved. 64 * 65 * Redistribution and use in source and binary forms, with or without 66 * modification, are permitted provided that the following conditions 67 * are met: 68 * 1. Redistributions of source code must retain the above copyright 69 * notice, this list of conditions and the following disclaimer. 70 * 2. Redistributions in binary form must reproduce the above copyright 71 * notice, this list of conditions and the following disclaimer in the 72 * documentation and/or other materials provided with the distribution. 73 * 3. Neither the name of the project nor the names of its contributors 74 * may be used to endorse or promote products derived from this software 75 * without specific prior written permission. 76 * 77 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 78 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 79 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 80 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 81 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 82 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 83 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 84 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 85 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 86 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 87 * SUCH DAMAGE. 88 */ 89 90 /* 91 * RFC1827/2406 Encapsulated Security Payload. 92 */ 93 94 struct newesp { 95 uint32_t esp_spi; /* ESP */ 96 uint32_t esp_seq; /* Sequence number */ 97 /*variable size*/ /* (IV and) Payload data */ 98 /*variable size*/ /* padding */ 99 /*8bit*/ /* pad size */ 100 /*8bit*/ /* next header */ 101 /*8bit*/ /* next header */ 102 /*variable size, 32bit bound*/ /* Authentication data */ 103 }; 104 105 #ifdef HAVE_LIBCRYPTO 106 union inaddr_u { 107 struct in_addr in4; 108 struct in6_addr in6; 109 }; 110 struct sa_list { 111 struct sa_list *next; 112 u_int daddr_version; 113 union inaddr_u daddr; 114 uint32_t spi; /* if == 0, then IKEv2 */ 115 int initiator; 116 u_char spii[8]; /* for IKEv2 */ 117 u_char spir[8]; 118 const EVP_CIPHER *evp; 119 int ivlen; 120 int authlen; 121 u_char authsecret[256]; 122 int authsecret_len; 123 u_char secret[256]; /* is that big enough for all secrets? */ 124 int secretlen; 125 }; 126 127 #ifndef HAVE_EVP_CIPHER_CTX_NEW 128 /* 129 * Allocate an EVP_CIPHER_CTX. 130 * Used if we have an older version of OpenSSL that doesn't provide 131 * routines to allocate and free them. 132 */ 133 static EVP_CIPHER_CTX * 134 EVP_CIPHER_CTX_new(void) 135 { 136 EVP_CIPHER_CTX *ctx; 137 138 ctx = malloc(sizeof(*ctx)); 139 if (ctx == NULL) 140 return (NULL); 141 memset(ctx, 0, sizeof(*ctx)); 142 return (ctx); 143 } 144 145 static void 146 EVP_CIPHER_CTX_free(EVP_CIPHER_CTX *ctx) 147 { 148 EVP_CIPHER_CTX_cleanup(ctx); 149 free(ctx); 150 } 151 #endif 152 153 #ifdef HAVE_EVP_CIPHERINIT_EX 154 /* 155 * Initialize the cipher by calling EVP_CipherInit_ex(), because 156 * calling EVP_CipherInit() will reset the cipher context, clearing 157 * the cipher, so calling it twice, with the second call having a 158 * null cipher, will clear the already-set cipher. EVP_CipherInit_ex(), 159 * however, won't reset the cipher context, so you can use it to specify 160 * the IV oin a second call after a first call to EVP_CipherInit_ex() 161 * to set the cipher and the key. 162 * 163 * XXX - is there some reason why we need to make two calls? 164 */ 165 static int 166 set_cipher_parameters(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher, 167 const unsigned char *key, 168 const unsigned char *iv, int enc) 169 { 170 return EVP_CipherInit_ex(ctx, cipher, NULL, key, iv, enc); 171 } 172 #else 173 /* 174 * Initialize the cipher by calling EVP_CipherInit(), because we don't 175 * have EVP_CipherInit_ex(); we rely on it not trashing the context. 176 */ 177 static int 178 set_cipher_parameters(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher, 179 const unsigned char *key, 180 const unsigned char *iv, int enc) 181 { 182 return EVP_CipherInit(ctx, cipher, key, iv, enc); 183 } 184 #endif 185 186 /* 187 * this will adjust ndo_packetp and ndo_snapend to new buffer! 188 */ 189 USES_APPLE_DEPRECATED_API 190 int esp_print_decrypt_buffer_by_ikev2(netdissect_options *ndo, 191 int initiator, 192 u_char spii[8], u_char spir[8], 193 const u_char *buf, const u_char *end) 194 { 195 struct sa_list *sa; 196 const u_char *iv; 197 unsigned int len; 198 EVP_CIPHER_CTX *ctx; 199 unsigned int block_size, output_buffer_size; 200 u_char *output_buffer; 201 202 /* initiator arg is any non-zero value */ 203 if(initiator) initiator=1; 204 205 /* see if we can find the SA, and if so, decode it */ 206 for (sa = ndo->ndo_sa_list_head; sa != NULL; sa = sa->next) { 207 if (sa->spi == 0 208 && initiator == sa->initiator 209 && memcmp(spii, sa->spii, 8) == 0 210 && memcmp(spir, sa->spir, 8) == 0) 211 break; 212 } 213 214 if(sa == NULL) return 0; 215 if(sa->evp == NULL) return 0; 216 217 /* 218 * remove authenticator, and see if we still have something to 219 * work with 220 */ 221 end = end - sa->authlen; 222 iv = buf; 223 buf = buf + sa->ivlen; 224 len = end-buf; 225 226 if(end <= buf) return 0; 227 228 ctx = EVP_CIPHER_CTX_new(); 229 if (ctx == NULL) 230 return 0; 231 if (set_cipher_parameters(ctx, sa->evp, sa->secret, NULL, 0) < 0) 232 (*ndo->ndo_warning)(ndo, "espkey init failed"); 233 set_cipher_parameters(ctx, NULL, NULL, iv, 0); 234 /* 235 * Allocate a buffer for the decrypted data. 236 * The output buffer must be separate from the input buffer, and 237 * its size must be a multiple of the cipher block size. 238 */ 239 block_size = (unsigned int)EVP_CIPHER_CTX_block_size(ctx); 240 output_buffer_size = len + (block_size - len % block_size); 241 output_buffer = (u_char *)malloc(output_buffer_size); 242 if (output_buffer == NULL) { 243 (*ndo->ndo_warning)(ndo, "can't allocate memory for decryption buffer"); 244 EVP_CIPHER_CTX_free(ctx); 245 return 0; 246 } 247 EVP_Cipher(ctx, output_buffer, buf, len); 248 EVP_CIPHER_CTX_free(ctx); 249 250 /* 251 * XXX - of course this is wrong, because buf is a const buffer, 252 * but changing this would require a more complicated fix. 253 */ 254 memcpy(__UNCONST(buf), output_buffer, len); 255 free(output_buffer); 256 257 ndo->ndo_packetp = buf; 258 ndo->ndo_snapend = end; 259 260 return 1; 261 } 262 USES_APPLE_RST 263 264 static void esp_print_addsa(netdissect_options *ndo, 265 struct sa_list *sa, int sa_def) 266 { 267 /* copy the "sa" */ 268 269 struct sa_list *nsa; 270 271 nsa = (struct sa_list *)malloc(sizeof(struct sa_list)); 272 if (nsa == NULL) 273 (*ndo->ndo_error)(ndo, "ran out of memory to allocate sa structure"); 274 275 *nsa = *sa; 276 277 if (sa_def) 278 ndo->ndo_sa_default = nsa; 279 280 nsa->next = ndo->ndo_sa_list_head; 281 ndo->ndo_sa_list_head = nsa; 282 } 283 284 285 static u_int hexdigit(netdissect_options *ndo, char hex) 286 { 287 if (hex >= '0' && hex <= '9') 288 return (hex - '0'); 289 else if (hex >= 'A' && hex <= 'F') 290 return (hex - 'A' + 10); 291 else if (hex >= 'a' && hex <= 'f') 292 return (hex - 'a' + 10); 293 else { 294 (*ndo->ndo_error)(ndo, "invalid hex digit %c in espsecret\n", hex); 295 return 0; 296 } 297 } 298 299 static u_int hex2byte(netdissect_options *ndo, char *hexstring) 300 { 301 u_int byte; 302 303 byte = (hexdigit(ndo, hexstring[0]) << 4) + hexdigit(ndo, hexstring[1]); 304 return byte; 305 } 306 307 /* 308 * returns size of binary, 0 on failure. 309 */ 310 static 311 int espprint_decode_hex(netdissect_options *ndo, 312 u_char *binbuf, unsigned int binbuf_len, 313 char *hex) 314 { 315 unsigned int len; 316 int i; 317 318 len = strlen(hex) / 2; 319 320 if (len > binbuf_len) { 321 (*ndo->ndo_warning)(ndo, "secret is too big: %d\n", len); 322 return 0; 323 } 324 325 i = 0; 326 while (hex[0] != '\0' && hex[1]!='\0') { 327 binbuf[i] = hex2byte(ndo, hex); 328 hex += 2; 329 i++; 330 } 331 332 return i; 333 } 334 335 /* 336 * decode the form: SPINUM@IP <tab> ALGONAME:0xsecret 337 */ 338 339 USES_APPLE_DEPRECATED_API 340 static int 341 espprint_decode_encalgo(netdissect_options *ndo, 342 char *decode, struct sa_list *sa) 343 { 344 size_t i; 345 const EVP_CIPHER *evp; 346 int authlen = 0; 347 char *colon, *p; 348 349 colon = strchr(decode, ':'); 350 if (colon == NULL) { 351 (*ndo->ndo_warning)(ndo, "failed to decode espsecret: %s\n", decode); 352 return 0; 353 } 354 *colon = '\0'; 355 356 if (strlen(decode) > strlen("-hmac96") && 357 !strcmp(decode + strlen(decode) - strlen("-hmac96"), 358 "-hmac96")) { 359 p = strstr(decode, "-hmac96"); 360 *p = '\0'; 361 authlen = 12; 362 } 363 if (strlen(decode) > strlen("-cbc") && 364 !strcmp(decode + strlen(decode) - strlen("-cbc"), "-cbc")) { 365 p = strstr(decode, "-cbc"); 366 *p = '\0'; 367 } 368 evp = EVP_get_cipherbyname(decode); 369 370 if (!evp) { 371 (*ndo->ndo_warning)(ndo, "failed to find cipher algo %s\n", decode); 372 sa->evp = NULL; 373 sa->authlen = 0; 374 sa->ivlen = 0; 375 return 0; 376 } 377 378 sa->evp = evp; 379 sa->authlen = authlen; 380 sa->ivlen = EVP_CIPHER_iv_length(evp); 381 382 colon++; 383 if (colon[0] == '0' && colon[1] == 'x') { 384 /* decode some hex! */ 385 386 colon += 2; 387 sa->secretlen = espprint_decode_hex(ndo, sa->secret, sizeof(sa->secret), colon); 388 if(sa->secretlen == 0) return 0; 389 } else { 390 i = strlen(colon); 391 392 if (i < sizeof(sa->secret)) { 393 memcpy(sa->secret, colon, i); 394 sa->secretlen = i; 395 } else { 396 memcpy(sa->secret, colon, sizeof(sa->secret)); 397 sa->secretlen = sizeof(sa->secret); 398 } 399 } 400 401 return 1; 402 } 403 USES_APPLE_RST 404 405 /* 406 * for the moment, ignore the auth algorith, just hard code the authenticator 407 * length. Need to research how openssl looks up HMAC stuff. 408 */ 409 static int 410 espprint_decode_authalgo(netdissect_options *ndo, 411 char *decode, struct sa_list *sa) 412 { 413 char *colon; 414 415 colon = strchr(decode, ':'); 416 if (colon == NULL) { 417 (*ndo->ndo_warning)(ndo, "failed to decode espsecret: %s\n", decode); 418 return 0; 419 } 420 *colon = '\0'; 421 422 if(ascii_strcasecmp(colon,"sha1") == 0 || 423 ascii_strcasecmp(colon,"md5") == 0) { 424 sa->authlen = 12; 425 } 426 return 1; 427 } 428 429 static void esp_print_decode_ikeline(netdissect_options *ndo, char *line, 430 const char *file, int lineno) 431 { 432 /* it's an IKEv2 secret, store it instead */ 433 struct sa_list sa1; 434 435 char *init; 436 char *icookie, *rcookie; 437 int ilen, rlen; 438 char *authkey; 439 char *enckey; 440 441 init = strsep(&line, " \t"); 442 icookie = strsep(&line, " \t"); 443 rcookie = strsep(&line, " \t"); 444 authkey = strsep(&line, " \t"); 445 enckey = strsep(&line, " \t"); 446 447 /* if any fields are missing */ 448 if(!init || !icookie || !rcookie || !authkey || !enckey) { 449 (*ndo->ndo_warning)(ndo, "print_esp: failed to find all fields for ikev2 at %s:%u", 450 file, lineno); 451 452 return; 453 } 454 455 ilen = strlen(icookie); 456 rlen = strlen(rcookie); 457 458 if((init[0]!='I' && init[0]!='R') 459 || icookie[0]!='0' || icookie[1]!='x' 460 || rcookie[0]!='0' || rcookie[1]!='x' 461 || ilen!=18 462 || rlen!=18) { 463 (*ndo->ndo_warning)(ndo, "print_esp: line %s:%u improperly formatted.", 464 file, lineno); 465 466 (*ndo->ndo_warning)(ndo, "init=%s icookie=%s(%u) rcookie=%s(%u)", 467 init, icookie, ilen, rcookie, rlen); 468 469 return; 470 } 471 472 sa1.spi = 0; 473 sa1.initiator = (init[0] == 'I'); 474 if(espprint_decode_hex(ndo, sa1.spii, sizeof(sa1.spii), icookie+2)!=8) 475 return; 476 477 if(espprint_decode_hex(ndo, sa1.spir, sizeof(sa1.spir), rcookie+2)!=8) 478 return; 479 480 if(!espprint_decode_encalgo(ndo, enckey, &sa1)) return; 481 482 if(!espprint_decode_authalgo(ndo, authkey, &sa1)) return; 483 484 esp_print_addsa(ndo, &sa1, FALSE); 485 } 486 487 /* 488 * 489 * special form: file /name 490 * causes us to go read from this file instead. 491 * 492 */ 493 static void esp_print_decode_onesecret(netdissect_options *ndo, char *line, 494 const char *file, int lineno) 495 { 496 struct sa_list sa1; 497 int sa_def; 498 499 char *spikey; 500 char *decode; 501 502 spikey = strsep(&line, " \t"); 503 sa_def = 0; 504 memset(&sa1, 0, sizeof(struct sa_list)); 505 506 /* if there is only one token, then it is an algo:key token */ 507 if (line == NULL) { 508 decode = spikey; 509 spikey = NULL; 510 /* sa1.daddr.version = 0; */ 511 /* memset(&sa1.daddr, 0, sizeof(sa1.daddr)); */ 512 /* sa1.spi = 0; */ 513 sa_def = 1; 514 } else 515 decode = line; 516 517 if (spikey && ascii_strcasecmp(spikey, "file") == 0) { 518 /* open file and read it */ 519 FILE *secretfile; 520 char fileline[1024]; 521 int subfile_lineno=0; 522 char *nl; 523 char *filename = line; 524 525 secretfile = fopen(filename, FOPEN_READ_TXT); 526 if (secretfile == NULL) { 527 (*ndo->ndo_error)(ndo, "print_esp: can't open %s: %s\n", 528 filename, strerror(errno)); 529 return; 530 } 531 532 while (fgets(fileline, sizeof(fileline)-1, secretfile) != NULL) { 533 subfile_lineno++; 534 /* remove newline from the line */ 535 nl = strchr(fileline, '\n'); 536 if (nl) 537 *nl = '\0'; 538 if (fileline[0] == '#') continue; 539 if (fileline[0] == '\0') continue; 540 541 esp_print_decode_onesecret(ndo, fileline, filename, subfile_lineno); 542 } 543 fclose(secretfile); 544 545 return; 546 } 547 548 if (spikey && ascii_strcasecmp(spikey, "ikev2") == 0) { 549 esp_print_decode_ikeline(ndo, line, file, lineno); 550 return; 551 } 552 553 if (spikey) { 554 555 char *spistr, *foo; 556 uint32_t spino; 557 558 spistr = strsep(&spikey, "@"); 559 560 spino = strtoul(spistr, &foo, 0); 561 if (spistr == foo || !spikey) { 562 (*ndo->ndo_warning)(ndo, "print_esp: failed to decode spi# %s\n", foo); 563 return; 564 } 565 566 sa1.spi = spino; 567 568 if (strtoaddr6(spikey, &sa1.daddr.in6) == 1) { 569 sa1.daddr_version = 6; 570 } else if (strtoaddr(spikey, &sa1.daddr.in4) == 1) { 571 sa1.daddr_version = 4; 572 } else { 573 (*ndo->ndo_warning)(ndo, "print_esp: can not decode IP# %s\n", spikey); 574 return; 575 } 576 } 577 578 if (decode) { 579 /* skip any blank spaces */ 580 while (isspace((unsigned char)*decode)) 581 decode++; 582 583 if(!espprint_decode_encalgo(ndo, decode, &sa1)) { 584 return; 585 } 586 } 587 588 esp_print_addsa(ndo, &sa1, sa_def); 589 } 590 591 USES_APPLE_DEPRECATED_API 592 static void esp_init(netdissect_options *ndo _U_) 593 { 594 /* 595 * 0.9.6 doesn't appear to define OPENSSL_API_COMPAT, so 596 * we check whether it's undefined or it's less than the 597 * value for 1.1.0. 598 */ 599 #if !defined(OPENSSL_API_COMPAT) || OPENSSL_API_COMPAT < 0x10100000L 600 OpenSSL_add_all_algorithms(); 601 #endif 602 EVP_add_cipher_alias(SN_des_ede3_cbc, "3des"); 603 } 604 USES_APPLE_RST 605 606 void esp_print_decodesecret(netdissect_options *ndo) 607 { 608 char *line; 609 char *p; 610 static int initialized = 0; 611 612 if (!initialized) { 613 esp_init(ndo); 614 initialized = 1; 615 } 616 617 p = ndo->ndo_espsecret; 618 619 while (p && p[0] != '\0') { 620 /* pick out the first line or first thing until a comma */ 621 if ((line = strsep(&p, "\n,")) == NULL) { 622 line = p; 623 p = NULL; 624 } 625 626 esp_print_decode_onesecret(ndo, line, "cmdline", 0); 627 } 628 629 ndo->ndo_espsecret = NULL; 630 } 631 632 #endif 633 634 #ifdef HAVE_LIBCRYPTO 635 USES_APPLE_DEPRECATED_API 636 #endif 637 int 638 esp_print(netdissect_options *ndo, 639 const u_char *bp, const int length, const u_char *bp2 640 #ifndef HAVE_LIBCRYPTO 641 _U_ 642 #endif 643 , 644 int *nhdr 645 #ifndef HAVE_LIBCRYPTO 646 _U_ 647 #endif 648 , 649 int *padlen 650 #ifndef HAVE_LIBCRYPTO 651 _U_ 652 #endif 653 ) 654 { 655 register const struct newesp *esp; 656 register const u_char *ep; 657 #ifdef HAVE_LIBCRYPTO 658 const struct ip *ip; 659 struct sa_list *sa = NULL; 660 const struct ip6_hdr *ip6 = NULL; 661 int advance; 662 int len; 663 u_char *secret; 664 int ivlen = 0; 665 const u_char *ivoff; 666 const u_char *p; 667 EVP_CIPHER_CTX *ctx; 668 unsigned int block_size, output_buffer_size; 669 u_char *output_buffer; 670 #endif 671 672 esp = (const struct newesp *)bp; 673 674 #ifdef HAVE_LIBCRYPTO 675 secret = NULL; 676 advance = 0; 677 #endif 678 679 #if 0 680 /* keep secret out of a register */ 681 p = (u_char *)&secret; 682 #endif 683 684 /* 'ep' points to the end of available data. */ 685 ep = ndo->ndo_snapend; 686 687 if ((const u_char *)(esp + 1) >= ep) { 688 ND_PRINT((ndo, "[|ESP]")); 689 goto fail; 690 } 691 ND_PRINT((ndo, "ESP(spi=0x%08x", EXTRACT_32BITS(&esp->esp_spi))); 692 ND_PRINT((ndo, ",seq=0x%x)", EXTRACT_32BITS(&esp->esp_seq))); 693 ND_PRINT((ndo, ", length %u", length)); 694 695 #ifndef HAVE_LIBCRYPTO 696 goto fail; 697 #else 698 /* initiailize SAs */ 699 if (ndo->ndo_sa_list_head == NULL) { 700 if (!ndo->ndo_espsecret) 701 goto fail; 702 703 esp_print_decodesecret(ndo); 704 } 705 706 if (ndo->ndo_sa_list_head == NULL) 707 goto fail; 708 709 ip = (const struct ip *)bp2; 710 switch (IP_V(ip)) { 711 case 6: 712 ip6 = (const struct ip6_hdr *)bp2; 713 /* we do not attempt to decrypt jumbograms */ 714 if (!EXTRACT_16BITS(&ip6->ip6_plen)) 715 goto fail; 716 /* if we can't get nexthdr, we do not need to decrypt it */ 717 len = sizeof(struct ip6_hdr) + EXTRACT_16BITS(&ip6->ip6_plen); 718 719 /* see if we can find the SA, and if so, decode it */ 720 for (sa = ndo->ndo_sa_list_head; sa != NULL; sa = sa->next) { 721 if (sa->spi == EXTRACT_32BITS(&esp->esp_spi) && 722 sa->daddr_version == 6 && 723 UNALIGNED_MEMCMP(&sa->daddr.in6, &ip6->ip6_dst, 724 sizeof(struct in6_addr)) == 0) { 725 break; 726 } 727 } 728 break; 729 case 4: 730 /* nexthdr & padding are in the last fragment */ 731 if (EXTRACT_16BITS(&ip->ip_off) & IP_MF) 732 goto fail; 733 len = EXTRACT_16BITS(&ip->ip_len); 734 735 /* see if we can find the SA, and if so, decode it */ 736 for (sa = ndo->ndo_sa_list_head; sa != NULL; sa = sa->next) { 737 if (sa->spi == EXTRACT_32BITS(&esp->esp_spi) && 738 sa->daddr_version == 4 && 739 UNALIGNED_MEMCMP(&sa->daddr.in4, &ip->ip_dst, 740 sizeof(struct in_addr)) == 0) { 741 break; 742 } 743 } 744 break; 745 default: 746 goto fail; 747 } 748 749 /* if we didn't find the specific one, then look for 750 * an unspecified one. 751 */ 752 if (sa == NULL) 753 sa = ndo->ndo_sa_default; 754 755 /* if not found fail */ 756 if (sa == NULL) 757 goto fail; 758 759 /* if we can't get nexthdr, we do not need to decrypt it */ 760 if (ep - bp2 < len) 761 goto fail; 762 if (ep - bp2 > len) { 763 /* FCS included at end of frame (NetBSD 1.6 or later) */ 764 ep = bp2 + len; 765 } 766 767 /* pointer to the IV, if there is one */ 768 ivoff = (const u_char *)(esp + 1) + 0; 769 /* length of the IV, if there is one; 0, if there isn't */ 770 ivlen = sa->ivlen; 771 secret = sa->secret; 772 ep = ep - sa->authlen; 773 774 if (sa->evp) { 775 ctx = EVP_CIPHER_CTX_new(); 776 if (ctx != NULL) { 777 if (set_cipher_parameters(ctx, sa->evp, secret, NULL, 0) < 0) 778 (*ndo->ndo_warning)(ndo, "espkey init failed"); 779 780 p = ivoff; 781 set_cipher_parameters(ctx, NULL, NULL, p, 0); 782 len = ep - (p + ivlen); 783 784 /* 785 * Allocate a buffer for the decrypted data. 786 * The output buffer must be separate from the 787 * input buffer, and its size must be a multiple 788 * of the cipher block size. 789 */ 790 block_size = (unsigned int)EVP_CIPHER_CTX_block_size(ctx); 791 output_buffer_size = len + (block_size - len % block_size); 792 output_buffer = (u_char *)malloc(output_buffer_size); 793 if (output_buffer == NULL) { 794 (*ndo->ndo_warning)(ndo, "can't allocate memory for decryption buffer"); 795 EVP_CIPHER_CTX_free(ctx); 796 return -1; 797 } 798 799 EVP_Cipher(ctx, output_buffer, p + ivlen, len); 800 EVP_CIPHER_CTX_free(ctx); 801 /* 802 * XXX - of course this is wrong, because buf is a 803 * const buffer, but changing this would require a 804 * more complicated fix. 805 */ 806 memcpy(__UNCONST(p + ivlen), output_buffer, len); 807 free(output_buffer); 808 advance = ivoff - (const u_char *)esp + ivlen; 809 } else 810 advance = sizeof(struct newesp); 811 } else 812 advance = sizeof(struct newesp); 813 814 /* sanity check for pad length */ 815 if (ep - bp < *(ep - 2)) 816 goto fail; 817 818 if (padlen) 819 *padlen = *(ep - 2) + 2; 820 821 if (nhdr) 822 *nhdr = *(ep - 1); 823 824 ND_PRINT((ndo, ": ")); 825 return advance; 826 #endif 827 828 fail: 829 return -1; 830 } 831 #ifdef HAVE_LIBCRYPTO 832 USES_APPLE_RST 833 #endif 834 835 /* 836 * Local Variables: 837 * c-style: whitesmith 838 * c-basic-offset: 8 839 * End: 840 */ 841