2 /* $KAME: parse.y,v 1.83 2004/05/18 08:48:23 sakane Exp $ */
5 * Copyright (C) 1995, 1996, 1997, 1998, and 1999 WIDE Project.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 3. Neither the name of the project nor the names of its contributors
17 * may be used to endorse or promote products derived from this software
18 * without specific prior written permission.
20 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34 #include <sys/types.h>
35 #include <sys/param.h>
36 #include <sys/socket.h>
38 #include <net/route.h>
39 #include <netinet/in.h>
40 #include <net/pfkeyv2.h>
41 #include <netipsec/key_var.h>
42 #include <netipsec/ipsec.h>
43 #include <arpa/inet.h>
56 (isdigit(c) ? (c - '0') : (isupper(c) ? (c - 'A' + 10) : (c - 'a' + 10)))
59 u_int p_ext, p_alg_enc, p_alg_auth, p_replay, p_mode;
61 u_int p_key_enc_len, p_key_auth_len;
62 caddr_t p_key_enc, p_key_auth;
63 time_t p_lt_hard, p_lt_soft;
65 static int p_aiflags = 0, p_aifamily = PF_UNSPEC;
67 static struct addrinfo *parse_addr(char *, char *);
68 static int fix_portstr(vchar_t *, vchar_t *, vchar_t *);
69 static int setvarbuf(char *, int *, struct sadb_ext *, int, caddr_t, int);
70 void parse_init(void);
71 void free_buffer(void);
73 int setkeymsg0(struct sadb_msg *, unsigned int, unsigned int, size_t);
74 static int setkeymsg_spdaddr(unsigned int, unsigned int, vchar_t *,
75 struct addrinfo *, int, struct addrinfo *, int);
76 static int setkeymsg_addr(unsigned int, unsigned int,
77 struct addrinfo *, struct addrinfo *, int);
78 static int setkeymsg_add(unsigned int, unsigned int,
79 struct addrinfo *, struct addrinfo *);
80 extern int setkeymsg(char *, size_t *);
81 extern int sendkeymsg(char *, size_t);
83 extern int yylex(void);
84 extern void yyfatal(const char *);
85 extern void yyerror(const char *);
95 %token EOT SLASH BLCL ELCL
96 %token ADD GET DELETE DELETEALL FLUSH DUMP
97 %token PR_ESP PR_AH PR_IPCOMP PR_TCP
98 %token F_PROTOCOL F_AUTH F_ENC F_REPLAY F_COMP F_RAWCPI
99 %token F_MODE MODE F_REQID
100 %token F_EXT EXTENSION NOCYCLICSEQ
101 %token ALG_AUTH ALG_AUTH_NOKEY
102 %token ALG_ENC ALG_ENC_NOKEY ALG_ENC_DESDERIV ALG_ENC_DES32IV ALG_ENC_OLD
105 %token F_LIFETIME_HARD F_LIFETIME_SOFT
106 %token DECSTRING QUOTEDSTRING HEXSTRING STRING ANY
108 %token SPDADD SPDDELETE SPDDUMP SPDFLUSH
109 %token F_POLICY PL_REQUESTS
113 %type <num> prefix protocol_spec upper_spec
114 %type <num> ALG_ENC ALG_ENC_DESDERIV ALG_ENC_DES32IV ALG_ENC_OLD ALG_ENC_NOKEY
115 %type <num> ALG_ENC_SALT
116 %type <num> ALG_AUTH ALG_AUTH_NOKEY
118 %type <num> PR_ESP PR_AH PR_IPCOMP PR_TCP
119 %type <num> EXTENSION MODE
120 %type <ulnum> DECSTRING
121 %type <val> PL_REQUESTS portstr key_string
122 %type <val> policy_requests
123 %type <val> QUOTEDSTRING HEXSTRING STRING
124 %type <val> F_AIFLAGS
125 %type <val> upper_misc_spec policy_spec
150 /* commands concerned with management, there is in tail of this file. */
154 : ADD ipaddropts ipaddr ipaddr protocol_spec spi extension_spec algorithm_spec EOT
158 status = setkeymsg_add(SADB_ADD, $5, $3, $4);
166 : DELETE ipaddropts ipaddr ipaddr protocol_spec spi extension_spec EOT
170 if ($3->ai_next || $4->ai_next) {
171 yyerror("multiple address specified");
174 if (p_mode != IPSEC_MODE_ANY)
175 yyerror("WARNING: mode is obsolete");
177 status = setkeymsg_addr(SADB_DELETE, $5, $3, $4, 0);
183 /* deleteall command */
185 : DELETEALL ipaddropts ipaddr ipaddr protocol_spec EOT
189 status = setkeymsg_addr(SADB_DELETE, $5, $3, $4, 1);
197 : GET ipaddropts ipaddr ipaddr protocol_spec spi extension_spec EOT
201 if (p_mode != IPSEC_MODE_ANY)
202 yyerror("WARNING: mode is obsolete");
204 status = setkeymsg_addr(SADB_GET, $5, $3, $4, 0);
212 : FLUSH protocol_spec EOT
215 setkeymsg0(&msg, SADB_FLUSH, $2, sizeof(msg));
216 sendkeymsg((char *)&msg, sizeof(msg));
222 : DUMP protocol_spec EOT
225 setkeymsg0(&msg, SADB_DUMP, $2, sizeof(msg));
226 sendkeymsg((char *)&msg, sizeof(msg));
233 $$ = SADB_SATYPE_UNSPEC;
237 $$ = SADB_SATYPE_ESP;
239 p_ext |= SADB_X_EXT_OLD;
241 p_ext &= ~SADB_X_EXT_OLD;
247 p_ext |= SADB_X_EXT_OLD;
249 p_ext &= ~SADB_X_EXT_OLD;
253 $$ = SADB_X_SATYPE_IPCOMP;
257 $$ = SADB_X_SATYPE_TCPSIGNATURE;
262 : DECSTRING { p_spi = $1; }
269 v = strtoul($1.buf, &ep, 16);
271 yyerror("invalid SPI");
274 if (v & ~0xffffffff) {
275 yyerror("SPI too big.");
290 : F_ENC enc_alg F_AUTH auth_alg
302 yyerror("unsupported algorithm");
307 | F_COMP ALG_COMP F_RAWCPI
310 yyerror("unsupported algorithm");
314 p_ext |= SADB_X_EXT_RAWCPI;
321 yyerror("unsupported algorithm");
328 if (ipsec_check_keylen(SADB_EXT_SUPPORTED_ENCRYPT,
329 p_alg_enc, PFKEY_UNUNIT64(p_key_enc_len)) < 0) {
330 yyerror(ipsec_strerror());
334 | ALG_ENC key_string {
336 yyerror("unsupported algorithm");
341 p_key_enc_len = $2.len;
343 if (ipsec_check_keylen(SADB_EXT_SUPPORTED_ENCRYPT,
344 p_alg_enc, PFKEY_UNUNIT64(p_key_enc_len)) < 0) {
345 yyerror(ipsec_strerror());
351 yyerror("unsupported algorithm");
354 yyerror("WARNING: obsolete algorithm");
359 if (ipsec_check_keylen(SADB_EXT_SUPPORTED_ENCRYPT,
360 p_alg_enc, PFKEY_UNUNIT64(p_key_enc_len)) < 0) {
361 yyerror(ipsec_strerror());
365 | ALG_ENC_DESDERIV key_string
368 yyerror("unsupported algorithm");
372 if (p_ext & SADB_X_EXT_OLD) {
373 yyerror("algorithm mismatched");
376 p_ext |= SADB_X_EXT_DERIV;
378 p_key_enc_len = $2.len;
380 if (ipsec_check_keylen(SADB_EXT_SUPPORTED_ENCRYPT,
381 p_alg_enc, PFKEY_UNUNIT64(p_key_enc_len)) < 0) {
382 yyerror(ipsec_strerror());
386 | ALG_ENC_DES32IV key_string
389 yyerror("unsupported algorithm");
393 if (!(p_ext & SADB_X_EXT_OLD)) {
394 yyerror("algorithm mismatched");
397 p_ext |= SADB_X_EXT_IV4B;
399 p_key_enc_len = $2.len;
401 if (ipsec_check_keylen(SADB_EXT_SUPPORTED_ENCRYPT,
402 p_alg_enc, PFKEY_UNUNIT64(p_key_enc_len)) < 0) {
403 yyerror(ipsec_strerror());
407 | ALG_ENC_SALT key_string
410 yyerror("unsupported algorithm");
415 p_key_enc_len = $2.len;
419 * Salted keys include a 4 byte value that is
420 * not part of the key.
422 if (ipsec_check_keylen(SADB_EXT_SUPPORTED_ENCRYPT,
423 p_alg_enc, PFKEY_UNUNIT64(p_key_enc_len - 4)) < 0) {
424 yyerror(ipsec_strerror());
431 : ALG_AUTH key_string {
433 yyerror("unsupported algorithm");
438 p_key_auth_len = $2.len;
441 if (p_alg_auth == SADB_X_AALG_TCP_MD5) {
442 if ((p_key_auth_len < 1) || (p_key_auth_len >
445 } else if (ipsec_check_keylen(SADB_EXT_SUPPORTED_AUTH,
446 p_alg_auth, PFKEY_UNUNIT64(p_key_auth_len)) < 0) {
447 yyerror(ipsec_strerror());
453 yyerror("unsupported algorithm");
475 l = strlen(yp) % 2 + strlen(yp) / 2;
476 if ((pp_key = malloc(l)) == 0) {
477 yyerror("not enough core");
480 memset(pp_key, 0, l);
483 if (strlen(yp) % 2) {
488 *bp = (ATOX(yp[0]) << 4) | ATOX(yp[1]);
499 | extension_spec extension
503 : F_EXT EXTENSION { p_ext |= $2; }
504 | F_EXT NOCYCLICSEQ { p_ext &= ~SADB_X_EXT_CYCSEQ; }
505 | F_MODE MODE { p_mode = $2; }
506 | F_MODE ANY { p_mode = IPSEC_MODE_ANY; }
507 | F_REQID DECSTRING { p_reqid = $2; }
510 if ((p_ext & SADB_X_EXT_OLD) != 0) {
511 yyerror("replay prevention cannot be used with "
517 | F_LIFETIME_HARD DECSTRING { p_lt_hard = $2; }
518 | F_LIFETIME_SOFT DECSTRING { p_lt_soft = $2; }
521 /* definition about command for SPD management */
524 : SPDADD ipaddropts STRING prefix portstr STRING prefix portstr upper_spec upper_misc_spec policy_spec EOT
527 struct addrinfo *src, *dst;
529 /* fixed port fields if ulp is icmpv6 */
530 if ($10.buf != NULL) {
531 if ($9 != IPPROTO_ICMPV6)
535 if (fix_portstr(&$10, &$5, &$8))
539 src = parse_addr($3.buf, $5.buf);
540 dst = parse_addr($6.buf, $8.buf);
542 /* yyerror is already called */
545 if (src->ai_next || dst->ai_next) {
546 yyerror("multiple address specified");
552 status = setkeymsg_spdaddr(SADB_X_SPDADD, $9, &$11,
559 | SPDADD TAGGED QUOTEDSTRING policy_spec EOT
566 : SPDDELETE ipaddropts STRING prefix portstr STRING prefix portstr upper_spec upper_misc_spec policy_spec EOT
569 struct addrinfo *src, *dst;
571 /* fixed port fields if ulp is icmpv6 */
572 if ($10.buf != NULL) {
573 if ($9 != IPPROTO_ICMPV6)
577 if (fix_portstr(&$10, &$5, &$8))
581 src = parse_addr($3.buf, $5.buf);
582 dst = parse_addr($6.buf, $8.buf);
584 /* yyerror is already called */
587 if (src->ai_next || dst->ai_next) {
588 yyerror("multiple address specified");
594 status = setkeymsg_spdaddr(SADB_X_SPDDELETE, $9, &$11,
607 setkeymsg0(&msg, SADB_X_SPDDUMP, SADB_SATYPE_UNSPEC,
609 sendkeymsg((char *)&msg, sizeof(msg));
617 setkeymsg0(&msg, SADB_X_SPDFLUSH, SADB_SATYPE_UNSPEC,
619 sendkeymsg((char *)&msg, sizeof(msg));
625 | ipaddropts ipaddropt
633 for (p = $1.buf + 1; *p; p++)
636 p_aifamily = AF_INET;
640 p_aifamily = AF_INET6;
644 p_aiflags = AI_NUMERICHOST;
647 yyerror("invalid flag");
656 $$ = parse_addr($1.buf, NULL);
658 /* yyerror already called by parse_addr */
665 : /*NOTHING*/ { $$ = -1; }
666 | SLASH DECSTRING { $$ = $2; }
672 $$.buf = strdup("0");
674 yyerror("insufficient memory");
677 $$.len = strlen($$.buf);
681 $$.buf = strdup("0");
683 yyerror("insufficient memory");
686 $$.len = strlen($$.buf);
688 | BLCL DECSTRING ELCL
691 snprintf(buf, sizeof(buf), "%lu", $2);
692 $$.buf = strdup(buf);
694 yyerror("insufficient memory");
697 $$.len = strlen($$.buf);
706 : DECSTRING { $$ = $1; }
707 | ANY { $$ = IPSEC_ULPROTO_ANY; }
708 | PR_TCP { $$ = IPPROTO_TCP; }
709 | PR_ESP { $$ = IPPROTO_ESP; }
712 struct protoent *ent;
714 ent = getprotobyname($1.buf);
718 if (strcmp("icmp6", $1.buf) == 0) {
720 } else if(strcmp("ip4", $1.buf) == 0) {
723 yyerror("invalid upper layer protocol");
739 $$.buf = strdup($1.buf);
741 yyerror("insufficient memory");
744 $$.len = strlen($$.buf);
749 : F_POLICY policy_requests
753 policy = ipsec_set_policy($2.buf, $2.len);
754 if (policy == NULL) {
755 yyerror(ipsec_strerror());
760 $$.len = ipsec_get_policylen(policy);
765 : PL_REQUESTS { $$ = $1; }
771 setkeymsg0(msg, type, satype, l)
772 struct sadb_msg *msg;
778 msg->sadb_msg_version = PF_KEY_V2;
779 msg->sadb_msg_type = type;
780 msg->sadb_msg_errno = 0;
781 msg->sadb_msg_satype = satype;
782 msg->sadb_msg_reserved = 0;
783 msg->sadb_msg_seq = 0;
784 msg->sadb_msg_pid = getpid();
785 msg->sadb_msg_len = PFKEY_UNIT64(l);
789 /* XXX NO BUFFER OVERRUN CHECK! BAD BAD! */
791 setkeymsg_spdaddr(type, upper, policy, srcs, splen, dsts, dplen)
795 struct addrinfo *srcs;
797 struct addrinfo *dsts;
800 struct sadb_msg *msg;
803 struct sadb_address m_addr;
804 struct addrinfo *s, *d;
810 msg = (struct sadb_msg *)buf;
815 /* fix up length afterwards */
816 setkeymsg0(msg, type, SADB_SATYPE_UNSPEC, 0);
817 l = sizeof(struct sadb_msg);
819 memcpy(buf + l, policy->buf, policy->len);
825 /* do it for all src/dst pairs */
826 for (s = srcs; s; s = s->ai_next) {
827 for (d = dsts; d; d = d->ai_next) {
831 if (s->ai_addr->sa_family != d->ai_addr->sa_family)
833 switch (s->ai_addr->sa_family) {
835 plen = sizeof(struct in_addr) << 3;
839 plen = sizeof(struct in6_addr) << 3;
848 salen = s->ai_addr->sa_len;
849 m_addr.sadb_address_len = PFKEY_UNIT64(sizeof(m_addr) +
850 PFKEY_ALIGN8(salen));
851 m_addr.sadb_address_exttype = SADB_EXT_ADDRESS_SRC;
852 m_addr.sadb_address_proto = upper;
853 m_addr.sadb_address_prefixlen =
854 (splen >= 0 ? splen : plen);
855 m_addr.sadb_address_reserved = 0;
857 setvarbuf(buf, &l, (struct sadb_ext *)&m_addr,
858 sizeof(m_addr), (caddr_t)sa, salen);
862 salen = d->ai_addr->sa_len;
863 m_addr.sadb_address_len = PFKEY_UNIT64(sizeof(m_addr) +
864 PFKEY_ALIGN8(salen));
865 m_addr.sadb_address_exttype = SADB_EXT_ADDRESS_DST;
866 m_addr.sadb_address_proto = upper;
867 m_addr.sadb_address_prefixlen =
868 (dplen >= 0 ? dplen : plen);
869 m_addr.sadb_address_reserved = 0;
871 setvarbuf(buf, &l, (struct sadb_ext *)&m_addr,
872 sizeof(m_addr), (caddr_t)sa, salen);
874 msg->sadb_msg_len = PFKEY_UNIT64(l);
888 /* XXX NO BUFFER OVERRUN CHECK! BAD BAD! */
890 setkeymsg_addr(type, satype, srcs, dsts, no_spi)
893 struct addrinfo *srcs;
894 struct addrinfo *dsts;
897 struct sadb_msg *msg;
901 struct sadb_x_sa2 m_sa2;
902 struct sadb_address m_addr;
903 struct addrinfo *s, *d;
909 msg = (struct sadb_msg *)buf;
914 /* fix up length afterwards */
915 setkeymsg0(msg, type, satype, 0);
916 l = sizeof(struct sadb_msg);
919 len = sizeof(struct sadb_sa);
920 m_sa.sadb_sa_len = PFKEY_UNIT64(len);
921 m_sa.sadb_sa_exttype = SADB_EXT_SA;
922 m_sa.sadb_sa_spi = htonl(p_spi);
923 m_sa.sadb_sa_replay = p_replay;
924 m_sa.sadb_sa_state = 0;
925 m_sa.sadb_sa_auth = p_alg_auth;
926 m_sa.sadb_sa_encrypt = p_alg_enc;
927 m_sa.sadb_sa_flags = p_ext;
929 memcpy(buf + l, &m_sa, len);
932 len = sizeof(struct sadb_x_sa2);
933 m_sa2.sadb_x_sa2_len = PFKEY_UNIT64(len);
934 m_sa2.sadb_x_sa2_exttype = SADB_X_EXT_SA2;
935 m_sa2.sadb_x_sa2_mode = p_mode;
936 m_sa2.sadb_x_sa2_reqid = p_reqid;
938 memcpy(buf + l, &m_sa2, len);
945 /* do it for all src/dst pairs */
946 for (s = srcs; s; s = s->ai_next) {
947 for (d = dsts; d; d = d->ai_next) {
951 if (s->ai_addr->sa_family != d->ai_addr->sa_family)
953 switch (s->ai_addr->sa_family) {
955 plen = sizeof(struct in_addr) << 3;
959 plen = sizeof(struct in6_addr) << 3;
968 salen = s->ai_addr->sa_len;
969 m_addr.sadb_address_len = PFKEY_UNIT64(sizeof(m_addr) +
970 PFKEY_ALIGN8(salen));
971 m_addr.sadb_address_exttype = SADB_EXT_ADDRESS_SRC;
972 m_addr.sadb_address_proto = IPSEC_ULPROTO_ANY;
973 m_addr.sadb_address_prefixlen = plen;
974 m_addr.sadb_address_reserved = 0;
976 setvarbuf(buf, &l, (struct sadb_ext *)&m_addr,
977 sizeof(m_addr), (caddr_t)sa, salen);
981 salen = d->ai_addr->sa_len;
982 m_addr.sadb_address_len = PFKEY_UNIT64(sizeof(m_addr) +
983 PFKEY_ALIGN8(salen));
984 m_addr.sadb_address_exttype = SADB_EXT_ADDRESS_DST;
985 m_addr.sadb_address_proto = IPSEC_ULPROTO_ANY;
986 m_addr.sadb_address_prefixlen = plen;
987 m_addr.sadb_address_reserved = 0;
989 setvarbuf(buf, &l, (struct sadb_ext *)&m_addr,
990 sizeof(m_addr), (caddr_t)sa, salen);
992 msg->sadb_msg_len = PFKEY_UNIT64(l);
1006 /* XXX NO BUFFER OVERRUN CHECK! BAD BAD! */
1008 setkeymsg_add(type, satype, srcs, dsts)
1010 unsigned int satype;
1011 struct addrinfo *srcs;
1012 struct addrinfo *dsts;
1014 struct sadb_msg *msg;
1017 struct sadb_sa m_sa;
1018 struct sadb_x_sa2 m_sa2;
1019 struct sadb_address m_addr;
1020 struct addrinfo *s, *d;
1023 struct sockaddr *sa;
1026 msg = (struct sadb_msg *)buf;
1031 /* fix up length afterwards */
1032 setkeymsg0(msg, type, satype, 0);
1033 l = sizeof(struct sadb_msg);
1035 /* set encryption algorithm, if present. */
1036 if (satype != SADB_X_SATYPE_IPCOMP && p_key_enc) {
1037 struct sadb_key m_key;
1039 m_key.sadb_key_len =
1040 PFKEY_UNIT64(sizeof(m_key)
1041 + PFKEY_ALIGN8(p_key_enc_len));
1042 m_key.sadb_key_exttype = SADB_EXT_KEY_ENCRYPT;
1043 m_key.sadb_key_bits = p_key_enc_len * 8;
1044 m_key.sadb_key_reserved = 0;
1047 (struct sadb_ext *)&m_key, sizeof(m_key),
1048 (caddr_t)p_key_enc, p_key_enc_len);
1051 /* set authentication algorithm, if present. */
1053 struct sadb_key m_key;
1055 m_key.sadb_key_len =
1056 PFKEY_UNIT64(sizeof(m_key)
1057 + PFKEY_ALIGN8(p_key_auth_len));
1058 m_key.sadb_key_exttype = SADB_EXT_KEY_AUTH;
1059 m_key.sadb_key_bits = p_key_auth_len * 8;
1060 m_key.sadb_key_reserved = 0;
1063 (struct sadb_ext *)&m_key, sizeof(m_key),
1064 (caddr_t)p_key_auth, p_key_auth_len);
1067 /* set lifetime for HARD */
1068 if (p_lt_hard != 0) {
1069 struct sadb_lifetime m_lt;
1070 u_int slen = sizeof(struct sadb_lifetime);
1072 m_lt.sadb_lifetime_len = PFKEY_UNIT64(slen);
1073 m_lt.sadb_lifetime_exttype = SADB_EXT_LIFETIME_HARD;
1074 m_lt.sadb_lifetime_allocations = 0;
1075 m_lt.sadb_lifetime_bytes = 0;
1076 m_lt.sadb_lifetime_addtime = p_lt_hard;
1077 m_lt.sadb_lifetime_usetime = 0;
1079 memcpy(buf + l, &m_lt, slen);
1083 /* set lifetime for SOFT */
1084 if (p_lt_soft != 0) {
1085 struct sadb_lifetime m_lt;
1086 u_int slen = sizeof(struct sadb_lifetime);
1088 m_lt.sadb_lifetime_len = PFKEY_UNIT64(slen);
1089 m_lt.sadb_lifetime_exttype = SADB_EXT_LIFETIME_SOFT;
1090 m_lt.sadb_lifetime_allocations = 0;
1091 m_lt.sadb_lifetime_bytes = 0;
1092 m_lt.sadb_lifetime_addtime = p_lt_soft;
1093 m_lt.sadb_lifetime_usetime = 0;
1095 memcpy(buf + l, &m_lt, slen);
1099 len = sizeof(struct sadb_sa);
1100 m_sa.sadb_sa_len = PFKEY_UNIT64(len);
1101 m_sa.sadb_sa_exttype = SADB_EXT_SA;
1102 m_sa.sadb_sa_spi = htonl(p_spi);
1103 m_sa.sadb_sa_replay = p_replay;
1104 m_sa.sadb_sa_state = 0;
1105 m_sa.sadb_sa_auth = p_alg_auth;
1106 m_sa.sadb_sa_encrypt = p_alg_enc;
1107 m_sa.sadb_sa_flags = p_ext;
1109 memcpy(buf + l, &m_sa, len);
1112 len = sizeof(struct sadb_x_sa2);
1113 m_sa2.sadb_x_sa2_len = PFKEY_UNIT64(len);
1114 m_sa2.sadb_x_sa2_exttype = SADB_X_EXT_SA2;
1115 m_sa2.sadb_x_sa2_mode = p_mode;
1116 m_sa2.sadb_x_sa2_reqid = p_reqid;
1118 memcpy(buf + l, &m_sa2, len);
1124 /* do it for all src/dst pairs */
1125 for (s = srcs; s; s = s->ai_next) {
1126 for (d = dsts; d; d = d->ai_next) {
1127 /* rewind pointer */
1130 if (s->ai_addr->sa_family != d->ai_addr->sa_family)
1132 switch (s->ai_addr->sa_family) {
1134 plen = sizeof(struct in_addr) << 3;
1138 plen = sizeof(struct in6_addr) << 3;
1147 salen = s->ai_addr->sa_len;
1148 m_addr.sadb_address_len = PFKEY_UNIT64(sizeof(m_addr) +
1149 PFKEY_ALIGN8(salen));
1150 m_addr.sadb_address_exttype = SADB_EXT_ADDRESS_SRC;
1151 m_addr.sadb_address_proto = IPSEC_ULPROTO_ANY;
1152 m_addr.sadb_address_prefixlen = plen;
1153 m_addr.sadb_address_reserved = 0;
1155 setvarbuf(buf, &l, (struct sadb_ext *)&m_addr,
1156 sizeof(m_addr), (caddr_t)sa, salen);
1160 salen = d->ai_addr->sa_len;
1161 m_addr.sadb_address_len = PFKEY_UNIT64(sizeof(m_addr) +
1162 PFKEY_ALIGN8(salen));
1163 m_addr.sadb_address_exttype = SADB_EXT_ADDRESS_DST;
1164 m_addr.sadb_address_proto = IPSEC_ULPROTO_ANY;
1165 m_addr.sadb_address_prefixlen = plen;
1166 m_addr.sadb_address_reserved = 0;
1168 setvarbuf(buf, &l, (struct sadb_ext *)&m_addr,
1169 sizeof(m_addr), (caddr_t)sa, salen);
1171 msg->sadb_msg_len = PFKEY_UNIT64(l);
1185 static struct addrinfo *
1186 parse_addr(host, port)
1190 struct addrinfo hints, *res = NULL;
1193 memset(&hints, 0, sizeof(hints));
1194 hints.ai_family = p_aifamily;
1195 hints.ai_socktype = SOCK_DGRAM; /*dummy*/
1196 hints.ai_protocol = IPPROTO_UDP; /*dummy*/
1197 hints.ai_flags = p_aiflags;
1198 error = getaddrinfo(host, port, &hints, &res);
1200 yyerror(gai_strerror(error));
1207 fix_portstr(spec, sport, dport)
1208 vchar_t *spec, *sport, *dport;
1214 for (p = spec->buf; *p != ',' && *p != '\0' && l < spec->len; p++, l++)
1223 for (p = p2; *p != '\0' && l < spec->len; p++, l++)
1225 if (*p != '\0' || *p2 == '\0') {
1226 yyerror("invalid an upper layer protocol spec");
1231 sport->buf = strdup(spec->buf);
1233 yyerror("insufficient memory");
1236 sport->len = strlen(sport->buf);
1237 dport->buf = strdup(p2);
1239 yyerror("insufficient memory");
1242 dport->len = strlen(dport->buf);
1248 setvarbuf(buf, off, ebuf, elen, vbuf, vlen)
1251 struct sadb_ext *ebuf;
1256 memset(buf + *off, 0, PFKEY_UNUNIT64(ebuf->sadb_ext_len));
1257 memcpy(buf + *off, (caddr_t)ebuf, elen);
1258 memcpy(buf + *off + elen, vbuf, vlen);
1259 (*off) += PFKEY_ALIGN8(elen + vlen);
1269 p_ext = SADB_X_EXT_CYCSEQ;
1270 p_alg_enc = SADB_EALG_NONE;
1271 p_alg_auth = SADB_AALG_NONE;
1272 p_mode = IPSEC_MODE_ANY;
1275 p_key_enc_len = p_key_auth_len = 0;
1276 p_key_enc = p_key_auth = 0;
1277 p_lt_hard = p_lt_soft = 0;
1280 p_aifamily = PF_UNSPEC;
1288 /* we got tons of memory leaks in the parser anyways, leave them */