parse.y revision 1.108
1/* $OpenBSD: parse.y,v 1.108 2006/06/18 18:18:01 hshoexer Exp $ */ 2 3/* 4 * Copyright (c) 2002, 2003, 2004 Henning Brauer <henning@openbsd.org> 5 * Copyright (c) 2001 Markus Friedl. All rights reserved. 6 * Copyright (c) 2001 Daniel Hartmeier. All rights reserved. 7 * Copyright (c) 2001 Theo de Raadt. All rights reserved. 8 * Copyright (c) 2004, 2005 Hans-Joerg Hoexer <hshoexer@openbsd.org> 9 * 10 * Permission to use, copy, modify, and distribute this software for any 11 * purpose with or without fee is hereby granted, provided that the above 12 * copyright notice and this permission notice appear in all copies. 13 * 14 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 15 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 16 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 17 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 18 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 19 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 20 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 21 */ 22 23%{ 24#include <sys/types.h> 25#include <sys/ioctl.h> 26#include <sys/queue.h> 27#include <sys/socket.h> 28#include <sys/stat.h> 29#include <net/if.h> 30#include <netinet/in.h> 31#include <netinet/ip_ipsp.h> 32#include <arpa/inet.h> 33 34#include <ctype.h> 35#include <err.h> 36#include <errno.h> 37#include <fcntl.h> 38#include <ifaddrs.h> 39#include <limits.h> 40#include <netdb.h> 41#include <stdarg.h> 42#include <stdio.h> 43#include <string.h> 44#include <syslog.h> 45#include <unistd.h> 46#include <netdb.h> 47 48#include "ipsecctl.h" 49 50#define KEYSIZE_LIMIT 1024 51 52static struct ipsecctl *ipsec = NULL; 53static FILE *fin = NULL; 54static int lineno = 1; 55static int errors = 0; 56static int debug = 0; 57 58const struct ipsec_xf authxfs[] = { 59 { "unknown", AUTHXF_UNKNOWN, 0, 0 }, 60 { "none", AUTHXF_NONE, 0, 0 }, 61 { "hmac-md5", AUTHXF_HMAC_MD5, 16, 0 }, 62 { "hmac-ripemd160", AUTHXF_HMAC_RIPEMD160, 20, 0 }, 63 { "hmac-sha1", AUTHXF_HMAC_SHA1, 20, 0 }, 64 { "hmac-sha2-256", AUTHXF_HMAC_SHA2_256, 32, 0 }, 65 { "hmac-sha2-384", AUTHXF_HMAC_SHA2_384, 48, 0 }, 66 { "hmac-sha2-512", AUTHXF_HMAC_SHA2_512, 64, 0 }, 67 { NULL, 0, 0, 0 }, 68}; 69 70const struct ipsec_xf encxfs[] = { 71 { "unknown", ENCXF_UNKNOWN, 0, 0 }, 72 { "none", ENCXF_NONE, 0, 0 }, 73 { "3des-cbc", ENCXF_3DES_CBC, 24, 24 }, 74 { "des-cbc", ENCXF_DES_CBC, 8, 8 }, 75 { "aes", ENCXF_AES, 16, 32 }, 76 { "aesctr", ENCXF_AESCTR, 16+4, 32+4 }, 77 { "blowfish", ENCXF_BLOWFISH, 5, 56 }, 78 { "cast128", ENCXF_CAST128, 5, 16 }, 79 { "null", ENCXF_NULL, 0, 0 }, 80 { "skipjack", ENCXF_SKIPJACK, 10, 10 }, 81 { NULL, 0, 0, 0 }, 82}; 83 84const struct ipsec_xf compxfs[] = { 85 { "unknown", COMPXF_UNKNOWN, 0, 0 }, 86 { "deflate", COMPXF_DEFLATE, 0, 0 }, 87 { "lzs", COMPXF_LZS, 0, 0 }, 88 { NULL, 0, 0, 0 }, 89}; 90 91const struct ipsec_xf groupxfs[] = { 92 { "unknown", GROUPXF_UNKNOWN, 0, 0 }, 93 { "none", GROUPXF_NONE, 0, 0 }, 94 { "modp768", GROUPXF_768, 768, 0 }, 95 { "grp1", GROUPXF_768, 768, 0 }, 96 { "modp1024", GROUPXF_1024, 1024, 0 }, 97 { "grp2", GROUPXF_1024, 1024, 0 }, 98 { "modp1536", GROUPXF_1536, 1536, 0 }, 99 { "grp5", GROUPXF_1536, 1536, 0 }, 100 { "modp2048", GROUPXF_2048, 2048, 0 }, 101 { "grp14", GROUPXF_2048, 2048, 0 }, 102 { "modp3072", GROUPXF_3072, 3072, 0 }, 103 { "grp15", GROUPXF_3072, 3072, 0 }, 104 { "modp4096", GROUPXF_4096, 4096, 0 }, 105 { "grp16", GROUPXF_4096, 4096, 0 }, 106 { "modp6144", GROUPXF_6144, 6144, 0 }, 107 { "grp18", GROUPXF_6144, 6144, 0 }, 108 { "modp8192", GROUPXF_8192, 8192, 0 }, 109 { "grp18", GROUPXF_8192, 8192, 0 }, 110 { NULL, 0, 0, 0 }, 111}; 112 113int yyerror(const char *, ...); 114int yyparse(void); 115int kw_cmp(const void *, const void *); 116int lookup(char *); 117int lgetc(FILE *); 118int lungetc(int); 119int findeol(void); 120int yylex(void); 121 122TAILQ_HEAD(symhead, sym) symhead = TAILQ_HEAD_INITIALIZER(symhead); 123struct sym { 124 TAILQ_ENTRY(sym) entries; 125 int used; 126 int persist; 127 char *nam; 128 char *val; 129}; 130 131int symset(const char *, const char *, int); 132int cmdline_symset(char *); 133char *symget(const char *); 134int atoul(char *, u_long *); 135int atospi(char *, u_int32_t *); 136u_int8_t x2i(unsigned char *); 137struct ipsec_key *parsekey(unsigned char *, size_t); 138struct ipsec_key *parsekeyfile(char *); 139struct ipsec_addr_wrap *host(const char *); 140struct ipsec_addr_wrap *host_v6(const char *, int); 141struct ipsec_addr_wrap *host_v4(const char *, int); 142struct ipsec_addr_wrap *host_dns(const char *, int, int); 143struct ipsec_addr_wrap *host_if(const char *, int); 144void ifa_load(void); 145int ifa_exists(const char *); 146struct ipsec_addr_wrap *ifa_lookup(const char *ifa_name); 147struct ipsec_addr_wrap *ifa_grouplookup(const char *); 148void set_ipmask(struct ipsec_addr_wrap *, u_int8_t); 149const struct ipsec_xf *parse_xf(const char *, const struct ipsec_xf *); 150struct ipsec_life *parse_life(int); 151struct ipsec_transforms *copytransforms(const struct ipsec_transforms *); 152struct ipsec_life *copylife(const struct ipsec_life *); 153struct ipsec_auth *copyipsecauth(const struct ipsec_auth *); 154struct ike_auth *copyikeauth(const struct ike_auth *); 155struct ipsec_key *copykey(struct ipsec_key *); 156struct ipsec_addr_wrap *copyhost(const struct ipsec_addr_wrap *); 157struct ipsec_rule *copyrule(struct ipsec_rule *); 158int validate_sa(u_int32_t, u_int8_t, 159 struct ipsec_transforms *, struct ipsec_key *, 160 struct ipsec_key *, u_int8_t); 161struct ipsec_rule *create_sa(u_int8_t, u_int8_t, struct ipsec_hosts *, 162 u_int32_t, struct ipsec_transforms *, 163 struct ipsec_key *, struct ipsec_key *); 164struct ipsec_rule *reverse_sa(struct ipsec_rule *, u_int32_t, 165 struct ipsec_key *, struct ipsec_key *); 166struct ipsec_rule *create_sagroup(struct ipsec_addr_wrap *, u_int8_t, 167 u_int32_t, struct ipsec_addr_wrap *, u_int8_t, 168 u_int32_t); 169struct ipsec_rule *create_flow(u_int8_t, u_int8_t, struct ipsec_hosts *, 170 struct ipsec_hosts *, u_int8_t, char *, char *, 171 u_int8_t); 172int expand_rule(struct ipsec_rule *, u_int8_t, u_int32_t, 173 struct ipsec_key *, struct ipsec_key *, int); 174struct ipsec_rule *reverse_rule(struct ipsec_rule *); 175struct ipsec_rule *create_ike(u_int8_t, struct ipsec_hosts *, 176 struct ipsec_hosts *, struct ike_mode *, 177 struct ike_mode *, u_int8_t, u_int8_t, u_int8_t, 178 char *, char *, struct ike_auth *); 179int add_sagroup(struct ipsec_rule *); 180 181struct ipsec_transforms *ipsec_transforms; 182 183typedef struct { 184 union { 185 u_int32_t number; 186 u_int8_t ikemode; 187 u_int8_t dir; 188 u_int8_t satype; /* encapsulating prococol */ 189 u_int8_t proto; /* encapsulated protocol */ 190 u_int8_t tmode; 191 char *string; 192 u_int16_t port; 193 struct ipsec_hosts hosts; 194 struct ipsec_hosts peers; 195 struct ipsec_addr_wrap *singlehost; 196 struct ipsec_addr_wrap *host; 197 struct { 198 char *srcid; 199 char *dstid; 200 } ids; 201 char *id; 202 u_int8_t type; 203 struct ike_auth ikeauth; 204 struct { 205 u_int32_t spiout; 206 u_int32_t spiin; 207 } spis; 208 struct { 209 struct ipsec_key *keyout; 210 struct ipsec_key *keyin; 211 } authkeys; 212 struct { 213 struct ipsec_key *keyout; 214 struct ipsec_key *keyin; 215 } enckeys; 216 struct { 217 struct ipsec_key *keyout; 218 struct ipsec_key *keyin; 219 } keys; 220 struct ipsec_transforms *transforms; 221 struct ipsec_life *life; 222 struct ike_mode *mainmode; 223 struct ike_mode *quickmode; 224 } v; 225 int lineno; 226} YYSTYPE; 227 228%} 229 230%token FLOW FROM ESP AH IN PEER ON OUT TO SRCID DSTID RSA PSK TCPMD5 SPI 231%token AUTHKEY ENCKEY FILENAME AUTHXF ENCXF ERROR IKE MAIN QUICK PASSIVE 232%token ACTIVE ANY IPIP IPCOMP COMPXF TUNNEL TRANSPORT DYNAMIC LIFE 233%token TYPE DENY BYPASS LOCAL PROTO USE ACQUIRE REQUIRE DONTACQ GROUP PORT 234%token <v.string> STRING 235%type <v.string> string 236%type <v.dir> dir 237%type <v.satype> satype 238%type <v.proto> proto 239%type <v.tmode> tmode 240%type <v.number> number 241%type <v.hosts> hosts 242%type <v.port> port 243%type <v.peers> peers 244%type <v.singlehost> singlehost 245%type <v.host> host host_list 246%type <v.ids> ids 247%type <v.id> id 248%type <v.spis> spispec 249%type <v.authkeys> authkeyspec 250%type <v.enckeys> enckeyspec 251%type <v.keys> keyspec 252%type <v.transforms> transforms 253%type <v.ikemode> ikemode 254%type <v.ikeauth> ikeauth 255%type <v.type> type 256%type <v.life> life 257%type <v.mainmode> mainmode 258%type <v.quickmode> quickmode 259%% 260 261grammar : /* empty */ 262 | grammar '\n' 263 | grammar ikerule '\n' 264 | grammar flowrule '\n' 265 | grammar sarule '\n' 266 | grammar tcpmd5rule '\n' 267 | grammar varset '\n' 268 | grammar error '\n' { errors++; } 269 ; 270 271number : STRING { 272 unsigned long ulval; 273 274 if (atoul($1, &ulval) == -1) { 275 yyerror("%s is not a number", $1); 276 free($1); 277 YYERROR; 278 } 279 if (ulval > UINT_MAX) { 280 yyerror("0x%lx out of range", ulval); 281 free($1); 282 YYERROR; 283 } 284 $$ = (u_int32_t)ulval; 285 free($1); 286 } 287 ; 288 289comma : ',' 290 | /* empty */ 291 ; 292 293tcpmd5rule : TCPMD5 hosts spispec authkeyspec { 294 struct ipsec_rule *r; 295 296 r = create_sa(IPSEC_TCPMD5, IPSEC_TRANSPORT, &$2, 297 $3.spiout, NULL, $4.keyout, NULL); 298 if (r == NULL) 299 YYERROR; 300 r->nr = ipsec->rule_nr++; 301 302 if (expand_rule(r, 0, $3.spiin, $4.keyin, NULL, 0)) 303 errx(1, "tcpmd5rule: expand_rule"); 304 } 305 ; 306 307sarule : satype tmode hosts spispec transforms authkeyspec 308 enckeyspec { 309 struct ipsec_rule *r; 310 311 r = create_sa($1, $2, &$3, $4.spiout, $5, $6.keyout, 312 $7.keyout); 313 if (r == NULL) 314 YYERROR; 315 r->nr = ipsec->rule_nr++; 316 317 if (expand_rule(r, 0, $4.spiin, $6.keyin, $7.keyin, 1)) 318 errx(1, "sarule: expand_rule"); 319 } 320 ; 321 322flowrule : FLOW satype dir proto hosts peers ids type { 323 struct ipsec_rule *r; 324 325 r = create_flow($3, $4, &$5, &$6, $2, $7.srcid, 326 $7.dstid, $8); 327 if (r == NULL) 328 YYERROR; 329 330 if (expand_rule(r, $3, 0, NULL, NULL, 0)) 331 errx(1, "flowrule: expand_rule"); 332 } 333 ; 334 335ikerule : IKE ikemode satype tmode proto hosts peers mainmode quickmode 336 ids ikeauth { 337 struct ipsec_rule *r; 338 339 r = create_ike($5, &$6, &$7, $8, $9, $3, $4, $2, 340 $10.srcid, $10.dstid, &$11); 341 if (r == NULL) 342 YYERROR; 343 r->nr = ipsec->rule_nr++; 344 345 if (expand_rule(r, 0, 0, NULL, NULL, 0)) 346 errx(1, "ikerule: expand_rule"); 347 } 348 ; 349 350satype : /* empty */ { $$ = IPSEC_ESP; } 351 | ESP { $$ = IPSEC_ESP; } 352 | AH { $$ = IPSEC_AH; } 353 | IPCOMP { $$ = IPSEC_IPCOMP; } 354 | IPIP { $$ = IPSEC_IPIP; } 355 ; 356 357proto : /* empty */ { $$ = 0; } 358 | PROTO STRING { 359 struct protoent *p; 360 const char *errstr; 361 int proto; 362 363 if ((p = getprotobyname($2)) != NULL) { 364 $$ = p->p_proto; 365 } else { 366 errstr = NULL; 367 proto = strtonum($2, 0, 255, &errstr); 368 if (errstr) 369 errx(1, "unknown protocol: %s", $2); 370 $$ = proto; 371 } 372 373 } 374 ; 375 376tmode : /* empty */ { $$ = IPSEC_TUNNEL; } 377 | TUNNEL { $$ = IPSEC_TUNNEL; } 378 | TRANSPORT { $$ = IPSEC_TRANSPORT; } 379 ; 380 381dir : /* empty */ { $$ = IPSEC_INOUT; } 382 | IN { $$ = IPSEC_IN; } 383 | OUT { $$ = IPSEC_OUT; } 384 ; 385 386hosts : FROM host port TO host port { 387 $$.src = $2; 388 $$.sport = $3; 389 $$.dst = $5; 390 $$.dport = $6; 391 } 392 | TO host port FROM host port { 393 $$.src = $5; 394 $$.sport = $6; 395 $$.dst = $2; 396 $$.dport = $3; 397 } 398 ; 399 400port : /* empty */ { $$ = 0; } 401 | PORT STRING { 402 struct servent *s; 403 const char *errstr; 404 int port; 405 406 if ((s = getservbyname($2, "tcp")) != NULL || 407 (s = getservbyname($2, "udp")) != NULL) { 408 $$ = s->s_port; 409 } else { 410 errstr = NULL; 411 port = strtonum($2, 0, USHRT_MAX, &errstr); 412 if (errstr) { 413 yyerror("unknown port: %s", $2); 414 YYERROR; 415 } 416 $$ = htons(port); 417 } 418 } 419 ; 420 421peers : /* empty */ { 422 $$.dst = NULL; 423 $$.src = NULL; 424 } 425 | PEER singlehost LOCAL singlehost { 426 $$.dst = $2; 427 $$.src = $4; 428 } 429 | LOCAL singlehost PEER singlehost { 430 $$.dst = $4; 431 $$.src = $2; 432 } 433 | PEER singlehost { 434 $$.dst = $2; 435 $$.src = NULL; 436 } 437 | LOCAL singlehost { 438 $$.dst = NULL; 439 $$.src = $2; 440 } 441 ; 442 443singlehost : /* empty */ { $$ = NULL; } 444 | STRING { 445 if (($$ = host($1)) == NULL) { 446 free($1); 447 yyerror("could not parse host specification"); 448 YYERROR; 449 } 450 free($1); 451 } 452 ; 453 454host_list : host { $$ = $1; } 455 | host_list comma host { 456 if ($3 == NULL) 457 $$ = $1; 458 else if ($1 == NULL) 459 $$ = $3; 460 else { 461 $1->tail->next = $3; 462 $1->tail = $3->tail; 463 $$ = $1; 464 } 465 } 466 ; 467 468host : STRING { 469 if (($$ = host($1)) == NULL) { 470 free($1); 471 yyerror("could not parse host specification"); 472 YYERROR; 473 } 474 free($1); 475 } 476 | STRING '/' number { 477 char *buf; 478 479 if (asprintf(&buf, "%s/%u", $1, $3) == -1) 480 err(1, "host: asprintf"); 481 free($1); 482 if (($$ = host(buf)) == NULL) { 483 free(buf); 484 yyerror("could not parse host specification"); 485 YYERROR; 486 } 487 free(buf); 488 } 489 | ANY { 490 struct ipsec_addr_wrap *ipa; 491 492 ipa = calloc(1, sizeof(struct ipsec_addr_wrap)); 493 if (ipa == NULL) 494 err(1, "host: calloc"); 495 496 ipa->af = AF_INET; 497 ipa->netaddress = 1; 498 if ((ipa->name = strdup("0.0.0.0/0")) == NULL) 499 err(1, "host: strdup"); 500 501 ipa->next = calloc(1, sizeof(struct ipsec_addr_wrap)); 502 if (ipa->next == NULL) 503 err(1, "host: calloc"); 504 505 ipa->next->af = AF_INET6; 506 ipa->next->netaddress = 1; 507 if ((ipa->next->name = strdup("::/0")) == NULL) 508 err(1, "host: strdup"); 509 510 $$ = ipa; 511 } 512 | '{' host_list '}' { $$ = $2; } 513 ; 514 515ids : /* empty */ { 516 $$.srcid = NULL; 517 $$.dstid = NULL; 518 } 519 | SRCID id DSTID id { 520 $$.srcid = $2; 521 $$.dstid = $4; 522 } 523 | SRCID id { 524 $$.srcid = $2; 525 $$.dstid = NULL; 526 } 527 | DSTID id { 528 $$.srcid = NULL; 529 $$.dstid = $2; 530 } 531 ; 532 533type : /* empty */ { 534 $$ = TYPE_REQUIRE; 535 } 536 | TYPE USE { 537 $$ = TYPE_USE; 538 } 539 | TYPE ACQUIRE { 540 $$ = TYPE_ACQUIRE; 541 } 542 | TYPE REQUIRE { 543 $$ = TYPE_REQUIRE; 544 } 545 | TYPE DENY { 546 $$ = TYPE_DENY; 547 } 548 | TYPE BYPASS { 549 $$ = TYPE_BYPASS; 550 } 551 | TYPE DONTACQ { 552 $$ = TYPE_DONTACQ; 553 } 554 ; 555 556id : STRING { $$ = $1; } 557 ; 558 559spispec : SPI STRING { 560 u_int32_t spi; 561 char *p = strchr($2, ':'); 562 563 if (p != NULL) { 564 *p++ = 0; 565 566 if (atospi(p, &spi) == -1) { 567 yyerror("%s is not a valid spi", p); 568 free($2); 569 YYERROR; 570 } 571 $$.spiin = spi; 572 } else 573 $$.spiin = 0; 574 575 if (atospi($2, &spi) == -1) { 576 yyerror("%s is not a valid spi", $2); 577 free($2); 578 YYERROR; 579 } 580 $$.spiout = spi; 581 582 583 free($2); 584 } 585 ; 586 587transforms : { 588 if ((ipsec_transforms = calloc(1, 589 sizeof(struct ipsec_transforms))) == NULL) 590 err(1, "transforms: calloc"); 591 } 592 transforms_l 593 { $$ = ipsec_transforms; } 594 | /* empty */ { 595 if (($$ = calloc(1, 596 sizeof(struct ipsec_transforms))) == NULL) 597 err(1, "transforms: calloc"); 598 } 599 ; 600 601transforms_l : transforms_l transform 602 | transform 603 ; 604 605transform : AUTHXF STRING { 606 if (ipsec_transforms->authxf) 607 yyerror("auth already set"); 608 else { 609 ipsec_transforms->authxf = parse_xf($2, 610 authxfs); 611 if (!ipsec_transforms->authxf) 612 yyerror("%s not a valid transform", $2); 613 } 614 } 615 | ENCXF STRING { 616 if (ipsec_transforms->encxf) 617 yyerror("enc already set"); 618 else { 619 ipsec_transforms->encxf = parse_xf($2, encxfs); 620 if (!ipsec_transforms->encxf) 621 yyerror("%s not a valid transform", $2); 622 } 623 } 624 | COMPXF STRING { 625 if (ipsec_transforms->compxf) 626 yyerror("comp already set"); 627 else { 628 ipsec_transforms->compxf = parse_xf($2, 629 compxfs); 630 if (!ipsec_transforms->compxf) 631 yyerror("%s not a valid transform", $2); 632 } 633 } 634 | GROUP STRING { 635 if (ipsec_transforms->groupxf) 636 yyerror("group already set"); 637 else { 638 ipsec_transforms->groupxf = parse_xf($2, 639 groupxfs); 640 if (!ipsec_transforms->groupxf) 641 yyerror("%s not a valid transform", $2); 642 } 643 } 644 ; 645 646mainmode : /* empty */ { 647 struct ike_mode *mm; 648 649 /* We create just an empty mode */ 650 if ((mm = calloc(1, sizeof(struct ike_mode))) == NULL) 651 err(1, "mainmode: calloc"); 652 $$ = mm; 653 } 654 | MAIN transforms life { 655 struct ike_mode *mm; 656 657 if ((mm = calloc(1, sizeof(struct ike_mode))) == NULL) 658 err(1, "mainmode: calloc"); 659 mm->xfs = $2; 660 mm->life = $3; 661 $$ = mm; 662 } 663 ; 664 665quickmode : /* empty */ { 666 struct ike_mode *qm; 667 668 /* We create just an empty mode */ 669 if ((qm = calloc(1, sizeof(struct ike_mode))) == NULL) 670 err(1, "quickmode: calloc"); 671 $$ = qm; 672 } 673 | QUICK transforms life { 674 struct ike_mode *qm; 675 676 if ((qm = calloc(1, sizeof(struct ike_mode))) == NULL) 677 err(1, "quickmode: calloc"); 678 qm->xfs = $2; 679 qm->life = $3; 680 $$ = qm; 681 } 682 ; 683 684life : /* empty */ { 685 struct ipsec_life *life; 686 687 /* We create just an empty transform */ 688 if ((life = calloc(1, sizeof(struct ipsec_life))) 689 == NULL) 690 err(1, "life: calloc"); 691 life->lifetime = -1; 692 life->lifevolume = -1; 693 $$ = life; 694 } 695 | LIFE number { 696 struct ipsec_life *life; 697 698 life = parse_life($2); 699 if (life == NULL) 700 yyerror("%s not a valid lifetime", $2); 701 $$ = life; 702 } 703 ; 704 705authkeyspec : /* empty */ { 706 $$.keyout = NULL; 707 $$.keyin = NULL; 708 } 709 | AUTHKEY keyspec { 710 $$.keyout = $2.keyout; 711 $$.keyin = $2.keyin; 712 } 713 ; 714 715enckeyspec : /* empty */ { 716 $$.keyout = NULL; 717 $$.keyin = NULL; 718 } 719 | ENCKEY keyspec { 720 $$.keyout = $2.keyout; 721 $$.keyin = $2.keyin; 722 } 723 ; 724 725keyspec : STRING { 726 unsigned char *hex; 727 unsigned char *p = strchr($1, ':'); 728 729 if (p != NULL ) { 730 *p++ = 0; 731 732 if (!strncmp(p, "0x", 2)) 733 p += 2; 734 $$.keyin = parsekey(p, strlen(p)); 735 } else 736 $$.keyin = NULL; 737 738 hex = $1; 739 if (!strncmp(hex, "0x", 2)) 740 hex += 2; 741 $$.keyout = parsekey(hex, strlen(hex)); 742 743 free($1); 744 } 745 | FILENAME STRING { 746 unsigned char *p = strchr($2, ':'); 747 748 if (p != NULL) { 749 *p++ = 0; 750 $$.keyin = parsekeyfile(p); 751 } 752 $$.keyout = parsekeyfile($2); 753 free($2); 754 } 755 ; 756 757ikemode : /* empty */ { $$ = IKE_ACTIVE; } 758 | PASSIVE { $$ = IKE_PASSIVE; } 759 | DYNAMIC { $$ = IKE_DYNAMIC; } 760 | ACTIVE { $$ = IKE_ACTIVE; } 761 ; 762 763ikeauth : /* empty */ { 764 $$.type = IKE_AUTH_RSA; 765 $$.string = NULL; 766 } 767 | RSA { 768 $$.type = IKE_AUTH_RSA; 769 $$.string = NULL; 770 } 771 | PSK STRING { 772 $$.type = IKE_AUTH_PSK; 773 if (($$.string = strdup($2)) == NULL) 774 err(1, "ikeauth: strdup"); 775 } 776 ; 777 778string : string STRING 779 { 780 if (asprintf(&$$, "%s %s", $1, $2) == -1) 781 err(1, "string: asprintf"); 782 free($1); 783 free($2); 784 } 785 | STRING 786 ; 787 788varset : STRING '=' string 789 { 790 if (ipsec->opts & IPSECCTL_OPT_VERBOSE) 791 printf("%s = \"%s\"\n", $1, $3); 792 if (symset($1, $3, 0) == -1) 793 err(1, "cannot store variable"); 794 free($1); 795 free($3); 796 } 797 ; 798 799%% 800 801struct keywords { 802 const char *k_name; 803 int k_val; 804}; 805 806int 807yyerror(const char *fmt, ...) 808{ 809 va_list ap; 810 extern const char *infile; 811 812 errors = 1; 813 va_start(ap, fmt); 814 fprintf(stderr, "%s: %d: ", infile, yylval.lineno); 815 vfprintf(stderr, fmt, ap); 816 fprintf(stderr, "\n"); 817 va_end(ap); 818 return (0); 819} 820 821int 822kw_cmp(const void *k, const void *e) 823{ 824 return (strcmp(k, ((const struct keywords *)e)->k_name)); 825} 826 827int 828lookup(char *s) 829{ 830 /* this has to be sorted always */ 831 static const struct keywords keywords[] = { 832 { "acquire", ACQUIRE }, 833 { "active", ACTIVE }, 834 { "ah", AH }, 835 { "any", ANY }, 836 { "auth", AUTHXF }, 837 { "authkey", AUTHKEY }, 838 { "bypass", BYPASS }, 839 { "comp", COMPXF }, 840 { "deny", DENY }, 841 { "dontacq", DONTACQ }, 842 { "dstid", DSTID }, 843 { "dynamic", DYNAMIC }, 844 { "enc", ENCXF }, 845 { "enckey", ENCKEY }, 846 { "esp", ESP }, 847 { "file", FILENAME }, 848 { "flow", FLOW }, 849 { "from", FROM }, 850 { "group", GROUP }, 851 { "ike", IKE }, 852 { "in", IN }, 853 { "ipcomp", IPCOMP }, 854 { "ipip", IPIP }, 855 { "life", LIFE }, 856 { "local", LOCAL }, 857 { "main", MAIN }, 858 { "out", OUT }, 859 { "passive", PASSIVE }, 860 { "peer", PEER }, 861 { "port", PORT }, 862 { "proto", PROTO }, 863 { "psk", PSK }, 864 { "quick", QUICK }, 865 { "require", REQUIRE }, 866 { "rsa", RSA }, 867 { "spi", SPI }, 868 { "srcid", SRCID }, 869 { "tcpmd5", TCPMD5 }, 870 { "to", TO }, 871 { "transport", TRANSPORT }, 872 { "tunnel", TUNNEL }, 873 { "type", TYPE }, 874 { "use", USE } 875 }; 876 const struct keywords *p; 877 878 p = bsearch(s, keywords, sizeof(keywords)/sizeof(keywords[0]), 879 sizeof(keywords[0]), kw_cmp); 880 881 if (p) { 882 if (debug > 1) 883 fprintf(stderr, "%s: %d\n", s, p->k_val); 884 return (p->k_val); 885 } else { 886 if (debug > 1) 887 fprintf(stderr, "string: %s\n", s); 888 return (STRING); 889 } 890} 891 892#define MAXPUSHBACK 128 893 894char *parsebuf; 895int parseindex; 896char pushback_buffer[MAXPUSHBACK]; 897int pushback_index = 0; 898 899int 900lgetc(FILE *f) 901{ 902 int c, next; 903 904 if (parsebuf) { 905 /* Read character from the parsebuffer instead of input. */ 906 if (parseindex >= 0) { 907 c = parsebuf[parseindex++]; 908 if (c != '\0') 909 return (c); 910 parsebuf = NULL; 911 } else 912 parseindex++; 913 } 914 915 if (pushback_index) 916 return (pushback_buffer[--pushback_index]); 917 918 while ((c = getc(f)) == '\\') { 919 next = getc(f); 920 if (next != '\n') { 921 c = next; 922 break; 923 } 924 yylval.lineno = lineno; 925 lineno++; 926 } 927 if (c == '\t' || c == ' ') { 928 /* Compress blanks to a single space. */ 929 do { 930 c = getc(f); 931 } while (c == '\t' || c == ' '); 932 ungetc(c, f); 933 c = ' '; 934 } 935 936 return (c); 937} 938 939int 940lungetc(int c) 941{ 942 if (c == EOF) 943 return (EOF); 944 if (parsebuf) { 945 parseindex--; 946 if (parseindex >= 0) 947 return (c); 948 } 949 if (pushback_index < MAXPUSHBACK-1) 950 return (pushback_buffer[pushback_index++] = c); 951 else 952 return (EOF); 953} 954 955int 956findeol(void) 957{ 958 int c; 959 960 parsebuf = NULL; 961 pushback_index = 0; 962 963 /* skip to either EOF or the first real EOL */ 964 while (1) { 965 c = lgetc(fin); 966 if (c == '\n') { 967 lineno++; 968 break; 969 } 970 if (c == EOF) 971 break; 972 } 973 return (ERROR); 974} 975 976int 977yylex(void) 978{ 979 char buf[8096]; 980 char *p, *val; 981 int endc, c; 982 int token; 983 984top: 985 p = buf; 986 while ((c = lgetc(fin)) == ' ') 987 ; /* nothing */ 988 989 yylval.lineno = lineno; 990 if (c == '#') 991 while ((c = lgetc(fin)) != '\n' && c != EOF) 992 ; /* nothing */ 993 if (c == '$' && parsebuf == NULL) { 994 while (1) { 995 if ((c = lgetc(fin)) == EOF) 996 return (0); 997 998 if (p + 1 >= buf + sizeof(buf) - 1) { 999 yyerror("string too long"); 1000 return (findeol()); 1001 } 1002 if (isalnum(c) || c == '_') { 1003 *p++ = (char)c; 1004 continue; 1005 } 1006 *p = '\0'; 1007 lungetc(c); 1008 break; 1009 } 1010 val = symget(buf); 1011 if (val == NULL) { 1012 yyerror("macro \"%s\" not defined", buf); 1013 return (findeol()); 1014 } 1015 parsebuf = val; 1016 parseindex = 0; 1017 goto top; 1018 } 1019 1020 switch (c) { 1021 case '\'': 1022 case '"': 1023 endc = c; 1024 while (1) { 1025 if ((c = lgetc(fin)) == EOF) 1026 return (0); 1027 if (c == endc) { 1028 *p = '\0'; 1029 break; 1030 } 1031 if (c == '\n') { 1032 lineno++; 1033 continue; 1034 } 1035 if (p + 1 >= buf + sizeof(buf) - 1) { 1036 yyerror("string too long"); 1037 return (findeol()); 1038 } 1039 *p++ = (char)c; 1040 } 1041 yylval.v.string = strdup(buf); 1042 if (yylval.v.string == NULL) 1043 err(1, "yylex: strdup"); 1044 return (STRING); 1045 } 1046 1047#define allowed_in_string(x) \ 1048 (isalnum(x) || (ispunct(x) && x != '(' && x != ')' && \ 1049 x != '{' && x != '}' && x != '<' && x != '>' && \ 1050 x != '!' && x != '=' && x != '/' && x != '#' && \ 1051 x != ',')) 1052 1053 if (isalnum(c) || c == ':' || c == '_' || c == '*') { 1054 do { 1055 *p++ = c; 1056 if ((unsigned)(p-buf) >= sizeof(buf)) { 1057 yyerror("string too long"); 1058 return (findeol()); 1059 } 1060 } while ((c = lgetc(fin)) != EOF && (allowed_in_string(c))); 1061 lungetc(c); 1062 *p = '\0'; 1063 if ((token = lookup(buf)) == STRING) 1064 if ((yylval.v.string = strdup(buf)) == NULL) 1065 err(1, "yylex: strdup"); 1066 return (token); 1067 } 1068 if (c == '\n') { 1069 yylval.lineno = lineno; 1070 lineno++; 1071 } 1072 if (c == EOF) 1073 return (0); 1074 return (c); 1075} 1076 1077int 1078parse_rules(FILE *input, struct ipsecctl *ipsecx) 1079{ 1080 struct sym *sym; 1081 1082 ipsec = ipsecx; 1083 fin = input; 1084 lineno = 1; 1085 errors = 0; 1086 1087 yyparse(); 1088 1089 /* Free macros and check which have not been used. */ 1090 while ((sym = TAILQ_FIRST(&symhead))) { 1091 if ((ipsec->opts & IPSECCTL_OPT_VERBOSE2) && !sym->used) 1092 fprintf(stderr, "warning: macro '%s' not " 1093 "used\n", sym->nam); 1094 TAILQ_REMOVE(&symhead, sym, entries); 1095 free(sym->nam); 1096 free(sym->val); 1097 free(sym); 1098 } 1099 1100 return (errors ? -1 : 0); 1101} 1102 1103int 1104symset(const char *nam, const char *val, int persist) 1105{ 1106 struct sym *sym; 1107 1108 for (sym = TAILQ_FIRST(&symhead); sym && strcmp(nam, sym->nam); 1109 sym = TAILQ_NEXT(sym, entries)) 1110 ; /* nothing */ 1111 1112 if (sym != NULL) { 1113 if (sym->persist == 1) 1114 return (0); 1115 else { 1116 TAILQ_REMOVE(&symhead, sym, entries); 1117 free(sym->nam); 1118 free(sym->val); 1119 free(sym); 1120 } 1121 } 1122 if ((sym = calloc(1, sizeof(*sym))) == NULL) 1123 return (-1); 1124 1125 sym->nam = strdup(nam); 1126 if (sym->nam == NULL) { 1127 free(sym); 1128 return (-1); 1129 } 1130 sym->val = strdup(val); 1131 if (sym->val == NULL) { 1132 free(sym->nam); 1133 free(sym); 1134 return (-1); 1135 } 1136 sym->used = 0; 1137 sym->persist = persist; 1138 TAILQ_INSERT_TAIL(&symhead, sym, entries); 1139 return (0); 1140} 1141 1142int 1143cmdline_symset(char *s) 1144{ 1145 char *sym, *val; 1146 int ret; 1147 size_t len; 1148 1149 if ((val = strrchr(s, '=')) == NULL) 1150 return (-1); 1151 1152 len = strlen(s) - strlen(val) + 1; 1153 if ((sym = malloc(len)) == NULL) 1154 err(1, "cmdline_symset: malloc"); 1155 1156 strlcpy(sym, s, len); 1157 1158 ret = symset(sym, val + 1, 1); 1159 free(sym); 1160 1161 return (ret); 1162} 1163 1164char * 1165symget(const char *nam) 1166{ 1167 struct sym *sym; 1168 1169 TAILQ_FOREACH(sym, &symhead, entries) 1170 if (strcmp(nam, sym->nam) == 0) { 1171 sym->used = 1; 1172 return (sym->val); 1173 } 1174 return (NULL); 1175} 1176 1177int 1178atoul(char *s, u_long *ulvalp) 1179{ 1180 u_long ulval; 1181 char *ep; 1182 1183 errno = 0; 1184 ulval = strtoul(s, &ep, 0); 1185 if (s[0] == '\0' || *ep != '\0') 1186 return (-1); 1187 if (errno == ERANGE && ulval == ULONG_MAX) 1188 return (-1); 1189 *ulvalp = ulval; 1190 return (0); 1191} 1192 1193int 1194atospi(char *s, u_int32_t *spivalp) 1195{ 1196 unsigned long ulval; 1197 1198 if (atoul(s, &ulval) == -1) 1199 return (-1); 1200 if (ulval >= SPI_RESERVED_MIN && ulval <= SPI_RESERVED_MAX) { 1201 yyerror("illegal SPI value"); 1202 return (-1); 1203 } 1204 *spivalp = ulval; 1205 return (0); 1206} 1207 1208u_int8_t 1209x2i(unsigned char *s) 1210{ 1211 char ss[3]; 1212 1213 ss[0] = s[0]; 1214 ss[1] = s[1]; 1215 ss[2] = 0; 1216 1217 if (!isxdigit(s[0]) || !isxdigit(s[1])) { 1218 yyerror("keys need to be specified in hex digits"); 1219 return (-1); 1220 } 1221 return ((u_int8_t)strtoul(ss, NULL, 16)); 1222} 1223 1224struct ipsec_key * 1225parsekey(unsigned char *hexkey, size_t len) 1226{ 1227 struct ipsec_key *key; 1228 int i; 1229 1230 key = calloc(1, sizeof(struct ipsec_key)); 1231 if (key == NULL) 1232 err(1, "parsekey: calloc"); 1233 1234 key->len = len / 2; 1235 key->data = calloc(key->len, sizeof(u_int8_t)); 1236 if (key->data == NULL) 1237 err(1, "parsekey: calloc"); 1238 1239 for (i = 0; i < (int)key->len; i++) 1240 key->data[i] = x2i(hexkey + 2 * i); 1241 1242 return (key); 1243} 1244 1245struct ipsec_key * 1246parsekeyfile(char *filename) 1247{ 1248 struct stat sb; 1249 int fd; 1250 unsigned char *hex; 1251 1252 if ((fd = open(filename, O_RDONLY)) < 0) 1253 err(1, "open %s", filename); 1254 if (fstat(fd, &sb) < 0) 1255 err(1, "parsekeyfile: stat %s", filename); 1256 if ((sb.st_size > KEYSIZE_LIMIT) || (sb.st_size == 0)) 1257 errx(1, "%s: key too %s", filename, sb.st_size ? "large" : 1258 "small"); 1259 if ((hex = calloc(sb.st_size, sizeof(unsigned char))) == NULL) 1260 err(1, "parsekeyfile: calloc"); 1261 if (read(fd, hex, sb.st_size) < sb.st_size) 1262 err(1, "parsekeyfile: read"); 1263 close(fd); 1264 return (parsekey(hex, sb.st_size)); 1265} 1266 1267struct ipsec_addr_wrap * 1268host(const char *s) 1269{ 1270 struct ipsec_addr_wrap *ipa = NULL; 1271 int mask, v4mask, cont = 1; 1272 char *p, *q, *ps; 1273 1274 if ((p = strrchr(s, '/')) != NULL) { 1275 errno = 0; 1276 mask = strtol(p + 1, &q, 0); 1277 if (errno == ERANGE || !q || *q || mask > 128 || q == (p + 1)) 1278 errx(1, "host: invalid netmask '%s'", p); 1279 if ((ps = malloc(strlen(s) - strlen(p) + 1)) == NULL) 1280 err(1, "host: calloc"); 1281 strlcpy(ps, s, strlen(s) - strlen(p) + 1); 1282 v4mask = mask; 1283 } else { 1284 if ((ps = strdup(s)) == NULL) 1285 err(1, "host: strdup"); 1286 v4mask = 32; 1287 mask = -1; 1288 } 1289 1290 /* Does interface with this name exist? */ 1291 if (cont && (ipa = host_if(ps, mask)) != NULL) 1292 cont = 0; 1293 1294 /* IPv4 address? */ 1295 if (cont && (ipa = host_v4(s, v4mask)) != NULL) 1296 cont = 0; 1297 1298 /* IPv6 address? */ 1299 if (cont && (ipa = host_v6(ps, mask == -1 ? 128 : mask)) != NULL) 1300 cont = 0; 1301 1302 /* dns lookup */ 1303 if (cont && (ipa = host_dns(s, v4mask, 0)) != NULL) 1304 cont = 0; 1305 free(ps); 1306 1307 if (ipa == NULL || cont == 1) { 1308 fprintf(stderr, "no IP address found for %s\n", s); 1309 return (NULL); 1310 } 1311 return (ipa); 1312} 1313 1314struct ipsec_addr_wrap * 1315host_v6(const char *s, int prefixlen) 1316{ 1317 struct ipsec_addr_wrap *ipa = NULL; 1318 struct addrinfo hints, *res0, *res; 1319 char hbuf[NI_MAXHOST]; 1320 1321 bzero(&hints, sizeof(struct addrinfo)); 1322 hints.ai_family = PF_UNSPEC; 1323 hints.ai_socktype = SOCK_STREAM; 1324 hints.ai_flags = AI_NUMERICHOST; 1325 if (getaddrinfo(s, NULL, &hints, &res0)) 1326 return (NULL); 1327 1328 for (res = res0; res; res = res->ai_next) { 1329 if (res->ai_family != AF_INET6) 1330 continue; 1331 break; /* found one */ 1332 } 1333 ipa = calloc(1, sizeof(struct ipsec_addr_wrap)); 1334 if (ipa == NULL) 1335 err(1, "host_addr: calloc"); 1336 ipa->af = res->ai_family; 1337 memcpy(&ipa->address.v6, 1338 &((struct sockaddr_in6 *)res->ai_addr)->sin6_addr.s6_addr, 1339 sizeof(struct in6_addr)); 1340 if (prefixlen > 128) 1341 prefixlen = 128; 1342 ipa->next = NULL; 1343 ipa->tail = ipa; 1344 1345 set_ipmask(ipa, prefixlen); 1346 if (getnameinfo(res->ai_addr, res->ai_addrlen, 1347 hbuf, sizeof(hbuf), NULL, 0, NI_NUMERICHOST)) { 1348 errx(1, "could not get a numeric hostname"); 1349 } 1350 1351 if (prefixlen != 128) { 1352 ipa->netaddress = 1; 1353 asprintf(&ipa->name, "%s/%d", hbuf, prefixlen); 1354 } else 1355 ipa->name = strdup(hbuf); 1356 if (ipa->name == NULL) 1357 err(1, "host_dns: strdup"); 1358 1359 freeaddrinfo(res0); 1360 1361 return (ipa); 1362} 1363 1364struct ipsec_addr_wrap * 1365host_v4(const char *s, int mask) 1366{ 1367 struct ipsec_addr_wrap *ipa = NULL; 1368 struct in_addr ina; 1369 int bits = 32; 1370 1371 bzero(&ina, sizeof(struct in_addr)); 1372 if (strrchr(s, '/') != NULL) { 1373 if ((bits = inet_net_pton(AF_INET, s, &ina, sizeof(ina))) == -1) 1374 return (NULL); 1375 } else { 1376 if (inet_pton(AF_INET, s, &ina) != 1) 1377 return (NULL); 1378 } 1379 1380 ipa = calloc(1, sizeof(struct ipsec_addr_wrap)); 1381 if (ipa == NULL) 1382 err(1, "host_v4: calloc"); 1383 1384 ipa->address.v4 = ina; 1385 ipa->name = strdup(s); 1386 if (ipa->name == NULL) 1387 err(1, "host_v4: strdup"); 1388 ipa->af = AF_INET; 1389 ipa->next = NULL; 1390 ipa->tail = ipa; 1391 1392 set_ipmask(ipa, bits); 1393 if (bits != (ipa->af == AF_INET ? 32 : 128)) 1394 ipa->netaddress = 1; 1395 1396 return (ipa); 1397} 1398 1399struct ipsec_addr_wrap * 1400host_dns(const char *s, int v4mask, int v6mask) 1401{ 1402 struct ipsec_addr_wrap *ipa = NULL; 1403 struct addrinfo hints, *res0, *res; 1404 int error; 1405 int bits = 32; 1406 1407 bzero(&hints, sizeof(struct addrinfo)); 1408 hints.ai_family = PF_UNSPEC; 1409 hints.ai_socktype = SOCK_STREAM; 1410 error = getaddrinfo(s, NULL, &hints, &res0); 1411 if (error) 1412 return (NULL); 1413 1414 for (res = res0; res; res = res->ai_next) { 1415 if (res->ai_family != AF_INET) 1416 continue; 1417 ipa = calloc(1, sizeof(struct ipsec_addr_wrap)); 1418 if (ipa == NULL) 1419 err(1, "host_dns: calloc"); 1420 memcpy(&ipa->address.v4, 1421 &((struct sockaddr_in *)res->ai_addr)->sin_addr.s_addr, 1422 sizeof(struct in_addr)); 1423 ipa->name = strdup(inet_ntoa(ipa->address.v4)); 1424 if (ipa->name == NULL) 1425 err(1, "host_dns: strdup"); 1426 ipa->af = AF_INET; 1427 ipa->next = NULL; 1428 ipa->tail = ipa; 1429 1430 set_ipmask(ipa, bits); 1431 if (bits != (ipa->af == AF_INET ? 32 : 128)) 1432 ipa->netaddress = 1; 1433 break; 1434 } 1435 freeaddrinfo(res0); 1436 1437 return (ipa); 1438} 1439 1440struct ipsec_addr_wrap * 1441host_if(const char *s, int mask) 1442{ 1443 struct ipsec_addr_wrap *ipa = NULL; 1444 1445 if (ifa_exists(s)) 1446 ipa = ifa_lookup(s); 1447 1448 return (ipa); 1449} 1450 1451/* interface lookup routintes */ 1452 1453struct ipsec_addr_wrap *iftab; 1454 1455void 1456ifa_load(void) 1457{ 1458 struct ifaddrs *ifap, *ifa; 1459 struct ipsec_addr_wrap *n = NULL, *h = NULL; 1460 1461 if (getifaddrs(&ifap) < 0) 1462 err(1, "ifa_load: getiffaddrs"); 1463 1464 for (ifa = ifap; ifa; ifa = ifa->ifa_next) { 1465 if (!(ifa->ifa_addr->sa_family == AF_INET || 1466 ifa->ifa_addr->sa_family == AF_INET6 || 1467 ifa->ifa_addr->sa_family == AF_LINK)) 1468 continue; 1469 n = calloc(1, sizeof(struct ipsec_addr_wrap)); 1470 if (n == NULL) 1471 err(1, "ifa_load: calloc"); 1472 n->af = ifa->ifa_addr->sa_family; 1473 if ((n->name = strdup(ifa->ifa_name)) == NULL) 1474 err(1, "ifa_load: strdup"); 1475 if (n->af == AF_INET) { 1476 n->af = AF_INET; 1477 memcpy(&n->address.v4, &((struct sockaddr_in *) 1478 ifa->ifa_addr)->sin_addr.s_addr, 1479 sizeof(struct in_addr)); 1480 memcpy(&n->mask.v4, &((struct sockaddr_in *) 1481 ifa->ifa_netmask)->sin_addr.s_addr, 1482 sizeof(struct in_addr)); 1483 } else if (n->af == AF_INET6) { 1484 n->af = AF_INET6; 1485 memcpy(&n->address.v6, &((struct sockaddr_in6 *) 1486 ifa->ifa_addr)->sin6_addr.s6_addr, 1487 sizeof(struct in6_addr)); 1488 memcpy(&n->mask.v6, &((struct sockaddr_in6 *) 1489 ifa->ifa_netmask)->sin6_addr.s6_addr, 1490 sizeof(struct in6_addr)); 1491 } 1492 if ((n->name = strdup(ifa->ifa_name)) == NULL) 1493 err(1, "ifa_load: strdup"); 1494 n->next = NULL; 1495 n->tail = n; 1496 if (h == NULL) 1497 h = n; 1498 else { 1499 h->tail->next = n; 1500 h->tail = n; 1501 } 1502 } 1503 1504 iftab = h; 1505 freeifaddrs(ifap); 1506} 1507 1508int 1509ifa_exists(const char *ifa_name) 1510{ 1511 struct ipsec_addr_wrap *n; 1512 struct ifgroupreq ifgr; 1513 int s; 1514 1515 if (iftab == NULL) 1516 ifa_load(); 1517 1518 /* check wether this is a group */ 1519 if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == -1) 1520 err(1, "ifa_exists: socket"); 1521 bzero(&ifgr, sizeof(ifgr)); 1522 strlcpy(ifgr.ifgr_name, ifa_name, sizeof(ifgr.ifgr_name)); 1523 if (ioctl(s, SIOCGIFGMEMB, (caddr_t)&ifgr) == 0) { 1524 close(s); 1525 return (1); 1526 } 1527 close(s); 1528 1529 for (n = iftab; n; n = n->next) { 1530 if (n->af == AF_LINK && !strncmp(n->name, ifa_name, 1531 IFNAMSIZ)) 1532 return (1); 1533 } 1534 1535 return (0); 1536} 1537 1538struct ipsec_addr_wrap * 1539ifa_grouplookup(const char *ifa_name) 1540{ 1541 struct ifg_req *ifg; 1542 struct ifgroupreq ifgr; 1543 int s; 1544 size_t len; 1545 struct ipsec_addr_wrap *n, *h = NULL, *hn; 1546 1547 if ((s = socket(AF_INET, SOCK_DGRAM, 0)) == -1) 1548 err(1, "socket"); 1549 bzero(&ifgr, sizeof(ifgr)); 1550 strlcpy(ifgr.ifgr_name, ifa_name, sizeof(ifgr.ifgr_name)); 1551 if (ioctl(s, SIOCGIFGMEMB, (caddr_t)&ifgr) == -1) { 1552 close(s); 1553 return (NULL); 1554 } 1555 1556 len = ifgr.ifgr_len; 1557 if ((ifgr.ifgr_groups = calloc(1, len)) == NULL) 1558 err(1, "calloc"); 1559 if (ioctl(s, SIOCGIFGMEMB, (caddr_t)&ifgr) == -1) 1560 err(1, "ioctl"); 1561 1562 for (ifg = ifgr.ifgr_groups; ifg && len >= sizeof(struct ifg_req); 1563 ifg++) { 1564 len -= sizeof(struct ifg_req); 1565 if ((n = ifa_lookup(ifg->ifgrq_member)) == NULL) 1566 continue; 1567 if (h == NULL) 1568 h = n; 1569 else { 1570 for (hn = h; hn->next != NULL; hn = hn->next) 1571 ; /* nothing */ 1572 hn->next = n; 1573 n->tail = hn; 1574 } 1575 } 1576 free(ifgr.ifgr_groups); 1577 close(s); 1578 1579 return (h); 1580} 1581 1582struct ipsec_addr_wrap * 1583ifa_lookup(const char *ifa_name) 1584{ 1585 struct ipsec_addr_wrap *p = NULL, *h = NULL, *n = NULL; 1586 1587 if (iftab == NULL) 1588 ifa_load(); 1589 1590 if ((n = ifa_grouplookup(ifa_name)) != NULL) 1591 return (n); 1592 1593 for (p = iftab; p; p = p->next) { 1594 if (p->af != AF_INET && p->af != AF_INET6) 1595 continue; 1596 if (strncmp(p->name, ifa_name, IFNAMSIZ)) 1597 continue; 1598 n = calloc(1, sizeof(struct ipsec_addr_wrap)); 1599 if (n == NULL) 1600 err(1, "ifa_lookup: calloc"); 1601 memcpy(n, p, sizeof(struct ipsec_addr_wrap)); 1602 if ((n->name = strdup(p->name)) == NULL) 1603 err(1, "ifa_lookup: strdup"); 1604 switch (n->af) { 1605 case AF_INET: 1606 set_ipmask(n, 32); 1607 break; 1608 case AF_INET6: 1609 /* route/show.c and bgpd/util.c give KAME credit */ 1610 if (IN6_IS_ADDR_LINKLOCAL(&n->address.v6) || 1611 IN6_IS_ADDR_MC_LINKLOCAL(&n->address.v6)) { 1612 u_int16_t tmp16; 1613 /* for now we can not handle link local, 1614 * therefore bail for now 1615 */ 1616 free(n); 1617 continue; 1618 1619 memcpy(&tmp16, &n->address.v6.s6_addr[2], 1620 sizeof(tmp16)); 1621 /* use this when we support link-local 1622 * n->??.scopeid = ntohs(tmp16); 1623 */ 1624 n->address.v6.s6_addr[2] = 0; 1625 n->address.v6.s6_addr[3] = 0; 1626 } 1627 set_ipmask(n, 128); 1628 break; 1629 } 1630 1631 n->next = NULL; 1632 n->tail = n; 1633 if (h == NULL) 1634 h = n; 1635 else { 1636 h->tail->next = n; 1637 h->tail = n; 1638 } 1639 } 1640 1641 return (h); 1642} 1643 1644void 1645set_ipmask(struct ipsec_addr_wrap *address, u_int8_t b) 1646{ 1647 struct ipsec_addr *ipa; 1648 int i, j = 0; 1649 1650 ipa = &address->mask; 1651 bzero(ipa, sizeof(struct ipsec_addr)); 1652 1653 while (b >= 32) { 1654 ipa->addr32[j++] = 0xffffffff; 1655 b -= 32; 1656 } 1657 for (i = 31; i > 31 - b; --i) 1658 ipa->addr32[j] |= (1 << i); 1659 if (b) 1660 ipa->addr32[j] = htonl(ipa->addr32[j]); 1661} 1662 1663const struct ipsec_xf * 1664parse_xf(const char *name, const struct ipsec_xf xfs[]) 1665{ 1666 int i; 1667 1668 for (i = 0; xfs[i].name != NULL; i++) { 1669 if (strncmp(name, xfs[i].name, strlen(name))) 1670 continue; 1671 return &xfs[i]; 1672 } 1673 return (NULL); 1674} 1675 1676struct ipsec_life * 1677parse_life(int value) 1678{ 1679 struct ipsec_life *life; 1680 1681 life = calloc(1, sizeof(struct ipsec_life)); 1682 if (life == NULL) 1683 err(1, "calloc"); 1684 1685 life->lifetime = value; 1686 1687 return (life); 1688} 1689 1690struct ipsec_transforms * 1691copytransforms(const struct ipsec_transforms *xfs) 1692{ 1693 struct ipsec_transforms *newxfs; 1694 1695 if (xfs == NULL) 1696 return (NULL); 1697 1698 newxfs = calloc(1, sizeof(struct ipsec_transforms)); 1699 if (newxfs == NULL) 1700 err(1, "copytransforms: calloc"); 1701 1702 memcpy(newxfs, xfs, sizeof(struct ipsec_transforms)); 1703 return (newxfs); 1704} 1705 1706struct ipsec_life * 1707copylife(const struct ipsec_life *life) 1708{ 1709 struct ipsec_life *newlife; 1710 1711 if (life == NULL) 1712 return (NULL); 1713 1714 newlife = calloc(1, sizeof(struct ipsec_life)); 1715 if (newlife == NULL) 1716 err(1, "copylife: calloc"); 1717 1718 memcpy(newlife, life, sizeof(struct ipsec_life)); 1719 return (newlife); 1720} 1721 1722struct ipsec_auth * 1723copyipsecauth(const struct ipsec_auth *auth) 1724{ 1725 struct ipsec_auth *newauth; 1726 1727 if (auth == NULL) 1728 return (NULL); 1729 1730 if ((newauth = calloc(1, sizeof(struct ipsec_auth))) == NULL) 1731 err(1, "calloc"); 1732 if (auth->srcid && 1733 asprintf(&newauth->srcid, "%s", auth->srcid) == -1) 1734 err(1, "asprintf"); 1735 if (auth->dstid && 1736 asprintf(&newauth->dstid, "%s", auth->dstid) == -1) 1737 err(1, "asprintf"); 1738 1739 newauth->idtype = auth->idtype; 1740 newauth->type = auth->type; 1741 1742 return (newauth); 1743} 1744 1745struct ike_auth * 1746copyikeauth(const struct ike_auth *auth) 1747{ 1748 struct ike_auth *newauth; 1749 1750 if (auth == NULL) 1751 return (NULL); 1752 1753 if ((newauth = calloc(1, sizeof(struct ike_auth))) == NULL) 1754 err(1, "calloc"); 1755 if (auth->string && 1756 asprintf(&newauth->string, "%s", auth->string) == -1) 1757 err(1, "asprintf"); 1758 1759 newauth->type = auth->type; 1760 1761 return (newauth); 1762} 1763 1764struct ipsec_key * 1765copykey(struct ipsec_key *key) 1766{ 1767 struct ipsec_key *newkey; 1768 1769 if (key == NULL) 1770 return (NULL); 1771 1772 if ((newkey = calloc(1, sizeof(struct ipsec_key))) == NULL) 1773 err(1, "calloc"); 1774 if ((newkey->data = calloc(key->len, sizeof(u_int8_t))) == NULL) 1775 err(1, "calloc"); 1776 memcpy(newkey->data, key->data, key->len); 1777 newkey->len = key->len; 1778 1779 return (newkey); 1780} 1781 1782struct ipsec_addr_wrap * 1783copyhost(const struct ipsec_addr_wrap *src) 1784{ 1785 struct ipsec_addr_wrap *dst; 1786 1787 if (src == NULL) 1788 return (NULL); 1789 1790 dst = calloc(1, sizeof(struct ipsec_addr_wrap)); 1791 if (dst == NULL) 1792 err(1, "copyhost: calloc"); 1793 1794 memcpy(dst, src, sizeof(struct ipsec_addr_wrap)); 1795 1796 if ((dst->name = strdup(src->name)) == NULL) 1797 err(1, "copyhost: strdup"); 1798 1799 return dst; 1800} 1801 1802struct ipsec_rule * 1803copyrule(struct ipsec_rule *rule) 1804{ 1805 struct ipsec_rule *r; 1806 1807 if ((r = calloc(1, sizeof(struct ipsec_rule))) == NULL) 1808 err(1, "calloc"); 1809 1810 r->src = copyhost(rule->src); 1811 r->dst = copyhost(rule->dst); 1812 r->local = copyhost(rule->local); 1813 r->peer = copyhost(rule->peer); 1814 r->auth = copyipsecauth(rule->auth); 1815 r->ikeauth = copyikeauth(rule->ikeauth); 1816 r->xfs = copytransforms(rule->xfs); 1817 r->mmxfs = copytransforms(rule->mmxfs); 1818 r->qmxfs = copytransforms(rule->qmxfs); 1819 r->mmlife = copylife(rule->mmlife); 1820 r->qmlife = copylife(rule->qmlife); 1821 r->authkey = copykey(rule->authkey); 1822 r->enckey = copykey(rule->enckey); 1823 1824 r->type = rule->type; 1825 r->satype = rule->satype; 1826 r->proto = rule->proto; 1827 r->tmode = rule->tmode; 1828 r->direction = rule->direction; 1829 r->flowtype = rule->flowtype; 1830 r->sport = rule->sport; 1831 r->dport = rule->dport; 1832 r->ikemode = rule->ikemode; 1833 r->spi = rule->spi; 1834 r->nr = rule->nr; 1835 1836 return (r); 1837} 1838 1839int 1840validate_sa(u_int32_t spi, u_int8_t satype, struct ipsec_transforms *xfs, 1841 struct ipsec_key *authkey, struct ipsec_key *enckey, u_int8_t tmode) 1842{ 1843 /* Sanity checks */ 1844 if (spi == 0) { 1845 yyerror("no SPI specified"); 1846 return (0); 1847 } 1848 if (satype == IPSEC_AH) { 1849 if (!xfs) { 1850 yyerror("no transforms specified"); 1851 return (0); 1852 } 1853 if (!xfs->authxf) 1854 xfs->authxf = &authxfs[AUTHXF_HMAC_SHA2_256]; 1855 if (xfs->encxf) { 1856 yyerror("ah does not provide encryption"); 1857 return (0); 1858 } 1859 if (xfs->compxf) { 1860 yyerror("ah does not provide compression"); 1861 return (0); 1862 } 1863 } 1864 if (satype == IPSEC_ESP) { 1865 if (!xfs) { 1866 yyerror("no transforms specified"); 1867 return (0); 1868 } 1869 if (xfs->compxf) { 1870 yyerror("esp does not provide compression"); 1871 return (0); 1872 } 1873 if (!xfs->authxf) 1874 xfs->authxf = &authxfs[AUTHXF_HMAC_SHA2_256]; 1875 if (!xfs->encxf) 1876 xfs->encxf = &encxfs[ENCXF_AES]; 1877 } 1878 if (satype == IPSEC_IPCOMP) { 1879 if (!xfs) { 1880 yyerror("no transform specified"); 1881 return (0); 1882 } 1883 if (xfs->authxf || xfs->encxf) { 1884 yyerror("no encryption or authentication with ipcomp"); 1885 return (0); 1886 } 1887 if (!xfs->compxf) 1888 xfs->compxf = &compxfs[COMPXF_DEFLATE]; 1889 } 1890 if (satype == IPSEC_IPIP) { 1891 if (!xfs) { 1892 yyerror("no transform specified"); 1893 return (0); 1894 } 1895 if (xfs->authxf || xfs->encxf || xfs->compxf) { 1896 yyerror("no encryption, authentication or compression" 1897 " with ipip"); 1898 return (0); 1899 } 1900 } 1901 if (satype == IPSEC_TCPMD5 && authkey == NULL && tmode != 1902 IPSEC_TRANSPORT) { 1903 yyerror("authentication key needed for tcpmd5"); 1904 return (0); 1905 } 1906 if (xfs && xfs->authxf) { 1907 if (!authkey) { 1908 yyerror("no authentication key specified"); 1909 return (0); 1910 } 1911 if (authkey->len != xfs->authxf->keymin) { 1912 yyerror("wrong authentication key length, needs to be " 1913 "%d bits", xfs->authxf->keymin * 8); 1914 return (0); 1915 } 1916 } 1917 if (xfs && xfs->encxf) { 1918 if (!enckey && xfs->encxf != &encxfs[ENCXF_NULL]) { 1919 yyerror("no encryption key specified"); 1920 return (0); 1921 } 1922 if (enckey) { 1923 if (enckey->len < xfs->encxf->keymin) { 1924 yyerror("encryption key too short (%d bits), " 1925 "minimum %d bits", enckey->len * 8, 1926 xfs->encxf->keymin * 8); 1927 return (0); 1928 } 1929 if (xfs->encxf->keymax < enckey->len) { 1930 yyerror("encryption key too long (%d bits), " 1931 "maximum %d bits", enckey->len * 8, 1932 xfs->encxf->keymax * 8); 1933 return (0); 1934 } 1935 } 1936 } 1937 1938 return 1; 1939} 1940 1941int 1942add_sagroup(struct ipsec_rule *r) 1943{ 1944 struct ipsec_rule *rp, *last, *group; 1945 int found = 0; 1946 1947 TAILQ_FOREACH(rp, &ipsec->group_queue, group_entry) { 1948 if (strcmp(rp->dst->name, r->dst->name) == 0) { 1949 found = 1; 1950 break; 1951 } 1952 } 1953 if (found) { 1954 last = TAILQ_LAST(&rp->dst_group_queue, dst_group_queue); 1955 TAILQ_INSERT_TAIL(&rp->dst_group_queue, r, dst_group_entry); 1956 1957 group = create_sagroup(last->dst, last->satype, last->spi, 1958 r->dst, r->satype, r->spi); 1959 if (group == NULL) 1960 return (1); 1961 group->nr = ipsec->rule_nr++; 1962 if (ipsecctl_add_rule(ipsec, group)) 1963 return (1); 1964 } else { 1965 TAILQ_INSERT_TAIL(&ipsec->group_queue, r, group_entry); 1966 TAILQ_INIT(&r->dst_group_queue); 1967 TAILQ_INSERT_TAIL(&r->dst_group_queue, r, dst_group_entry); 1968 } 1969 1970 return (0); 1971} 1972 1973struct ipsec_rule * 1974create_sa(u_int8_t satype, u_int8_t tmode, struct ipsec_hosts *hosts, 1975 u_int32_t spi, struct ipsec_transforms *xfs, struct ipsec_key *authkey, 1976 struct ipsec_key *enckey) 1977{ 1978 struct ipsec_rule *r; 1979 1980 if (validate_sa(spi, satype, xfs, authkey, enckey, tmode) == 0) 1981 return (NULL); 1982 1983 r = calloc(1, sizeof(struct ipsec_rule)); 1984 if (r == NULL) 1985 err(1, "create_sa: calloc"); 1986 1987 r->type |= RULE_SA; 1988 r->satype = satype; 1989 r->tmode = tmode; 1990 r->src = hosts->src; 1991 r->dst = hosts->dst; 1992 r->spi = spi; 1993 r->xfs = xfs; 1994 r->authkey = authkey; 1995 r->enckey = enckey; 1996 1997 return r; 1998} 1999 2000struct ipsec_rule * 2001reverse_sa(struct ipsec_rule *rule, u_int32_t spi, struct ipsec_key *authkey, 2002 struct ipsec_key *enckey) 2003{ 2004 struct ipsec_rule *reverse; 2005 2006 if (validate_sa(spi, rule->satype, rule->xfs, authkey, enckey, 2007 rule->tmode) == 0) 2008 return (NULL); 2009 2010 reverse = calloc(1, sizeof(struct ipsec_rule)); 2011 if (reverse == NULL) 2012 err(1, "reverse_sa: calloc"); 2013 2014 reverse->type |= RULE_SA; 2015 reverse->satype = rule->satype; 2016 reverse->tmode = rule->tmode; 2017 reverse->src = copyhost(rule->dst); 2018 reverse->dst = copyhost(rule->src); 2019 reverse->spi = spi; 2020 reverse->xfs = copytransforms(rule->xfs); 2021 reverse->authkey = authkey; 2022 reverse->enckey = enckey; 2023 2024 return (reverse); 2025} 2026 2027struct ipsec_rule * 2028create_sagroup(struct ipsec_addr_wrap *dst, u_int8_t proto, u_int32_t spi, 2029 struct ipsec_addr_wrap *dst2, u_int8_t proto2, u_int32_t spi2) 2030{ 2031 struct ipsec_rule *r; 2032 2033 r = calloc(1, sizeof(struct ipsec_rule)); 2034 if (r == NULL) 2035 err(1, "create_sagroup: calloc"); 2036 2037 r->type |= RULE_GROUP; 2038 2039 r->dst = copyhost(dst); 2040 r->dst2 = copyhost(dst2); 2041 r->proto = proto; 2042 r->proto2 = proto2; 2043 r->spi = spi; 2044 r->spi2 = spi2; 2045 r->satype = proto; 2046 2047 return (r); 2048} 2049 2050struct ipsec_rule * 2051create_flow(u_int8_t dir, u_int8_t proto, struct ipsec_hosts *hosts, 2052 struct ipsec_hosts *peers, 2053 u_int8_t satype, char *srcid, char *dstid, u_int8_t type) 2054{ 2055 struct ipsec_rule *r; 2056 2057 r = calloc(1, sizeof(struct ipsec_rule)); 2058 if (r == NULL) 2059 err(1, "create_flow: calloc"); 2060 2061 r->type |= RULE_FLOW; 2062 2063 if (dir == IPSEC_INOUT) 2064 r->direction = IPSEC_OUT; 2065 else 2066 r->direction = dir; 2067 2068 r->satype = satype; 2069 r->proto = proto; 2070 r->src = hosts->src; 2071 r->sport = hosts->sport; 2072 r->dst = hosts->dst; 2073 r->dport = hosts->dport; 2074 if ((hosts->sport != 0 || hosts->dport != 0) && 2075 (proto != IPPROTO_TCP && proto != IPPROTO_UDP)) { 2076 yyerror("no protocol supplied with source/destination ports"); 2077 goto errout; 2078 } 2079 2080 if (type == TYPE_DENY || type == TYPE_BYPASS) { 2081 r->flowtype = type; 2082 return (r); 2083 } 2084 2085 r->flowtype = type; 2086 r->local = peers->src; 2087 if (peers->dst == NULL) { 2088 /* Set peer to remote host. Must be a host address. */ 2089 if (r->direction == IPSEC_IN) { 2090 if (r->src->netaddress) { 2091 yyerror("no peer specified"); 2092 goto errout; 2093 } 2094 r->peer = copyhost(r->src); 2095 } else { 2096 if (r->dst->netaddress) { 2097 yyerror("no peer specified"); 2098 goto errout; 2099 } 2100 r->peer = copyhost(r->dst); 2101 } 2102 } else 2103 r->peer = peers->dst; 2104 2105 r->auth = calloc(1, sizeof(struct ipsec_auth)); 2106 if (r->auth == NULL) 2107 err(1, "create_flow: calloc"); 2108 r->auth->srcid = srcid; 2109 r->auth->dstid = dstid; 2110 r->auth->idtype = ID_FQDN; /* XXX For now only FQDN. */ 2111 2112 return r; 2113 2114errout: 2115 free(r); 2116 if (srcid) 2117 free(srcid); 2118 if (dstid) 2119 free(dstid); 2120 free(hosts->src); 2121 hosts->src = NULL; 2122 free(hosts->dst); 2123 hosts->dst = NULL; 2124 2125 return NULL; 2126} 2127 2128int 2129expand_rule(struct ipsec_rule *rule, u_int8_t direction, u_int32_t spi, 2130 struct ipsec_key *authkey, struct ipsec_key *enckey, int group) 2131{ 2132 struct ipsec_rule *r, *revr; 2133 struct ipsec_addr_wrap *src, *dst; 2134 int added = 0; 2135 2136 for (src = rule->src; src; src = src->next) { 2137 for (dst = rule->dst; dst; dst = dst->next) { 2138 if (src->af != dst->af) 2139 continue; 2140 r = copyrule(rule); 2141 2142 r->src = copyhost(src); 2143 r->dst = copyhost(dst); 2144 2145 r->nr = ipsec->rule_nr++; 2146 if (ipsecctl_add_rule(ipsec, r)) 2147 return (1); 2148 if (group && add_sagroup(r)) 2149 return (1); 2150 2151 if (direction == IPSEC_INOUT) { 2152 /* Create and add reverse flow rule. */ 2153 revr = reverse_rule(r); 2154 if (revr == NULL) 2155 return (1); 2156 2157 revr->nr = ipsec->rule_nr++; 2158 if (ipsecctl_add_rule(ipsec, revr)) 2159 return (1); 2160 if (group && add_sagroup(revr)) 2161 return (1); 2162 } else if (spi != 0 || authkey || enckey) { 2163 /* Create and add reverse sa rule. */ 2164 revr = reverse_sa(r, spi, authkey, enckey); 2165 if (revr == NULL) 2166 return (1); 2167 2168 revr->nr = ipsec->rule_nr++; 2169 if (ipsecctl_add_rule(ipsec, revr)) 2170 return (1); 2171 if (group && add_sagroup(revr)) 2172 return (1); 2173 } 2174 added++; 2175 } 2176 } 2177 if (!added) 2178 yyerror("rule expands to no valid combination"); 2179 ipsecctl_free_rule(rule); 2180 return (0); 2181} 2182 2183struct ipsec_rule * 2184reverse_rule(struct ipsec_rule *rule) 2185{ 2186 struct ipsec_rule *reverse; 2187 2188 reverse = calloc(1, sizeof(struct ipsec_rule)); 2189 if (reverse == NULL) 2190 err(1, "reverse_rule: calloc"); 2191 2192 reverse->type |= RULE_FLOW; 2193 2194 /* Reverse direction */ 2195 if (rule->direction == (u_int8_t)IPSEC_OUT) 2196 reverse->direction = (u_int8_t)IPSEC_IN; 2197 else 2198 reverse->direction = (u_int8_t)IPSEC_OUT; 2199 2200 reverse->flowtype = rule->flowtype; 2201 reverse->src = copyhost(rule->dst); 2202 reverse->dst = copyhost(rule->src); 2203 reverse->sport = rule->dport; 2204 reverse->dport = rule->sport; 2205 if (rule->local) 2206 reverse->local = copyhost(rule->local); 2207 if (rule->peer) 2208 reverse->peer = copyhost(rule->peer); 2209 reverse->satype = rule->satype; 2210 reverse->proto = rule->proto; 2211 2212 if (rule->auth) { 2213 reverse->auth = calloc(1, sizeof(struct ipsec_auth)); 2214 if (reverse->auth == NULL) 2215 err(1, "reverse_rule: calloc"); 2216 if (rule->auth->dstid && (reverse->auth->dstid = 2217 strdup(rule->auth->dstid)) == NULL) 2218 err(1, "reverse_rule: strdup"); 2219 if (rule->auth->srcid && (reverse->auth->srcid = 2220 strdup(rule->auth->srcid)) == NULL) 2221 err(1, "reverse_rule: strdup"); 2222 reverse->auth->idtype = rule->auth->idtype; 2223 reverse->auth->type = rule->auth->type; 2224 } 2225 2226 return reverse; 2227} 2228 2229struct ipsec_rule * 2230create_ike(u_int8_t proto, struct ipsec_hosts *hosts, struct ipsec_hosts *peers, 2231 struct ike_mode *mainmode, struct ike_mode *quickmode, 2232 u_int8_t satype, u_int8_t tmode, u_int8_t mode, char *srcid, char *dstid, 2233 struct ike_auth *authtype) 2234{ 2235 struct ipsec_rule *r; 2236 2237 r = calloc(1, sizeof(struct ipsec_rule)); 2238 if (r == NULL) 2239 err(1, "create_ike: calloc"); 2240 2241 r->type = RULE_IKE; 2242 2243 r->proto = proto; 2244 r->src = hosts->src; 2245 r->sport = hosts->sport; 2246 r->dst = hosts->dst; 2247 r->dport = hosts->dport; 2248 if ((hosts->sport != 0 || hosts->dport != 0) && 2249 (proto != IPPROTO_TCP && proto != IPPROTO_UDP)) { 2250 yyerror("no protocol supplied with source/destination ports"); 2251 free(r); 2252 free(hosts->src); 2253 hosts->src = NULL; 2254 free(hosts->dst); 2255 hosts->dst = NULL; 2256 if (mainmode) { 2257 free(mainmode->xfs); 2258 mainmode->xfs = NULL; 2259 free(mainmode->life); 2260 mainmode->life = NULL; 2261 } 2262 if (quickmode) { 2263 free(quickmode->xfs); 2264 quickmode->xfs = NULL; 2265 free(quickmode->life); 2266 quickmode->life = NULL; 2267 } 2268 if (srcid) 2269 free(srcid); 2270 if (dstid) 2271 free(dstid); 2272 return NULL; 2273 } 2274 2275 if (peers->dst == NULL) { 2276 /* Set peer to remote host. Must be a host address. */ 2277 if (r->direction == IPSEC_IN) { 2278 if (r->src->netaddress) 2279 r->peer = NULL; 2280 else 2281 r->peer = copyhost(r->src); 2282 } else { 2283 if (r->dst->netaddress) 2284 r->peer = NULL; 2285 else 2286 r->peer = copyhost(r->dst); 2287 } 2288 } else 2289 r->peer = peers->dst; 2290 2291 if (peers->src) 2292 r->local = peers->src; 2293 2294 r->satype = satype; 2295 r->tmode = tmode; 2296 r->ikemode = mode; 2297 if (mainmode) { 2298 r->mmxfs = mainmode->xfs; 2299 r->mmlife = mainmode->life; 2300 } 2301 if (quickmode) { 2302 r->qmxfs = quickmode->xfs; 2303 r->qmlife = quickmode->life; 2304 } 2305 r->auth = calloc(1, sizeof(struct ipsec_auth)); 2306 if (r->auth == NULL) 2307 err(1, "create_ike: calloc"); 2308 r->auth->srcid = srcid; 2309 r->auth->dstid = dstid; 2310 r->auth->idtype = ID_FQDN; /* XXX For now only FQDN. */ 2311 r->ikeauth = calloc(1, sizeof(struct ike_auth)); 2312 if (r->ikeauth == NULL) 2313 err(1, "create_ike: calloc"); 2314 r->ikeauth->type = authtype->type; 2315 r->ikeauth->string = authtype->string; 2316 2317 return (r); 2318} 2319