1 /* $OpenBSD: ip_esp.c,v 1.117 2012/06/29 14:48:04 mikeb Exp $ */ 2 /* 3 * The authors of this code are John Ioannidis (ji@tla.org), 4 * Angelos D. Keromytis (kermit@csd.uch.gr) and 5 * Niels Provos (provos@physnet.uni-hamburg.de). 6 * 7 * The original version of this code was written by John Ioannidis 8 * for BSD/OS in Athens, Greece, in November 1995. 9 * 10 * Ported to OpenBSD and NetBSD, with additional transforms, in December 1996, 11 * by Angelos D. Keromytis. 12 * 13 * Additional transforms and features in 1997 and 1998 by Angelos D. Keromytis 14 * and Niels Provos. 15 * 16 * Additional features in 1999 by Angelos D. Keromytis. 17 * 18 * Copyright (C) 1995, 1996, 1997, 1998, 1999 by John Ioannidis, 19 * Angelos D. Keromytis and Niels Provos. 20 * Copyright (c) 2001 Angelos D. Keromytis. 21 * 22 * Permission to use, copy, and modify this software with or without fee 23 * is hereby granted, provided that this entire notice is included in 24 * all copies of any software which is or includes a copy or 25 * modification of this software. 26 * You may use this code under the GNU public license if you so wish. Please 27 * contribute changes back to the authors under this freer than GPL license 28 * so that we may further the use of strong encryption without limitations to 29 * all. 30 * 31 * THIS SOFTWARE IS BEING PROVIDED "AS IS", WITHOUT ANY EXPRESS OR 32 * IMPLIED WARRANTY. IN PARTICULAR, NONE OF THE AUTHORS MAKES ANY 33 * REPRESENTATION OR WARRANTY OF ANY KIND CONCERNING THE 34 * MERCHANTABILITY OF THIS SOFTWARE OR ITS FITNESS FOR ANY PARTICULAR 35 * PURPOSE. 36 */ 37 38 #include "pfsync.h" 39 40 #include <sys/param.h> 41 #include <sys/systm.h> 42 #include <sys/mbuf.h> 43 #include <sys/socket.h> 44 45 #include <net/if.h> 46 #include <net/bpf.h> 47 48 #include <dev/rndvar.h> 49 50 #ifdef INET 51 #include <netinet/in.h> 52 #include <netinet/in_systm.h> 53 #include <netinet/ip.h> 54 #include <netinet/ip_var.h> 55 #endif /* INET */ 56 57 #ifdef INET6 58 #ifndef INET 59 #include <netinet/in.h> 60 #endif 61 #include <netinet/ip6.h> 62 #endif /* INET6 */ 63 64 #include <netinet/ip_ipsp.h> 65 #include <netinet/ip_esp.h> 66 #include <net/pfkeyv2.h> 67 #include <net/if_enc.h> 68 69 #if NPFSYNC > 0 70 #include <net/pfvar.h> 71 #include <net/if_pfsync.h> 72 #endif /* NPFSYNC > 0 */ 73 74 #include <crypto/cryptodev.h> 75 #include <crypto/xform.h> 76 77 #include "bpfilter.h" 78 79 #ifdef ENCDEBUG 80 #define DPRINTF(x) if (encdebug) printf x 81 #else 82 #define DPRINTF(x) 83 #endif 84 85 struct espstat espstat; 86 87 /* 88 * esp_attach() is called from the transformation initialization code. 89 */ 90 int 91 esp_attach() 92 { 93 return 0; 94 } 95 96 /* 97 * esp_init() is called when an SPI is being set up. 98 */ 99 int 100 esp_init(struct tdb *tdbp, struct xformsw *xsp, struct ipsecinit *ii) 101 { 102 struct enc_xform *txform = NULL; 103 struct auth_hash *thash = NULL; 104 struct cryptoini cria, crie, crin; 105 106 if (!ii->ii_encalg && !ii->ii_authalg) { 107 DPRINTF(("esp_init(): neither authentication nor encryption " 108 "algorithm given")); 109 return EINVAL; 110 } 111 112 if (ii->ii_encalg) { 113 switch (ii->ii_encalg) { 114 case SADB_EALG_NULL: 115 txform = &enc_xform_null; 116 break; 117 118 case SADB_EALG_DESCBC: 119 txform = &enc_xform_des; 120 break; 121 122 case SADB_EALG_3DESCBC: 123 txform = &enc_xform_3des; 124 break; 125 126 case SADB_X_EALG_AES: 127 txform = &enc_xform_rijndael128; 128 break; 129 130 case SADB_X_EALG_AESCTR: 131 txform = &enc_xform_aes_ctr; 132 break; 133 134 case SADB_X_EALG_AESGCM16: 135 txform = &enc_xform_aes_gcm; 136 break; 137 138 case SADB_X_EALG_AESGMAC: 139 txform = &enc_xform_aes_gmac; 140 break; 141 142 case SADB_X_EALG_BLF: 143 txform = &enc_xform_blf; 144 break; 145 146 case SADB_X_EALG_CAST: 147 txform = &enc_xform_cast5; 148 break; 149 150 default: 151 DPRINTF(("esp_init(): unsupported encryption algorithm %d specified\n", ii->ii_encalg)); 152 return EINVAL; 153 } 154 155 if (ii->ii_enckeylen < txform->minkey) { 156 DPRINTF(("esp_init(): keylength %d too small (min length is %d) for algorithm %s\n", ii->ii_enckeylen, txform->minkey, txform->name)); 157 return EINVAL; 158 } 159 160 if (ii->ii_enckeylen > txform->maxkey) { 161 DPRINTF(("esp_init(): keylength %d too large (max length is %d) for algorithm %s\n", ii->ii_enckeylen, txform->maxkey, txform->name)); 162 return EINVAL; 163 } 164 165 if (ii->ii_encalg == SADB_X_EALG_AESGCM16 || 166 ii->ii_encalg == SADB_X_EALG_AESGMAC) { 167 switch (ii->ii_enckeylen) { 168 case 20: 169 ii->ii_authalg = SADB_X_AALG_AES128GMAC; 170 break; 171 case 28: 172 ii->ii_authalg = SADB_X_AALG_AES192GMAC; 173 break; 174 case 36: 175 ii->ii_authalg = SADB_X_AALG_AES256GMAC; 176 break; 177 } 178 ii->ii_authkeylen = ii->ii_enckeylen; 179 ii->ii_authkey = ii->ii_enckey; 180 } 181 182 tdbp->tdb_encalgxform = txform; 183 184 DPRINTF(("esp_init(): initialized TDB with enc algorithm %s\n", 185 txform->name)); 186 187 tdbp->tdb_ivlen = txform->ivsize; 188 if (tdbp->tdb_flags & TDBF_HALFIV) 189 tdbp->tdb_ivlen /= 2; 190 } 191 192 if (ii->ii_authalg) { 193 switch (ii->ii_authalg) { 194 case SADB_AALG_MD5HMAC: 195 thash = &auth_hash_hmac_md5_96; 196 break; 197 198 case SADB_AALG_SHA1HMAC: 199 thash = &auth_hash_hmac_sha1_96; 200 break; 201 202 case SADB_X_AALG_RIPEMD160HMAC: 203 thash = &auth_hash_hmac_ripemd_160_96; 204 break; 205 206 case SADB_X_AALG_SHA2_256: 207 thash = &auth_hash_hmac_sha2_256_128; 208 break; 209 210 case SADB_X_AALG_SHA2_384: 211 thash = &auth_hash_hmac_sha2_384_192; 212 break; 213 214 case SADB_X_AALG_SHA2_512: 215 thash = &auth_hash_hmac_sha2_512_256; 216 break; 217 218 case SADB_X_AALG_AES128GMAC: 219 thash = &auth_hash_gmac_aes_128; 220 break; 221 222 case SADB_X_AALG_AES192GMAC: 223 thash = &auth_hash_gmac_aes_192; 224 break; 225 226 case SADB_X_AALG_AES256GMAC: 227 thash = &auth_hash_gmac_aes_256; 228 break; 229 230 default: 231 DPRINTF(("esp_init(): unsupported authentication algorithm %d specified\n", ii->ii_authalg)); 232 return EINVAL; 233 } 234 235 if (ii->ii_authkeylen != thash->keysize) { 236 DPRINTF(("esp_init(): keylength %d doesn't match algorithm %s keysize (%d)\n", ii->ii_authkeylen, thash->name, thash->keysize)); 237 return EINVAL; 238 } 239 240 tdbp->tdb_authalgxform = thash; 241 242 DPRINTF(("esp_init(): initialized TDB with hash algorithm %s\n", 243 thash->name)); 244 } 245 246 tdbp->tdb_xform = xsp; 247 tdbp->tdb_bitmap = 0; 248 tdbp->tdb_rpl = AH_HMAC_INITIAL_RPL; 249 250 /* Initialize crypto session */ 251 if (tdbp->tdb_encalgxform) { 252 /* Save the raw keys */ 253 tdbp->tdb_emxkeylen = ii->ii_enckeylen; 254 tdbp->tdb_emxkey = malloc(tdbp->tdb_emxkeylen, M_XDATA, 255 M_WAITOK); 256 bcopy(ii->ii_enckey, tdbp->tdb_emxkey, tdbp->tdb_emxkeylen); 257 258 bzero(&crie, sizeof(crie)); 259 260 crie.cri_alg = tdbp->tdb_encalgxform->type; 261 262 if (tdbp->tdb_authalgxform) 263 crie.cri_next = &cria; 264 else 265 crie.cri_next = NULL; 266 267 crie.cri_klen = ii->ii_enckeylen * 8; 268 crie.cri_key = ii->ii_enckey; 269 /* XXX Rounds ? */ 270 } 271 272 if (tdbp->tdb_authalgxform) { 273 /* Save the raw keys */ 274 tdbp->tdb_amxkeylen = ii->ii_authkeylen; 275 tdbp->tdb_amxkey = malloc(tdbp->tdb_amxkeylen, M_XDATA, 276 M_WAITOK); 277 bcopy(ii->ii_authkey, tdbp->tdb_amxkey, tdbp->tdb_amxkeylen); 278 279 bzero(&cria, sizeof(cria)); 280 281 cria.cri_alg = tdbp->tdb_authalgxform->type; 282 283 if ((tdbp->tdb_wnd > 0) && !(tdbp->tdb_flags & TDBF_NOREPLAY) && 284 (tdbp->tdb_flags & TDBF_ESN)) { 285 bzero(&crin, sizeof(crin)); 286 crin.cri_alg = CRYPTO_ESN; 287 cria.cri_next = &crin; 288 } 289 290 cria.cri_klen = ii->ii_authkeylen * 8; 291 cria.cri_key = ii->ii_authkey; 292 } 293 294 return crypto_newsession(&tdbp->tdb_cryptoid, 295 (tdbp->tdb_encalgxform ? &crie : &cria), 0); 296 } 297 298 /* 299 * Paranoia. 300 */ 301 int 302 esp_zeroize(struct tdb *tdbp) 303 { 304 int err; 305 306 if (tdbp->tdb_amxkey) { 307 explicit_bzero(tdbp->tdb_amxkey, tdbp->tdb_amxkeylen); 308 free(tdbp->tdb_amxkey, M_XDATA); 309 tdbp->tdb_amxkey = NULL; 310 } 311 312 if (tdbp->tdb_emxkey) { 313 explicit_bzero(tdbp->tdb_emxkey, tdbp->tdb_emxkeylen); 314 free(tdbp->tdb_emxkey, M_XDATA); 315 tdbp->tdb_emxkey = NULL; 316 } 317 318 err = crypto_freesession(tdbp->tdb_cryptoid); 319 tdbp->tdb_cryptoid = 0; 320 return err; 321 } 322 323 #define MAXBUFSIZ (AH_ALEN_MAX > ESP_MAX_IVS ? AH_ALEN_MAX : ESP_MAX_IVS) 324 325 /* 326 * ESP input processing, called (eventually) through the protocol switch. 327 */ 328 int 329 esp_input(struct mbuf *m, struct tdb *tdb, int skip, int protoff) 330 { 331 struct auth_hash *esph = (struct auth_hash *) tdb->tdb_authalgxform; 332 struct enc_xform *espx = (struct enc_xform *) tdb->tdb_encalgxform; 333 struct cryptodesc *crde = NULL, *crda = NULL; 334 struct cryptop *crp; 335 struct tdb_crypto *tc; 336 int plen, alen, hlen; 337 struct m_tag *mtag; 338 u_int32_t btsx, esn; 339 340 /* Determine the ESP header length */ 341 if (tdb->tdb_flags & TDBF_NOREPLAY) 342 hlen = sizeof(u_int32_t) + tdb->tdb_ivlen; /* "old" ESP */ 343 else 344 hlen = 2 * sizeof(u_int32_t) + tdb->tdb_ivlen; /* "new" ESP */ 345 346 alen = esph ? esph->authsize : 0; 347 plen = m->m_pkthdr.len - (skip + hlen + alen); 348 if (plen <= 0) { 349 DPRINTF(("esp_input: invalid payload length\n")); 350 espstat.esps_badilen++; 351 m_freem(m); 352 return EINVAL; 353 } 354 355 if (espx) { 356 /* 357 * Verify payload length is multiple of encryption algorithm 358 * block size. 359 */ 360 if (plen & (espx->blocksize - 1)) { 361 DPRINTF(("esp_input(): payload of %d octets not a multiple of %d octets, SA %s/%08x\n", plen, espx->blocksize, ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 362 espstat.esps_badilen++; 363 m_freem(m); 364 return EINVAL; 365 } 366 } 367 368 /* Replay window checking, if appropriate -- no value commitment. */ 369 if ((tdb->tdb_wnd > 0) && (!(tdb->tdb_flags & TDBF_NOREPLAY))) { 370 m_copydata(m, skip + sizeof(u_int32_t), sizeof(u_int32_t), 371 (unsigned char *) &btsx); 372 btsx = ntohl(btsx); 373 374 switch (checkreplaywindow(btsx, &tdb->tdb_rpl, tdb->tdb_wnd, 375 &tdb->tdb_bitmap, &esn, tdb->tdb_flags & TDBF_ESN, 0)) { 376 case 0: /* All's well */ 377 break; 378 379 case 1: 380 m_freem(m); 381 DPRINTF(("esp_input(): replay counter wrapped for SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 382 espstat.esps_wrap++; 383 return EACCES; 384 385 case 2: 386 case 3: 387 DPRINTF(("esp_input(): duplicate packet received in SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 388 m_freem(m); 389 espstat.esps_replay++; 390 return EACCES; 391 392 default: 393 m_freem(m); 394 DPRINTF(("esp_input(): bogus value from checkreplaywindow() in SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 395 return EACCES; 396 } 397 } 398 399 /* Update the counters */ 400 tdb->tdb_cur_bytes += m->m_pkthdr.len - skip - hlen - alen; 401 espstat.esps_ibytes += m->m_pkthdr.len - skip - hlen - alen; 402 403 /* Hard expiration */ 404 if ((tdb->tdb_flags & TDBF_BYTES) && 405 (tdb->tdb_cur_bytes >= tdb->tdb_exp_bytes)) { 406 pfkeyv2_expire(tdb, SADB_EXT_LIFETIME_HARD); 407 tdb_delete(tdb); 408 m_freem(m); 409 return ENXIO; 410 } 411 412 /* Notify on soft expiration */ 413 if ((tdb->tdb_flags & TDBF_SOFT_BYTES) && 414 (tdb->tdb_cur_bytes >= tdb->tdb_soft_bytes)) { 415 pfkeyv2_expire(tdb, SADB_EXT_LIFETIME_SOFT); 416 tdb->tdb_flags &= ~TDBF_SOFT_BYTES; /* Turn off checking */ 417 } 418 419 #ifdef notyet 420 /* Find out if we've already done crypto */ 421 for (mtag = m_tag_find(m, PACKET_TAG_IPSEC_IN_CRYPTO_DONE, NULL); 422 mtag != NULL; 423 mtag = m_tag_find(m, PACKET_TAG_IPSEC_IN_CRYPTO_DONE, mtag)) { 424 struct tdb_ident *tdbi; 425 426 tdbi = (struct tdb_ident *) (mtag + 1); 427 if (tdbi->proto == tdb->tdb_sproto && tdbi->spi == tdb->tdb_spi && 428 tdbi->rdomain == tdb->tdb_rdomain && !bcmp(&tdbi->dst, 429 &tdb->tdb_dst, sizeof(union sockaddr_union))) 430 break; 431 } 432 #else 433 mtag = NULL; 434 #endif 435 436 /* Get crypto descriptors */ 437 crp = crypto_getreq(esph && espx ? 2 : 1); 438 if (crp == NULL) { 439 m_freem(m); 440 DPRINTF(("esp_input(): failed to acquire crypto descriptors\n")); 441 espstat.esps_crypto++; 442 return ENOBUFS; 443 } 444 445 /* Get IPsec-specific opaque pointer */ 446 if (esph == NULL || mtag != NULL) 447 tc = malloc(sizeof(*tc), M_XDATA, M_NOWAIT | M_ZERO); 448 else 449 tc = malloc(sizeof(*tc) + alen, M_XDATA, M_NOWAIT | M_ZERO); 450 if (tc == NULL) { 451 m_freem(m); 452 crypto_freereq(crp); 453 DPRINTF(("esp_input(): failed to allocate tdb_crypto\n")); 454 espstat.esps_crypto++; 455 return ENOBUFS; 456 } 457 458 tc->tc_ptr = (caddr_t) mtag; 459 460 if (esph) { 461 crda = crp->crp_desc; 462 crde = crda->crd_next; 463 464 /* Authentication descriptor */ 465 crda->crd_skip = skip; 466 crda->crd_inject = m->m_pkthdr.len - alen; 467 468 crda->crd_alg = esph->type; 469 crda->crd_key = tdb->tdb_amxkey; 470 crda->crd_klen = tdb->tdb_amxkeylen * 8; 471 472 if ((tdb->tdb_wnd > 0) && !(tdb->tdb_flags & TDBF_NOREPLAY) && 473 (tdb->tdb_flags & TDBF_ESN)) { 474 esn = htonl(esn); 475 bcopy(&esn, crda->crd_esn, 4); 476 crda->crd_flags |= CRD_F_ESN; 477 } 478 479 if (espx && espx->type == CRYPTO_AES_GCM_16) 480 crda->crd_len = hlen - tdb->tdb_ivlen; 481 else 482 crda->crd_len = m->m_pkthdr.len - (skip + alen); 483 484 /* Copy the authenticator */ 485 if (mtag == NULL) 486 m_copydata(m, m->m_pkthdr.len - alen, alen, (caddr_t) (tc + 1)); 487 } else 488 crde = crp->crp_desc; 489 490 /* Crypto operation descriptor */ 491 crp->crp_ilen = m->m_pkthdr.len; /* Total input length */ 492 crp->crp_flags = CRYPTO_F_IMBUF; 493 crp->crp_buf = (caddr_t) m; 494 crp->crp_callback = (int (*) (struct cryptop *)) esp_input_cb; 495 crp->crp_sid = tdb->tdb_cryptoid; 496 crp->crp_opaque = (caddr_t) tc; 497 498 /* These are passed as-is to the callback */ 499 tc->tc_skip = skip; 500 tc->tc_protoff = protoff; 501 tc->tc_spi = tdb->tdb_spi; 502 tc->tc_proto = tdb->tdb_sproto; 503 tc->tc_rdomain = tdb->tdb_rdomain; 504 bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union)); 505 506 /* Decryption descriptor */ 507 if (espx) { 508 crde->crd_skip = skip + hlen; 509 crde->crd_inject = skip + hlen - tdb->tdb_ivlen; 510 511 if (tdb->tdb_flags & TDBF_HALFIV) { 512 /* Copy half-IV from packet */ 513 m_copydata(m, crde->crd_inject, tdb->tdb_ivlen, crde->crd_iv); 514 515 /* Cook IV */ 516 for (btsx = 0; btsx < tdb->tdb_ivlen; btsx++) 517 crde->crd_iv[tdb->tdb_ivlen + btsx] = ~crde->crd_iv[btsx]; 518 519 crde->crd_flags |= CRD_F_IV_EXPLICIT; 520 } 521 522 crde->crd_alg = espx->type; 523 crde->crd_key = tdb->tdb_emxkey; 524 crde->crd_klen = tdb->tdb_emxkeylen * 8; 525 /* XXX Rounds ? */ 526 527 if (crde->crd_alg == CRYPTO_AES_GMAC) 528 crde->crd_len = 0; 529 else 530 crde->crd_len = m->m_pkthdr.len - (skip + hlen + alen); 531 } 532 533 if (mtag == NULL) 534 return crypto_dispatch(crp); 535 else 536 return esp_input_cb(crp); 537 } 538 539 /* 540 * ESP input callback, called directly by the crypto driver. 541 */ 542 int 543 esp_input_cb(void *op) 544 { 545 u_int8_t lastthree[3], aalg[AH_HMAC_MAX_HASHLEN]; 546 int s, hlen, roff, skip, protoff, error; 547 struct mbuf *m1, *mo, *m; 548 struct auth_hash *esph; 549 struct tdb_crypto *tc; 550 struct cryptop *crp; 551 struct m_tag *mtag; 552 struct tdb *tdb; 553 u_int32_t btsx, esn; 554 caddr_t ptr; 555 556 crp = (struct cryptop *) op; 557 558 tc = (struct tdb_crypto *) crp->crp_opaque; 559 skip = tc->tc_skip; 560 protoff = tc->tc_protoff; 561 mtag = (struct m_tag *) tc->tc_ptr; 562 563 m = (struct mbuf *) crp->crp_buf; 564 if (m == NULL) { 565 /* Shouldn't happen... */ 566 free(tc, M_XDATA); 567 crypto_freereq(crp); 568 espstat.esps_crypto++; 569 DPRINTF(("esp_input_cb(): bogus returned buffer from crypto\n")); 570 return (EINVAL); 571 } 572 573 s = spltdb(); 574 575 tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto); 576 if (tdb == NULL) { 577 free(tc, M_XDATA); 578 espstat.esps_notdb++; 579 DPRINTF(("esp_input_cb(): TDB is expired while in crypto")); 580 error = EPERM; 581 goto baddone; 582 } 583 584 esph = (struct auth_hash *) tdb->tdb_authalgxform; 585 586 /* Check for crypto errors */ 587 if (crp->crp_etype) { 588 if (crp->crp_etype == EAGAIN) { 589 /* Reset the session ID */ 590 if (tdb->tdb_cryptoid != 0) 591 tdb->tdb_cryptoid = crp->crp_sid; 592 splx(s); 593 return crypto_dispatch(crp); 594 } 595 free(tc, M_XDATA); 596 espstat.esps_noxform++; 597 DPRINTF(("esp_input_cb(): crypto error %d\n", crp->crp_etype)); 598 error = crp->crp_etype; 599 goto baddone; 600 } 601 602 /* If authentication was performed, check now. */ 603 if (esph != NULL) { 604 /* 605 * If we have a tag, it means an IPsec-aware NIC did the verification 606 * for us. 607 */ 608 if (mtag == NULL) { 609 /* Copy the authenticator from the packet */ 610 m_copydata(m, m->m_pkthdr.len - esph->authsize, 611 esph->authsize, aalg); 612 613 ptr = (caddr_t) (tc + 1); 614 615 /* Verify authenticator */ 616 if (timingsafe_bcmp(ptr, aalg, esph->authsize)) { 617 free(tc, M_XDATA); 618 DPRINTF(("esp_input_cb(): authentication failed for packet in SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 619 espstat.esps_badauth++; 620 error = EACCES; 621 goto baddone; 622 } 623 } 624 625 /* Remove trailing authenticator */ 626 m_adj(m, -(esph->authsize)); 627 } 628 free(tc, M_XDATA); 629 630 /* Replay window checking, if appropriate */ 631 if ((tdb->tdb_wnd > 0) && (!(tdb->tdb_flags & TDBF_NOREPLAY))) { 632 m_copydata(m, skip + sizeof(u_int32_t), sizeof(u_int32_t), 633 (unsigned char *) &btsx); 634 btsx = ntohl(btsx); 635 636 switch (checkreplaywindow(btsx, &tdb->tdb_rpl, tdb->tdb_wnd, 637 &tdb->tdb_bitmap, &esn, tdb->tdb_flags & TDBF_ESN, 1)) { 638 case 0: /* All's well */ 639 #if NPFSYNC > 0 640 pfsync_update_tdb(tdb,0); 641 #endif 642 break; 643 644 case 1: 645 DPRINTF(("esp_input_cb(): replay counter wrapped for SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 646 espstat.esps_wrap++; 647 error = EACCES; 648 goto baddone; 649 650 case 2: 651 case 3: 652 DPRINTF(("esp_input_cb(): duplicate packet received in SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 653 espstat.esps_replay++; 654 error = EACCES; 655 goto baddone; 656 657 default: 658 DPRINTF(("esp_input_cb(): bogus value from checkreplaywindow() in SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 659 error = EACCES; 660 goto baddone; 661 } 662 } 663 664 /* Release the crypto descriptors */ 665 crypto_freereq(crp); 666 667 /* Determine the ESP header length */ 668 if (tdb->tdb_flags & TDBF_NOREPLAY) 669 hlen = sizeof(u_int32_t) + tdb->tdb_ivlen; /* "old" ESP */ 670 else 671 hlen = 2 * sizeof(u_int32_t) + tdb->tdb_ivlen; /* "new" ESP */ 672 673 /* Find beginning of ESP header */ 674 m1 = m_getptr(m, skip, &roff); 675 if (m1 == NULL) { 676 espstat.esps_hdrops++; 677 splx(s); 678 DPRINTF(("esp_input_cb(): bad mbuf chain, SA %s/%08x\n", 679 ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 680 m_freem(m); 681 return EINVAL; 682 } 683 684 /* Remove the ESP header and IV from the mbuf. */ 685 if (roff == 0) { 686 /* The ESP header was conveniently at the beginning of the mbuf */ 687 m_adj(m1, hlen); 688 if (!(m1->m_flags & M_PKTHDR)) 689 m->m_pkthdr.len -= hlen; 690 } else if (roff + hlen >= m1->m_len) { 691 /* 692 * Part or all of the ESP header is at the end of this mbuf, so 693 * first let's remove the remainder of the ESP header from the 694 * beginning of the remainder of the mbuf chain, if any. 695 */ 696 if (roff + hlen > m1->m_len) { 697 /* Adjust the next mbuf by the remainder */ 698 m_adj(m1->m_next, roff + hlen - m1->m_len); 699 700 /* The second mbuf is guaranteed not to have a pkthdr... */ 701 m->m_pkthdr.len -= (roff + hlen - m1->m_len); 702 } 703 704 /* Now, let's unlink the mbuf chain for a second...*/ 705 mo = m1->m_next; 706 m1->m_next = NULL; 707 708 /* ...and trim the end of the first part of the chain...sick */ 709 m_adj(m1, -(m1->m_len - roff)); 710 if (!(m1->m_flags & M_PKTHDR)) 711 m->m_pkthdr.len -= (m1->m_len - roff); 712 713 /* Finally, let's relink */ 714 m1->m_next = mo; 715 } else { 716 /* 717 * The ESP header lies in the "middle" of the mbuf...do an 718 * overlapping copy of the remainder of the mbuf over the ESP 719 * header. 720 */ 721 bcopy(mtod(m1, u_char *) + roff + hlen, 722 mtod(m1, u_char *) + roff, m1->m_len - (roff + hlen)); 723 m1->m_len -= hlen; 724 m->m_pkthdr.len -= hlen; 725 } 726 727 /* Save the last three bytes of decrypted data */ 728 m_copydata(m, m->m_pkthdr.len - 3, 3, lastthree); 729 730 /* Verify pad length */ 731 if (lastthree[1] + 2 > m->m_pkthdr.len - skip) { 732 espstat.esps_badilen++; 733 splx(s); 734 DPRINTF(("esp_input_cb(): invalid padding length %d for packet in SA %s/%08x\n", lastthree[1], ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 735 m_freem(m); 736 return EINVAL; 737 } 738 739 /* Verify correct decryption by checking the last padding bytes */ 740 if (!(tdb->tdb_flags & TDBF_RANDOMPADDING)) { 741 if ((lastthree[1] != lastthree[0]) && (lastthree[1] != 0)) { 742 espstat.esps_badenc++; 743 splx(s); 744 DPRINTF(("esp_input(): decryption failed for packet in SA %s/%08x\n", ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 745 m_freem(m); 746 return EINVAL; 747 } 748 } 749 750 /* Trim the mbuf chain to remove the trailing authenticator and padding */ 751 m_adj(m, -(lastthree[1] + 2)); 752 753 /* Restore the Next Protocol field */ 754 m_copyback(m, protoff, sizeof(u_int8_t), lastthree + 2, M_NOWAIT); 755 756 /* Back to generic IPsec input processing */ 757 error = ipsec_common_input_cb(m, tdb, skip, protoff, mtag); 758 splx(s); 759 return (error); 760 761 baddone: 762 splx(s); 763 764 if (m != NULL) 765 m_freem(m); 766 767 crypto_freereq(crp); 768 769 return (error); 770 } 771 772 /* 773 * ESP output routine, called by ipsp_process_packet(). 774 */ 775 int 776 esp_output(struct mbuf *m, struct tdb *tdb, struct mbuf **mp, int skip, 777 int protoff) 778 { 779 struct enc_xform *espx = (struct enc_xform *) tdb->tdb_encalgxform; 780 struct auth_hash *esph = (struct auth_hash *) tdb->tdb_authalgxform; 781 int ilen, hlen, rlen, padding, blks, alen; 782 struct mbuf *mi, *mo = (struct mbuf *) NULL; 783 struct tdb_crypto *tc; 784 unsigned char *pad; 785 u_int8_t prot; 786 787 struct cryptodesc *crde = NULL, *crda = NULL; 788 struct cryptop *crp; 789 #if NBPFILTER > 0 790 struct ifnet *encif; 791 792 if ((encif = enc_getif(tdb->tdb_rdomain, tdb->tdb_tap)) != NULL) { 793 encif->if_opackets++; 794 encif->if_obytes += m->m_pkthdr.len; 795 796 if (encif->if_bpf) { 797 struct enchdr hdr; 798 799 bzero (&hdr, sizeof(hdr)); 800 801 hdr.af = tdb->tdb_dst.sa.sa_family; 802 hdr.spi = tdb->tdb_spi; 803 if (espx) 804 hdr.flags |= M_CONF; 805 if (esph) 806 hdr.flags |= M_AUTH; 807 808 bpf_mtap_hdr(encif->if_bpf, (char *)&hdr, 809 ENC_HDRLEN, m, BPF_DIRECTION_OUT); 810 } 811 } 812 #endif 813 814 if (tdb->tdb_flags & TDBF_NOREPLAY) 815 hlen = sizeof(u_int32_t) + tdb->tdb_ivlen; 816 else 817 hlen = 2 * sizeof(u_int32_t) + tdb->tdb_ivlen; 818 819 rlen = m->m_pkthdr.len - skip; /* Raw payload length. */ 820 if (espx) 821 blks = MAX(espx->blocksize, 4); 822 else 823 blks = 4; /* If no encryption, we have to be 4-byte aligned. */ 824 825 padding = ((blks - ((rlen + 2) % blks)) % blks) + 2; 826 827 alen = esph ? esph->authsize : 0; 828 espstat.esps_output++; 829 830 switch (tdb->tdb_dst.sa.sa_family) { 831 #ifdef INET 832 case AF_INET: 833 /* Check for IP maximum packet size violations. */ 834 if (skip + hlen + rlen + padding + alen > IP_MAXPACKET) { 835 DPRINTF(("esp_output(): packet in SA %s/%08x got " 836 "too big\n", ipsp_address(tdb->tdb_dst), 837 ntohl(tdb->tdb_spi))); 838 m_freem(m); 839 espstat.esps_toobig++; 840 return EMSGSIZE; 841 } 842 break; 843 #endif /* INET */ 844 845 #ifdef INET6 846 case AF_INET6: 847 /* Check for IPv6 maximum packet size violations. */ 848 if (skip + hlen + rlen + padding + alen > IPV6_MAXPACKET) { 849 DPRINTF(("esp_output(): packet in SA %s/%08x got too " 850 "big\n", ipsp_address(tdb->tdb_dst), 851 ntohl(tdb->tdb_spi))); 852 m_freem(m); 853 espstat.esps_toobig++; 854 return EMSGSIZE; 855 } 856 break; 857 #endif /* INET6 */ 858 859 default: 860 DPRINTF(("esp_output(): unknown/unsupported protocol " 861 "family %d, SA %s/%08x\n", tdb->tdb_dst.sa.sa_family 862 , ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 863 m_freem(m); 864 espstat.esps_nopf++; 865 return EPFNOSUPPORT; 866 } 867 868 /* Update the counters. */ 869 tdb->tdb_cur_bytes += m->m_pkthdr.len - skip; 870 espstat.esps_obytes += m->m_pkthdr.len - skip; 871 872 /* Hard byte expiration. */ 873 if (tdb->tdb_flags & TDBF_BYTES && 874 tdb->tdb_cur_bytes >= tdb->tdb_exp_bytes) { 875 pfkeyv2_expire(tdb, SADB_EXT_LIFETIME_HARD); 876 tdb_delete(tdb); 877 m_freem(m); 878 return EINVAL; 879 } 880 881 /* Soft byte expiration. */ 882 if (tdb->tdb_flags & TDBF_SOFT_BYTES && 883 tdb->tdb_cur_bytes >= tdb->tdb_soft_bytes) { 884 pfkeyv2_expire(tdb, SADB_EXT_LIFETIME_SOFT); 885 tdb->tdb_flags &= ~TDBF_SOFT_BYTES; /* Turn off checking. */ 886 } 887 888 /* 889 * Loop through mbuf chain; if we find a readonly mbuf, 890 * replace the rest of the chain. 891 */ 892 mo = NULL; 893 mi = m; 894 while (mi != NULL && !M_READONLY(mi)) { 895 mo = mi; 896 mi = mi->m_next; 897 } 898 899 if (mi != NULL) { 900 /* Replace the rest of the mbuf chain. */ 901 struct mbuf *n = m_copym2(mi, 0, M_COPYALL, M_DONTWAIT); 902 903 if (n == NULL) { 904 DPRINTF(("esp_output(): bad mbuf chain, SA %s/%08x\n", 905 ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 906 espstat.esps_hdrops++; 907 m_freem(m); 908 return ENOBUFS; 909 } 910 911 if (mo != NULL) 912 mo->m_next = n; 913 else 914 m = n; 915 916 m_freem(mi); 917 } 918 919 /* Inject ESP header. */ 920 mo = m_inject(m, skip, hlen, M_DONTWAIT); 921 if (mo == NULL) { 922 DPRINTF(("esp_output(): failed to inject ESP header for " 923 "SA %s/%08x\n", ipsp_address(tdb->tdb_dst), 924 ntohl(tdb->tdb_spi))); 925 m_freem(m); 926 espstat.esps_hdrops++; 927 return ENOBUFS; 928 } 929 930 /* Initialize ESP header. */ 931 bcopy((caddr_t) &tdb->tdb_spi, mtod(mo, caddr_t), sizeof(u_int32_t)); 932 if (!(tdb->tdb_flags & TDBF_NOREPLAY)) { 933 u_int32_t replay; 934 tdb->tdb_rpl++; 935 replay = htonl((u_int32_t)tdb->tdb_rpl); 936 bcopy((caddr_t) &replay, mtod(mo, caddr_t) + sizeof(u_int32_t), 937 sizeof(u_int32_t)); 938 #if NPFSYNC > 0 939 pfsync_update_tdb(tdb,1); 940 #endif 941 } 942 943 /* 944 * Add padding -- better to do it ourselves than use the crypto engine, 945 * although if/when we support compression, we'd have to do that. 946 */ 947 mo = m_inject(m, m->m_pkthdr.len, padding + alen, M_DONTWAIT); 948 if (mo == NULL) { 949 DPRINTF(("esp_output(): m_inject failed for SA %s/%08x\n", 950 ipsp_address(tdb->tdb_dst), ntohl(tdb->tdb_spi))); 951 m_freem(m); 952 return ENOBUFS; 953 } 954 pad = mtod(mo, u_char *); 955 956 /* Self-describing or random padding ? */ 957 if (!(tdb->tdb_flags & TDBF_RANDOMPADDING)) 958 for (ilen = 0; ilen < padding - 2; ilen++) 959 pad[ilen] = ilen + 1; 960 else 961 arc4random_buf((void *) pad, padding - 2); 962 963 /* Fix padding length and Next Protocol in padding itself. */ 964 pad[padding - 2] = padding - 2; 965 m_copydata(m, protoff, sizeof(u_int8_t), pad + padding - 1); 966 967 /* Fix Next Protocol in IPv4/IPv6 header. */ 968 prot = IPPROTO_ESP; 969 m_copyback(m, protoff, sizeof(u_int8_t), &prot, M_NOWAIT); 970 971 /* Get crypto descriptors. */ 972 crp = crypto_getreq(esph && espx ? 2 : 1); 973 if (crp == NULL) { 974 m_freem(m); 975 DPRINTF(("esp_output(): failed to acquire crypto " 976 "descriptors\n")); 977 espstat.esps_crypto++; 978 return ENOBUFS; 979 } 980 981 if (espx) { 982 crde = crp->crp_desc; 983 crda = crde->crd_next; 984 985 /* Encryption descriptor. */ 986 crde->crd_skip = skip + hlen; 987 crde->crd_flags = CRD_F_ENCRYPT; 988 crde->crd_inject = skip + hlen - tdb->tdb_ivlen; 989 990 if (tdb->tdb_flags & TDBF_HALFIV) { 991 /* Copy half-iv in the packet. */ 992 m_copyback(m, crde->crd_inject, tdb->tdb_ivlen, 993 tdb->tdb_iv, M_NOWAIT); 994 995 /* Cook half-iv. */ 996 bcopy(tdb->tdb_iv, crde->crd_iv, tdb->tdb_ivlen); 997 for (ilen = 0; ilen < tdb->tdb_ivlen; ilen++) 998 crde->crd_iv[tdb->tdb_ivlen + ilen] = 999 ~crde->crd_iv[ilen]; 1000 1001 crde->crd_flags |= 1002 CRD_F_IV_PRESENT | CRD_F_IV_EXPLICIT; 1003 } 1004 1005 /* Encryption operation. */ 1006 crde->crd_alg = espx->type; 1007 crde->crd_key = tdb->tdb_emxkey; 1008 crde->crd_klen = tdb->tdb_emxkeylen * 8; 1009 /* XXX Rounds ? */ 1010 1011 if (crde->crd_alg == CRYPTO_AES_GMAC) 1012 crde->crd_len = 0; 1013 else 1014 crde->crd_len = m->m_pkthdr.len - (skip + hlen + alen); 1015 } else 1016 crda = crp->crp_desc; 1017 1018 /* IPsec-specific opaque crypto info. */ 1019 tc = malloc(sizeof(*tc), M_XDATA, M_NOWAIT | M_ZERO); 1020 if (tc == NULL) { 1021 m_freem(m); 1022 crypto_freereq(crp); 1023 DPRINTF(("esp_output(): failed to allocate tdb_crypto\n")); 1024 espstat.esps_crypto++; 1025 return ENOBUFS; 1026 } 1027 1028 tc->tc_spi = tdb->tdb_spi; 1029 tc->tc_proto = tdb->tdb_sproto; 1030 tc->tc_rdomain = tdb->tdb_rdomain; 1031 bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union)); 1032 1033 /* Crypto operation descriptor. */ 1034 crp->crp_ilen = m->m_pkthdr.len; /* Total input length. */ 1035 crp->crp_flags = CRYPTO_F_IMBUF; 1036 crp->crp_buf = (caddr_t) m; 1037 crp->crp_callback = (int (*) (struct cryptop *)) esp_output_cb; 1038 crp->crp_opaque = (caddr_t) tc; 1039 crp->crp_sid = tdb->tdb_cryptoid; 1040 1041 if (esph) { 1042 /* Authentication descriptor. */ 1043 crda->crd_skip = skip; 1044 crda->crd_inject = m->m_pkthdr.len - alen; 1045 1046 /* Authentication operation. */ 1047 crda->crd_alg = esph->type; 1048 crda->crd_key = tdb->tdb_amxkey; 1049 crda->crd_klen = tdb->tdb_amxkeylen * 8; 1050 1051 if ((tdb->tdb_wnd > 0) && !(tdb->tdb_flags & TDBF_NOREPLAY) && 1052 (tdb->tdb_flags & TDBF_ESN)) { 1053 u_int32_t esn; 1054 1055 esn = htonl((u_int32_t)(tdb->tdb_rpl >> 32)); 1056 bcopy(&esn, crda->crd_esn, 4); 1057 crda->crd_flags |= CRD_F_ESN; 1058 } 1059 1060 if (espx && espx->type == CRYPTO_AES_GCM_16) 1061 crda->crd_len = hlen - tdb->tdb_ivlen; 1062 else 1063 crda->crd_len = m->m_pkthdr.len - (skip + alen); 1064 } 1065 1066 if ((tdb->tdb_flags & TDBF_SKIPCRYPTO) == 0) 1067 return crypto_dispatch(crp); 1068 else 1069 return esp_output_cb(crp); 1070 } 1071 1072 /* 1073 * ESP output callback, called directly by the crypto driver. 1074 */ 1075 int 1076 esp_output_cb(void *op) 1077 { 1078 struct cryptop *crp = (struct cryptop *) op; 1079 struct tdb_crypto *tc; 1080 struct tdb *tdb; 1081 struct mbuf *m; 1082 int error, s; 1083 1084 tc = (struct tdb_crypto *) crp->crp_opaque; 1085 1086 m = (struct mbuf *) crp->crp_buf; 1087 if (m == NULL) { 1088 /* Shouldn't happen... */ 1089 free(tc, M_XDATA); 1090 crypto_freereq(crp); 1091 espstat.esps_crypto++; 1092 DPRINTF(("esp_output_cb(): bogus returned buffer from " 1093 "crypto\n")); 1094 return (EINVAL); 1095 } 1096 1097 1098 s = spltdb(); 1099 1100 tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto); 1101 if (tdb == NULL) { 1102 free(tc, M_XDATA); 1103 espstat.esps_notdb++; 1104 DPRINTF(("esp_output_cb(): TDB is expired while in crypto\n")); 1105 error = EPERM; 1106 goto baddone; 1107 } 1108 1109 /* Check for crypto errors. */ 1110 if (crp->crp_etype) { 1111 if (crp->crp_etype == EAGAIN) { 1112 /* Reset the session ID */ 1113 if (tdb->tdb_cryptoid != 0) 1114 tdb->tdb_cryptoid = crp->crp_sid; 1115 splx(s); 1116 return crypto_dispatch(crp); 1117 } 1118 free(tc, M_XDATA); 1119 espstat.esps_noxform++; 1120 DPRINTF(("esp_output_cb(): crypto error %d\n", 1121 crp->crp_etype)); 1122 error = crp->crp_etype; 1123 goto baddone; 1124 } 1125 free(tc, M_XDATA); 1126 1127 /* Release crypto descriptors. */ 1128 crypto_freereq(crp); 1129 1130 /* 1131 * If we're doing half-iv, keep a copy of the last few bytes of the 1132 * encrypted part, for use as the next IV. Note that HALF-IV is only 1133 * supposed to be used without authentication (the old ESP specs). 1134 */ 1135 if (tdb->tdb_flags & TDBF_HALFIV) 1136 m_copydata(m, m->m_pkthdr.len - tdb->tdb_ivlen, tdb->tdb_ivlen, 1137 tdb->tdb_iv); 1138 1139 /* Call the IPsec input callback. */ 1140 error = ipsp_process_done(m, tdb); 1141 splx(s); 1142 return error; 1143 1144 baddone: 1145 splx(s); 1146 1147 if (m != NULL) 1148 m_freem(m); 1149 1150 crypto_freereq(crp); 1151 1152 return error; 1153 } 1154 1155 static __inline int 1156 checkreplay(u_int64_t *bitmap, u_int32_t diff) 1157 { 1158 if (*bitmap & (1ULL << diff)) 1159 return (1); 1160 return (0); 1161 } 1162 1163 static __inline void 1164 setreplay(u_int64_t *bitmap, u_int32_t diff, u_int32_t window, int wupdate) 1165 { 1166 if (wupdate) { 1167 if (diff < window) 1168 *bitmap = ((*bitmap) << diff) | 1; 1169 else 1170 *bitmap = 1; 1171 } else 1172 *bitmap |= 1ULL << diff; 1173 } 1174 1175 /* 1176 * To prevent ESN desynchronization replay distance specifies maximum 1177 * valid difference between the received SN and the last authenticated 1178 * one. It's arbitrary chosen to be 1000 packets, meaning that only 1179 * up to 999 packets can be lost. 1180 */ 1181 #define REPLAY_DISTANCE (1000) 1182 1183 /* 1184 * return 0 on success 1185 * return 1 for counter == 0 1186 * return 2 for very old packet 1187 * return 3 for packet within current window but already received 1188 */ 1189 int 1190 checkreplaywindow(u_int32_t seq, u_int64_t *last, u_int32_t window, 1191 u_int64_t *bitmap, u_int32_t *seqhigh, int esn, int commit) 1192 { 1193 u_int32_t tl, th, wl; 1194 u_int32_t seqh, diff; 1195 1196 tl = (u_int32_t)*last; 1197 th = (u_int32_t)(*last >> 32); 1198 1199 /* Zero SN is not allowed */ 1200 if (seq == 0 && tl == 0 && th == 0) 1201 return (1); 1202 1203 /* Current replay window starts here */ 1204 wl = tl - window + 1; 1205 1206 /* 1207 * We keep the high part intact when: 1208 * 1) the SN is within [wl, 0xffffffff] and the whole window is 1209 * within one subspace; 1210 * 2) the SN is within [0, wl) and window spans two subspaces. 1211 */ 1212 if ((tl >= window - 1 && seq >= wl) || 1213 (tl < window - 1 && seq < wl)) { 1214 seqh = *seqhigh = th; 1215 if (seq > tl) { 1216 if (seq - tl >= REPLAY_DISTANCE) 1217 return (2); 1218 if (commit) { 1219 setreplay(bitmap, seq - tl, window, 1); 1220 *last = ((u_int64_t)seqh << 32) | seq; 1221 } 1222 } else { 1223 if (checkreplay(bitmap, tl - seq)) 1224 return (3); 1225 if (commit) 1226 setreplay(bitmap, tl - seq, window, 0); 1227 } 1228 return (0); 1229 } 1230 1231 /* Can't wrap if not doing ESN */ 1232 if (!esn) 1233 return (1); 1234 1235 /* 1236 * SN is within [wl, 0xffffffff] and wl is within 1237 * [0xffffffff-window, 0xffffffff]. This means we got a SN 1238 * which is within our replay window, but in the previous 1239 * subspace. 1240 */ 1241 if (tl < window - 1 && seq >= wl) { 1242 seqh = *seqhigh = th - 1; 1243 diff = (u_int32_t)((((u_int64_t)th << 32) | tl) - 1244 (((u_int64_t)seqh << 32) | seq)); 1245 if (checkreplay(bitmap, diff)) 1246 return (3); 1247 if (commit) 1248 setreplay(bitmap, diff, window, 0); 1249 return (0); 1250 } 1251 1252 /* 1253 * SN has wrapped and the last authenticated SN is in the old 1254 * subspace. 1255 */ 1256 1257 if (seq - tl >= REPLAY_DISTANCE) 1258 return (2); 1259 1260 seqh = *seqhigh = th + 1; 1261 if (seqh == 0) /* Don't let high bit to wrap */ 1262 return (1); 1263 if (commit) { 1264 diff = (u_int32_t)((((u_int64_t)seqh << 32) | seq) - 1265 (((u_int64_t)th << 32) | tl)); 1266 setreplay(bitmap, diff, window, 1); 1267 *last = ((u_int64_t)seqh << 32) | seq; 1268 } 1269 1270 return (0); 1271 } 1272