]> git.saurik.com Git - apple/ipsec.git/blob - ipsec-tools/racoon/pfkey_racoon.c
03e70b4394f9f634a8b4d79b469525c337b63b14
[apple/ipsec.git] / ipsec-tools / racoon / pfkey_racoon.c
1 /* $Id: pfkey.c,v 1.31.2.10 2005/10/03 14:52:19 manubsd Exp $ */
2
3 /*
4 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. Neither the name of the project nor the names of its contributors
16 * may be used to endorse or promote products derived from this software
17 * without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
23 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29 * SUCH DAMAGE.
30 */
31
32 #include "config.h"
33
34 #include <stdlib.h>
35 #include <string.h>
36 #include <stdio.h>
37 #include <netdb.h>
38 #include <errno.h>
39 #ifdef HAVE_UNISTD_H
40 #include <unistd.h>
41 #endif
42 #include <netdb.h>
43 #include <netinet/in.h>
44 #include <arpa/inet.h>
45
46 #ifdef ENABLE_NATT
47 # ifdef __linux__
48 # include <linux/udp.h>
49 # endif
50 # if defined(__NetBSD__) || defined(__FreeBSD__)
51 # include <netinet/udp.h>
52 # endif
53 #endif
54
55 #include <sys/types.h>
56 #include <sys/param.h>
57 #include <sys/socket.h>
58 #include <sys/queue.h>
59 #include <sys/sysctl.h>
60
61 #include <net/route.h>
62 #ifdef __APPLE__
63 #include <System/net/pfkeyv2.h>
64 #else
65 #include <net/pfkeyv2.h>
66 #endif
67
68 #include <netinet/in.h>
69 #ifndef HAVE_NETINET6_IPSEC
70 #include <netinet/ipsec.h>
71 #else
72 #include <netinet6/ipsec.h>
73 #endif
74
75 #include "libpfkey.h"
76
77 #include "var.h"
78 #include "misc.h"
79 #include "vmbuf.h"
80 #include "plog.h"
81 #include "sockmisc.h"
82 #include "debug.h"
83
84 #include "schedule.h"
85 #include "localconf.h"
86 #include "remoteconf.h"
87 #include "isakmp_var.h"
88 #include "isakmp.h"
89 #include "isakmp_inf.h"
90 #include "ipsec_doi.h"
91 #include "oakley.h"
92 #include "pfkey.h"
93 #include "handler.h"
94 #include "policy.h"
95 #include "algorithm.h"
96 #include "sainfo.h"
97 #include "proposal.h"
98 #include "admin.h"
99 #include "privsep.h"
100 #include "strnames.h"
101 #include "backupsa.h"
102 #include "gcmalloc.h"
103 #include "nattraversal.h"
104 #include "crypto_openssl.h"
105 #include "grabmyaddr.h"
106 #include "vpn_control.h"
107 #include "vpn_control_var.h"
108
109 #if defined(SADB_X_EALG_RIJNDAELCBC) && !defined(SADB_X_EALG_AESCBC)
110 #define SADB_X_EALG_AESCBC SADB_X_EALG_RIJNDAELCBC
111 #endif
112
113 /* prototype */
114 static u_int ipsecdoi2pfkey_aalg __P((u_int));
115 static u_int ipsecdoi2pfkey_ealg __P((u_int));
116 static u_int ipsecdoi2pfkey_calg __P((u_int));
117 static u_int ipsecdoi2pfkey_alg __P((u_int, u_int));
118 static u_int keylen_aalg __P((u_int));
119 static u_int keylen_ealg __P((u_int, int));
120
121 static int pk_recvgetspi __P((caddr_t *));
122 static int pk_recvupdate __P((caddr_t *));
123 static int pk_recvadd __P((caddr_t *));
124 static int pk_recvdelete __P((caddr_t *));
125 static int pk_recvacquire __P((caddr_t *));
126 static int pk_recvexpire __P((caddr_t *));
127 static int pk_recvflush __P((caddr_t *));
128 static int getsadbpolicy __P((caddr_t *, int *, int, struct ph2handle *));
129 static int pk_recvspdupdate __P((caddr_t *));
130 static int pk_recvspdadd __P((caddr_t *));
131 static int pk_recvspddelete __P((caddr_t *));
132 static int pk_recvspdexpire __P((caddr_t *));
133 static int pk_recvspdget __P((caddr_t *));
134 static int pk_recvspddump __P((caddr_t *));
135 static int pk_recvspdflush __P((caddr_t *));
136 static struct sadb_msg *pk_recv __P((int, int *));
137
138 static int (*pkrecvf[]) __P((caddr_t *)) = {
139 NULL,
140 pk_recvgetspi,
141 pk_recvupdate,
142 pk_recvadd,
143 pk_recvdelete,
144 NULL, /* SADB_GET */
145 pk_recvacquire,
146 NULL, /* SABD_REGISTER */
147 pk_recvexpire,
148 pk_recvflush,
149 NULL, /* SADB_DUMP */
150 NULL, /* SADB_X_PROMISC */
151 NULL, /* SADB_X_PCHANGE */
152 pk_recvspdupdate,
153 pk_recvspdadd,
154 pk_recvspddelete,
155 pk_recvspdget,
156 NULL, /* SADB_X_SPDACQUIRE */
157 pk_recvspddump,
158 pk_recvspdflush,
159 NULL, /* SADB_X_SPDSETIDX */
160 pk_recvspdexpire,
161 NULL, /* SADB_X_SPDDELETE2 */
162 NULL, /* SADB_X_NAT_T_NEW_MAPPING */
163 NULL, /* SADB_X_MIGRATE */
164 #if (SADB_MAX > 24)
165 #error "SADB extra message?"
166 #endif
167 };
168
169 static int addnewsp __P((caddr_t *));
170
171 /* cope with old kame headers - ugly */
172 #ifndef SADB_X_AALG_MD5
173 #define SADB_X_AALG_MD5 SADB_AALG_MD5
174 #endif
175 #ifndef SADB_X_AALG_SHA
176 #define SADB_X_AALG_SHA SADB_AALG_SHA
177 #endif
178 #ifndef SADB_X_AALG_NULL
179 #define SADB_X_AALG_NULL SADB_AALG_NULL
180 #endif
181
182 #ifndef SADB_X_EALG_BLOWFISHCBC
183 #define SADB_X_EALG_BLOWFISHCBC SADB_EALG_BLOWFISHCBC
184 #endif
185 #ifndef SADB_X_EALG_CAST128CBC
186 #define SADB_X_EALG_CAST128CBC SADB_EALG_CAST128CBC
187 #endif
188 #ifndef SADB_X_EALG_RC5CBC
189 #ifdef SADB_EALG_RC5CBC
190 #define SADB_X_EALG_RC5CBC SADB_EALG_RC5CBC
191 #endif
192 #endif
193
194
195 int
196 pfkey_process(msg)
197 struct sadb_msg *msg;
198 {
199 caddr_t mhp[SADB_EXT_MAX + 1];
200 int error = -1;
201
202 plog(LLV_DEBUG, LOCATION, NULL, "get pfkey %s message\n",
203 s_pfkey_type(msg->sadb_msg_type));
204 plogdump(LLV_DEBUG2, msg, msg->sadb_msg_len << 3);
205
206 /* validity check */
207 if (msg->sadb_msg_errno) {
208 int pri;
209
210 /* when SPD is empty, treat the state as no error. */
211 if (msg->sadb_msg_type == SADB_X_SPDDUMP &&
212 msg->sadb_msg_errno == ENOENT)
213 pri = LLV_DEBUG;
214 else
215 pri = LLV_ERROR;
216
217 plog(pri, LOCATION, NULL,
218 "pfkey %s failed: %s\n",
219 s_pfkey_type(msg->sadb_msg_type),
220 strerror(msg->sadb_msg_errno));
221
222 goto end;
223 }
224
225 /* check pfkey message. */
226 if (pfkey_align(msg, mhp)) {
227 plog(LLV_ERROR, LOCATION, NULL,
228 "libipsec failed pfkey align (%s)\n",
229 ipsec_strerror());
230 goto end;
231 }
232 if (pfkey_check(mhp)) {
233 plog(LLV_ERROR, LOCATION, NULL,
234 "libipsec failed pfkey check (%s)\n",
235 ipsec_strerror());
236 goto end;
237 }
238 msg = (struct sadb_msg *)mhp[0];
239
240 /* safety check */
241 if (msg->sadb_msg_type >= ARRAYLEN(pkrecvf)) {
242 plog(LLV_ERROR, LOCATION, NULL,
243 "unknown PF_KEY message type=%u\n",
244 msg->sadb_msg_type);
245 goto end;
246 }
247
248 if (pkrecvf[msg->sadb_msg_type] == NULL) {
249 plog(LLV_INFO, LOCATION, NULL,
250 "unsupported PF_KEY message %s\n",
251 s_pfkey_type(msg->sadb_msg_type));
252 goto end;
253 }
254
255 if ((pkrecvf[msg->sadb_msg_type])(mhp) < 0)
256 goto end;
257
258 error = 0;
259 end:
260 if (msg)
261 racoon_free(msg);
262 return(error);
263 }
264
265 /*
266 * PF_KEY packet handler
267 * 0: success
268 * -1: fail
269 */
270 int
271 pfkey_handler()
272 {
273 struct sadb_msg *msg;
274 int len;
275
276 /* receive pfkey message. */
277 len = 0;
278 msg = (struct sadb_msg *)pk_recv(lcconf->sock_pfkey, &len);
279 if (msg == NULL) {
280 if (len < 0) {
281 plog(LLV_ERROR, LOCATION, NULL,
282 "failed to recv from pfkey (%s)\n",
283 strerror(errno));
284 return -1;
285 } else {
286 /* short message - msg not ready */
287 return 0;
288 }
289 }
290 return pfkey_process(msg);
291 }
292
293 void
294 pfkey_post_handler()
295 {
296 struct saved_msg_elem *elem;
297 struct saved_msg_elem *elem_tmp = NULL;
298
299 TAILQ_FOREACH_SAFE(elem, &lcconf->saved_msg_queue, chain, elem_tmp) {
300 pfkey_process((struct sadb_msg *)elem->msg);
301 TAILQ_REMOVE(&lcconf->saved_msg_queue, elem, chain);
302 racoon_free(elem);
303
304 }
305 }
306
307 int
308 pfkey_save_msg(msg)
309 struct sadb_msg *msg;
310 {
311 struct saved_msg_elem *elem;
312
313 elem = (struct saved_msg_elem *)racoon_calloc(sizeof(struct saved_msg_elem), 1);
314 if (elem == NULL)
315 return -1;
316 elem->msg = msg;
317 TAILQ_INSERT_TAIL(&lcconf->saved_msg_queue, elem, chain);
318 return 0;
319 }
320
321 /*
322 * dump SADB
323 */
324 vchar_t *
325 pfkey_dump_sadb(satype)
326 int satype;
327 {
328 int s = -1;
329 vchar_t *buf = NULL;
330 pid_t pid = getpid();
331 struct sadb_msg *msg = NULL;
332 size_t bl, ml;
333 int len;
334
335 if ((s = privsep_pfkey_open()) < 0) {
336 plog(LLV_ERROR, LOCATION, NULL,
337 "libipsec failed pfkey open: %s\n",
338 ipsec_strerror());
339 return NULL;
340 }
341
342 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_dump\n");
343 if (pfkey_send_dump(s, satype) < 0) {
344 plog(LLV_ERROR, LOCATION, NULL,
345 "libipsec failed dump: %s\n", ipsec_strerror());
346 goto fail;
347 }
348
349 while (1) {
350 if (msg)
351 racoon_free(msg);
352 msg = pk_recv(s, &len);
353 if (msg == NULL) {
354 if (len < 0)
355 goto done;
356 else
357 continue;
358 }
359
360 if (msg->sadb_msg_pid != pid)
361 continue;
362
363 /*
364 * for multi-processor system this had to be added because the messages can
365 * be interleaved - they won't all be dump messages
366 */
367 if (msg->sadb_msg_type != SADB_DUMP) { /* save for later processing */
368 pfkey_save_msg(msg);
369 msg = NULL;
370 continue;
371 }
372
373 ml = msg->sadb_msg_len << 3;
374 bl = buf ? buf->l : 0;
375 buf = vrealloc(buf, bl + ml);
376 if (buf == NULL) {
377 plog(LLV_ERROR, LOCATION, NULL,
378 "failed to reallocate buffer to dump.\n");
379 goto fail;
380 }
381 memcpy(buf->v + bl, msg, ml);
382
383 if (msg->sadb_msg_seq == 0)
384 break;
385 }
386 goto done;
387
388 fail:
389 if (buf)
390 vfree(buf);
391 buf = NULL;
392 done:
393 if (msg)
394 racoon_free(msg);
395 if (s >= 0)
396 privsep_pfkey_close(s);
397 return buf;
398 }
399
400 #ifdef ENABLE_ADMINPORT
401 /*
402 * flush SADB
403 */
404 void
405 pfkey_flush_sadb(proto)
406 u_int proto;
407 {
408 int satype;
409
410 /* convert to SADB_SATYPE */
411 if ((satype = admin2pfkey_proto(proto)) < 0)
412 return;
413
414 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_flush\n");
415 if (pfkey_send_flush(lcconf->sock_pfkey, satype) < 0) {
416 plog(LLV_ERROR, LOCATION, NULL,
417 "libipsec failed send flush (%s)\n", ipsec_strerror());
418 return;
419 }
420
421 return;
422 }
423 #endif
424
425 /*
426 * These are the SATYPEs that we manage. We register to get
427 * PF_KEY messages related to these SATYPEs, and we also use
428 * this list to determine which SATYPEs to delete SAs for when
429 * we receive an INITIAL-CONTACT.
430 */
431 const struct pfkey_satype pfkey_satypes[] = {
432 { SADB_SATYPE_AH, "AH" },
433 { SADB_SATYPE_ESP, "ESP" },
434 { SADB_X_SATYPE_IPCOMP, "IPCOMP" },
435 };
436 const int pfkey_nsatypes =
437 sizeof(pfkey_satypes) / sizeof(pfkey_satypes[0]);
438
439 /*
440 * PF_KEY initialization
441 */
442 int
443 pfkey_init()
444 {
445 int i, reg_fail;
446
447 if ((lcconf->sock_pfkey = privsep_pfkey_open()) < 0) {
448 plog(LLV_ERROR, LOCATION, NULL,
449 "libipsec failed pfkey open (%s)\n", ipsec_strerror());
450 return -1;
451 }
452
453 for (i = 0, reg_fail = 0; i < pfkey_nsatypes; i++) {
454 plog(LLV_DEBUG, LOCATION, NULL,
455 "call pfkey_send_register for %s\n",
456 pfkey_satypes[i].ps_name);
457 if (pfkey_send_register(lcconf->sock_pfkey,
458 pfkey_satypes[i].ps_satype) < 0 ||
459 pfkey_recv_register(lcconf->sock_pfkey) < 0) {
460 plog(LLV_WARNING, LOCATION, NULL,
461 "failed to register %s (%s)\n",
462 pfkey_satypes[i].ps_name,
463 ipsec_strerror());
464 reg_fail++;
465 }
466 }
467
468 if (reg_fail == pfkey_nsatypes) {
469 plog(LLV_ERROR, LOCATION, NULL,
470 "failed to regist any protocol.\n");
471 pfkey_close(lcconf->sock_pfkey);
472 return -1;
473 }
474
475 initsp();
476
477 if (pfkey_send_spddump(lcconf->sock_pfkey) < 0) {
478 plog(LLV_ERROR, LOCATION, NULL,
479 "libipsec sending spddump failed: %s\n",
480 ipsec_strerror());
481 pfkey_close(lcconf->sock_pfkey);
482 return -1;
483 }
484 #if 0
485 if (pfkey_promisc_toggle(1) < 0) {
486 pfkey_close(lcconf->sock_pfkey);
487 return -1;
488 }
489 #endif
490 return 0;
491 }
492
493 /* %%% for conversion */
494 /* IPSECDOI_ATTR_AUTH -> SADB_AALG */
495 static u_int
496 ipsecdoi2pfkey_aalg(hashtype)
497 u_int hashtype;
498 {
499 switch (hashtype) {
500 case IPSECDOI_ATTR_AUTH_HMAC_MD5:
501 return SADB_AALG_MD5HMAC;
502 case IPSECDOI_ATTR_AUTH_HMAC_SHA1:
503 return SADB_AALG_SHA1HMAC;
504 case IPSECDOI_ATTR_AUTH_HMAC_SHA2_256:
505 #if (defined SADB_X_AALG_SHA2_256) && !defined(SADB_X_AALG_SHA2_256HMAC)
506 return SADB_X_AALG_SHA2_256;
507 #else
508 return SADB_X_AALG_SHA2_256HMAC;
509 #endif
510 case IPSECDOI_ATTR_AUTH_HMAC_SHA2_384:
511 #if (defined SADB_X_AALG_SHA2_384) && !defined(SADB_X_AALG_SHA2_384HMAC)
512 return SADB_X_AALG_SHA2_384;
513 #else
514 return SADB_X_AALG_SHA2_384HMAC;
515 #endif
516 case IPSECDOI_ATTR_AUTH_HMAC_SHA2_512:
517 #if (defined SADB_X_AALG_SHA2_512) && !defined(SADB_X_AALG_SHA2_512HMAC)
518 return SADB_X_AALG_SHA2_512;
519 #else
520 return SADB_X_AALG_SHA2_512HMAC;
521 #endif
522 case IPSECDOI_ATTR_AUTH_KPDK: /* need special care */
523 return SADB_AALG_NONE;
524
525 /* not supported */
526 case IPSECDOI_ATTR_AUTH_DES_MAC:
527 plog(LLV_ERROR, LOCATION, NULL,
528 "Not supported hash type: %u\n", hashtype);
529 return ~0;
530
531 case 0: /* reserved */
532 default:
533 return SADB_AALG_NONE;
534
535 plog(LLV_ERROR, LOCATION, NULL,
536 "Invalid hash type: %u\n", hashtype);
537 return ~0;
538 }
539 /*NOTREACHED*/
540 }
541
542 /* IPSECDOI_ESP -> SADB_EALG */
543 static u_int
544 ipsecdoi2pfkey_ealg(t_id)
545 u_int t_id;
546 {
547 switch (t_id) {
548 case IPSECDOI_ESP_DES_IV64: /* sa_flags |= SADB_X_EXT_OLD */
549 return SADB_EALG_DESCBC;
550 case IPSECDOI_ESP_DES:
551 return SADB_EALG_DESCBC;
552 case IPSECDOI_ESP_3DES:
553 return SADB_EALG_3DESCBC;
554 #ifdef SADB_X_EALG_RC5CBC
555 case IPSECDOI_ESP_RC5:
556 return SADB_X_EALG_RC5CBC;
557 #endif
558 case IPSECDOI_ESP_CAST:
559 return SADB_X_EALG_CAST128CBC;
560 case IPSECDOI_ESP_BLOWFISH:
561 return SADB_X_EALG_BLOWFISHCBC;
562 case IPSECDOI_ESP_DES_IV32: /* flags |= (SADB_X_EXT_OLD|
563 SADB_X_EXT_IV4B)*/
564 return SADB_EALG_DESCBC;
565 case IPSECDOI_ESP_NULL:
566 return SADB_EALG_NULL;
567 #ifdef SADB_X_EALG_AESCBC
568 case IPSECDOI_ESP_AES:
569 return SADB_X_EALG_AESCBC;
570 #endif
571 #ifdef SADB_X_EALG_TWOFISHCBC
572 case IPSECDOI_ESP_TWOFISH:
573 return SADB_X_EALG_TWOFISHCBC;
574 #endif
575
576 /* not supported */
577 case IPSECDOI_ESP_3IDEA:
578 case IPSECDOI_ESP_IDEA:
579 case IPSECDOI_ESP_RC4:
580 plog(LLV_ERROR, LOCATION, NULL,
581 "Not supported transform: %u\n", t_id);
582 return ~0;
583
584 case 0: /* reserved */
585 default:
586 plog(LLV_ERROR, LOCATION, NULL,
587 "Invalid transform id: %u\n", t_id);
588 return ~0;
589 }
590 /*NOTREACHED*/
591 }
592
593 /* IPCOMP -> SADB_CALG */
594 static u_int
595 ipsecdoi2pfkey_calg(t_id)
596 u_int t_id;
597 {
598 switch (t_id) {
599 case IPSECDOI_IPCOMP_OUI:
600 return SADB_X_CALG_OUI;
601 case IPSECDOI_IPCOMP_DEFLATE:
602 return SADB_X_CALG_DEFLATE;
603 case IPSECDOI_IPCOMP_LZS:
604 return SADB_X_CALG_LZS;
605
606 case 0: /* reserved */
607 default:
608 plog(LLV_ERROR, LOCATION, NULL,
609 "Invalid transform id: %u\n", t_id);
610 return ~0;
611 }
612 /*NOTREACHED*/
613 }
614
615 /* IPSECDOI_PROTO -> SADB_SATYPE */
616 u_int
617 ipsecdoi2pfkey_proto(proto)
618 u_int proto;
619 {
620 switch (proto) {
621 case IPSECDOI_PROTO_IPSEC_AH:
622 return SADB_SATYPE_AH;
623 case IPSECDOI_PROTO_IPSEC_ESP:
624 return SADB_SATYPE_ESP;
625 case IPSECDOI_PROTO_IPCOMP:
626 return SADB_X_SATYPE_IPCOMP;
627
628 default:
629 plog(LLV_ERROR, LOCATION, NULL,
630 "Invalid ipsec_doi proto: %u\n", proto);
631 return ~0;
632 }
633 /*NOTREACHED*/
634 }
635
636 static u_int
637 ipsecdoi2pfkey_alg(algclass, type)
638 u_int algclass, type;
639 {
640 switch (algclass) {
641 case IPSECDOI_ATTR_AUTH:
642 return ipsecdoi2pfkey_aalg(type);
643 case IPSECDOI_PROTO_IPSEC_ESP:
644 return ipsecdoi2pfkey_ealg(type);
645 case IPSECDOI_PROTO_IPCOMP:
646 return ipsecdoi2pfkey_calg(type);
647 default:
648 plog(LLV_ERROR, LOCATION, NULL,
649 "Invalid ipsec_doi algclass: %u\n", algclass);
650 return ~0;
651 }
652 /*NOTREACHED*/
653 }
654
655 /* SADB_SATYPE -> IPSECDOI_PROTO */
656 u_int
657 pfkey2ipsecdoi_proto(satype)
658 u_int satype;
659 {
660 switch (satype) {
661 case SADB_SATYPE_AH:
662 return IPSECDOI_PROTO_IPSEC_AH;
663 case SADB_SATYPE_ESP:
664 return IPSECDOI_PROTO_IPSEC_ESP;
665 case SADB_X_SATYPE_IPCOMP:
666 return IPSECDOI_PROTO_IPCOMP;
667
668 default:
669 plog(LLV_ERROR, LOCATION, NULL,
670 "Invalid pfkey proto: %u\n", satype);
671 return ~0;
672 }
673 /*NOTREACHED*/
674 }
675
676 /* IPSECDOI_ATTR_ENC_MODE -> IPSEC_MODE */
677 u_int
678 ipsecdoi2pfkey_mode(mode)
679 u_int mode;
680 {
681 switch (mode) {
682 case IPSECDOI_ATTR_ENC_MODE_TUNNEL:
683 #ifdef ENABLE_NATT
684 case IPSECDOI_ATTR_ENC_MODE_UDPTUNNEL_RFC:
685 case IPSECDOI_ATTR_ENC_MODE_UDPTUNNEL_DRAFT:
686 #endif
687 return IPSEC_MODE_TUNNEL;
688 case IPSECDOI_ATTR_ENC_MODE_TRNS:
689 #ifdef ENABLE_NATT
690 case IPSECDOI_ATTR_ENC_MODE_UDPTRNS_RFC:
691 case IPSECDOI_ATTR_ENC_MODE_UDPTRNS_DRAFT:
692 #endif
693 return IPSEC_MODE_TRANSPORT;
694 default:
695 plog(LLV_ERROR, LOCATION, NULL, "Invalid mode type: %u\n", mode);
696 return ~0;
697 }
698 /*NOTREACHED*/
699 }
700
701 /* IPSECDOI_ATTR_ENC_MODE -> IPSEC_MODE */
702 u_int
703 pfkey2ipsecdoi_mode(mode)
704 u_int mode;
705 {
706 switch (mode) {
707 case IPSEC_MODE_TUNNEL:
708 return IPSECDOI_ATTR_ENC_MODE_TUNNEL;
709 case IPSEC_MODE_TRANSPORT:
710 return IPSECDOI_ATTR_ENC_MODE_TRNS;
711 case IPSEC_MODE_ANY:
712 return IPSECDOI_ATTR_ENC_MODE_ANY;
713 default:
714 plog(LLV_ERROR, LOCATION, NULL, "Invalid mode type: %u\n", mode);
715 return ~0;
716 }
717 /*NOTREACHED*/
718 }
719
720 /* default key length for encryption algorithm */
721 static u_int
722 keylen_aalg(hashtype)
723 u_int hashtype;
724 {
725 int res;
726
727 if (hashtype == 0)
728 return SADB_AALG_NONE;
729
730 res = alg_ipsec_hmacdef_hashlen(hashtype);
731 if (res == -1) {
732 plog(LLV_ERROR, LOCATION, NULL,
733 "invalid hmac algorithm %u.\n", hashtype);
734 return ~0;
735 }
736 return res;
737 }
738
739 /* default key length for encryption algorithm */
740 static u_int
741 keylen_ealg(enctype, encklen)
742 u_int enctype;
743 int encklen;
744 {
745 int res;
746
747 res = alg_ipsec_encdef_keylen(enctype, encklen);
748 if (res == -1) {
749 plog(LLV_ERROR, LOCATION, NULL,
750 "invalid encryption algorithm %u.\n", enctype);
751 return ~0;
752 }
753 return res;
754 }
755
756 int
757 pfkey_convertfromipsecdoi(proto_id, t_id, hashtype,
758 e_type, e_keylen, a_type, a_keylen, flags)
759 u_int proto_id;
760 u_int t_id;
761 u_int hashtype;
762 u_int *e_type;
763 u_int *e_keylen;
764 u_int *a_type;
765 u_int *a_keylen;
766 u_int *flags;
767 {
768 *flags = 0;
769 switch (proto_id) {
770 case IPSECDOI_PROTO_IPSEC_ESP:
771 if ((*e_type = ipsecdoi2pfkey_ealg(t_id)) == ~0)
772 goto bad;
773 if ((*e_keylen = keylen_ealg(t_id, *e_keylen)) == ~0)
774 goto bad;
775 *e_keylen >>= 3;
776
777 if ((*a_type = ipsecdoi2pfkey_aalg(hashtype)) == ~0)
778 goto bad;
779 if ((*a_keylen = keylen_aalg(hashtype)) == ~0)
780 goto bad;
781 *a_keylen >>= 3;
782
783 if (*e_type == SADB_EALG_NONE) {
784 plog(LLV_ERROR, LOCATION, NULL, "no ESP algorithm.\n");
785 goto bad;
786 }
787 break;
788
789 case IPSECDOI_PROTO_IPSEC_AH:
790 if ((*a_type = ipsecdoi2pfkey_aalg(hashtype)) == ~0)
791 goto bad;
792 if ((*a_keylen = keylen_aalg(hashtype)) == ~0)
793 goto bad;
794 *a_keylen >>= 3;
795
796 if (t_id == IPSECDOI_ATTR_AUTH_HMAC_MD5
797 && hashtype == IPSECDOI_ATTR_AUTH_KPDK) {
798 /* AH_MD5 + Auth(KPDK) = RFC1826 keyed-MD5 */
799 *a_type = SADB_X_AALG_MD5;
800 *flags |= SADB_X_EXT_OLD;
801 }
802 *e_type = SADB_EALG_NONE;
803 *e_keylen = 0;
804 if (*a_type == SADB_AALG_NONE) {
805 plog(LLV_ERROR, LOCATION, NULL, "no AH algorithm.\n");
806 goto bad;
807 }
808 break;
809
810 case IPSECDOI_PROTO_IPCOMP:
811 if ((*e_type = ipsecdoi2pfkey_calg(t_id)) == ~0)
812 goto bad;
813 *e_keylen = 0;
814
815 *flags = SADB_X_EXT_RAWCPI;
816
817 *a_type = SADB_AALG_NONE;
818 *a_keylen = 0;
819 if (*e_type == SADB_X_CALG_NONE) {
820 plog(LLV_ERROR, LOCATION, NULL, "no IPCOMP algorithm.\n");
821 goto bad;
822 }
823 break;
824
825 default:
826 plog(LLV_ERROR, LOCATION, NULL, "unknown IPsec protocol.\n");
827 goto bad;
828 }
829
830 return 0;
831
832 bad:
833 errno = EINVAL;
834 return -1;
835 }
836
837 /* called from scheduler */
838 void
839 pfkey_timeover_stub(p)
840 void *p;
841 {
842
843 pfkey_timeover((struct ph2handle *)p);
844 }
845
846 void
847 pfkey_timeover(iph2)
848 struct ph2handle *iph2;
849 {
850 plog(LLV_ERROR, LOCATION, NULL,
851 "%s give up to get IPsec-SA due to time up to wait.\n",
852 saddrwop2str(iph2->dst));
853 SCHED_KILL(iph2->sce);
854
855 /* If initiator side, send error to kernel by SADB_ACQUIRE. */
856 if (iph2->side == INITIATOR)
857 pk_sendeacquire(iph2);
858
859 unbindph12(iph2);
860 remph2(iph2);
861 delph2(iph2);
862
863 return;
864 }
865
866 /*%%%*/
867 /* send getspi message per ipsec protocol per remote address */
868 /*
869 * the local address and remote address in ph1handle are dealed
870 * with destination address and source address respectively.
871 * Because SPI is decided by responder.
872 */
873 int
874 pk_sendgetspi(iph2)
875 struct ph2handle *iph2;
876 {
877 struct sockaddr *src = NULL, *dst = NULL;
878 u_int satype, mode;
879 struct saprop *pp;
880 struct saproto *pr;
881 u_int32_t minspi, maxspi;
882 int proxy = 0;
883
884 if (iph2->side == INITIATOR) {
885 pp = iph2->proposal;
886 proxy = iph2->ph1->rmconf->support_proxy;
887 } else {
888 pp = iph2->approval;
889 if (iph2->sainfo && iph2->sainfo->id_i)
890 proxy = 1;
891 }
892
893 /* for mobile IPv6 */
894 if (proxy && iph2->src_id && iph2->dst_id &&
895 ipsecdoi_transportmode(pp)) {
896 src = iph2->src_id;
897 dst = iph2->dst_id;
898 } else {
899 src = iph2->src;
900 dst = iph2->dst;
901 }
902
903 for (pr = pp->head; pr != NULL; pr = pr->next) {
904
905 /* validity check */
906 satype = ipsecdoi2pfkey_proto(pr->proto_id);
907 if (satype == ~0) {
908 plog(LLV_ERROR, LOCATION, NULL,
909 "invalid proto_id %d\n", pr->proto_id);
910 return -1;
911 }
912 /* this works around a bug in Linux kernel where it allocates 4 byte
913 spi's for IPCOMP */
914 else if (satype == SADB_X_SATYPE_IPCOMP) {
915 minspi = 0x100;
916 maxspi = 0xffff;
917 }
918 else {
919 minspi = 0;
920 maxspi = 0;
921 }
922 mode = ipsecdoi2pfkey_mode(pr->encmode);
923 if (mode == ~0) {
924 plog(LLV_ERROR, LOCATION, NULL,
925 "invalid encmode %d\n", pr->encmode);
926 return -1;
927 }
928
929 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_getspi\n");
930 if (pfkey_send_getspi(
931 lcconf->sock_pfkey,
932 satype,
933 mode,
934 dst, /* src of SA */
935 src, /* dst of SA */
936 minspi, maxspi,
937 pr->reqid_in, iph2->seq) < 0) {
938 plog(LLV_ERROR, LOCATION, NULL,
939 "ipseclib failed send getspi (%s)\n",
940 ipsec_strerror());
941 return -1;
942 }
943 plog(LLV_DEBUG, LOCATION, NULL,
944 "pfkey GETSPI sent: %s\n",
945 sadbsecas2str(dst, src, satype, 0, mode));
946 }
947
948 return 0;
949 }
950
951 /*
952 * receive GETSPI from kernel.
953 */
954 static int
955 pk_recvgetspi(mhp)
956 caddr_t *mhp;
957 {
958 struct sadb_msg *msg;
959 struct sadb_sa *sa;
960 struct ph2handle *iph2;
961 struct sockaddr *dst;
962 int proto_id;
963 int allspiok, notfound;
964 struct saprop *pp;
965 struct saproto *pr;
966
967 /* validity check */
968 if (mhp[SADB_EXT_SA] == NULL
969 || mhp[SADB_EXT_ADDRESS_DST] == NULL) {
970 plog(LLV_ERROR, LOCATION, NULL,
971 "inappropriate sadb getspi message passed.\n");
972 return -1;
973 }
974 msg = (struct sadb_msg *)mhp[0];
975 sa = (struct sadb_sa *)mhp[SADB_EXT_SA];
976 dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); /* note SA dir */
977
978 /* the message has to be processed or not ? */
979 if (msg->sadb_msg_pid != getpid()) {
980 plog(LLV_DEBUG, LOCATION, NULL,
981 "%s message is not interesting "
982 "because pid %d is not mine.\n",
983 s_pfkey_type(msg->sadb_msg_type),
984 msg->sadb_msg_pid);
985 return -1;
986 }
987
988 iph2 = getph2byseq(msg->sadb_msg_seq);
989 if (iph2 == NULL) {
990 plog(LLV_DEBUG, LOCATION, NULL,
991 "seq %d of %s message not interesting.\n",
992 msg->sadb_msg_seq,
993 s_pfkey_type(msg->sadb_msg_type));
994 return -1;
995 }
996
997 if (iph2->status != PHASE2ST_GETSPISENT) {
998 plog(LLV_ERROR, LOCATION, NULL,
999 "status mismatch (db:%d msg:%d)\n",
1000 iph2->status, PHASE2ST_GETSPISENT);
1001 return -1;
1002 }
1003
1004 /* set SPI, and check to get all spi whether or not */
1005 allspiok = 1;
1006 notfound = 1;
1007 proto_id = pfkey2ipsecdoi_proto(msg->sadb_msg_satype);
1008 pp = iph2->side == INITIATOR ? iph2->proposal : iph2->approval;
1009
1010 for (pr = pp->head; pr != NULL; pr = pr->next) {
1011 if (pr->proto_id == proto_id && pr->spi == 0) {
1012 pr->spi = sa->sadb_sa_spi;
1013 notfound = 0;
1014 plog(LLV_DEBUG, LOCATION, NULL,
1015 "pfkey GETSPI succeeded: %s\n",
1016 sadbsecas2str(iph2->dst, iph2->src,
1017 msg->sadb_msg_satype,
1018 sa->sadb_sa_spi,
1019 ipsecdoi2pfkey_mode(pr->encmode)));
1020 }
1021 if (pr->spi == 0)
1022 allspiok = 0; /* not get all spi */
1023 }
1024
1025 if (notfound) {
1026 plog(LLV_ERROR, LOCATION, NULL,
1027 "get spi for unknown address %s\n",
1028 saddrwop2str(iph2->dst));
1029 return -1;
1030 }
1031
1032 if (allspiok) {
1033 /* update status */
1034 iph2->status = PHASE2ST_GETSPIDONE;
1035 if (isakmp_post_getspi(iph2) < 0) {
1036 plog(LLV_ERROR, LOCATION, NULL,
1037 "failed to start post getspi.\n");
1038 unbindph12(iph2);
1039 remph2(iph2);
1040 delph2(iph2);
1041 iph2 = NULL;
1042 return -1;
1043 }
1044 }
1045
1046 return 0;
1047 }
1048
1049 /*
1050 * set inbound SA
1051 */
1052 int
1053 pk_sendupdate(iph2)
1054 struct ph2handle *iph2;
1055 {
1056 struct saproto *pr;
1057 struct sockaddr *src = NULL, *dst = NULL;
1058 u_int e_type, e_keylen, a_type, a_keylen, flags;
1059 u_int satype, mode;
1060 u_int64_t lifebyte = 0;
1061 u_int wsize = 4; /* XXX static size of window */
1062 int proxy = 0;
1063 struct ph2natt natt;
1064
1065 /* sanity check */
1066 if (iph2->approval == NULL) {
1067 plog(LLV_ERROR, LOCATION, NULL,
1068 "no approvaled SAs found.\n");
1069 }
1070
1071 if (iph2->side == INITIATOR)
1072 proxy = iph2->ph1->rmconf->support_proxy;
1073 else if (iph2->sainfo && iph2->sainfo->id_i)
1074 proxy = 1;
1075
1076 /* for mobile IPv6 */
1077 if (proxy && iph2->src_id && iph2->dst_id &&
1078 ipsecdoi_transportmode(iph2->approval)) {
1079 src = iph2->src_id;
1080 dst = iph2->dst_id;
1081 } else {
1082 src = iph2->src;
1083 dst = iph2->dst;
1084 }
1085
1086 for (pr = iph2->approval->head; pr != NULL; pr = pr->next) {
1087 /* validity check */
1088 satype = ipsecdoi2pfkey_proto(pr->proto_id);
1089 if (satype == ~0) {
1090 plog(LLV_ERROR, LOCATION, NULL,
1091 "invalid proto_id %d\n", pr->proto_id);
1092 return -1;
1093 }
1094 else if (satype == SADB_X_SATYPE_IPCOMP) {
1095 /* IPCOMP has no replay window */
1096 wsize = 0;
1097 }
1098 #ifdef ENABLE_SAMODE_UNSPECIFIED
1099 mode = IPSEC_MODE_ANY;
1100 #else
1101 mode = ipsecdoi2pfkey_mode(pr->encmode);
1102 if (mode == ~0) {
1103 plog(LLV_ERROR, LOCATION, NULL,
1104 "invalid encmode %d\n", pr->encmode);
1105 return -1;
1106 }
1107 #endif
1108
1109 /* set algorithm type and key length */
1110 e_keylen = pr->head->encklen;
1111 if (pfkey_convertfromipsecdoi(
1112 pr->proto_id,
1113 pr->head->trns_id,
1114 pr->head->authtype,
1115 &e_type, &e_keylen,
1116 &a_type, &a_keylen, &flags) < 0)
1117 return -1;
1118
1119 #if 0
1120 lifebyte = iph2->approval->lifebyte * 1024,
1121 #else
1122 lifebyte = 0;
1123 #endif
1124
1125 #ifdef __APPLE__
1126 #ifdef ENABLE_NATT
1127 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_update\n");
1128 if (pr->udp_encap) {
1129 memset (&natt, 0, sizeof (natt));
1130 natt.sport = extract_port (iph2->ph1->remote);
1131 flags |= SADB_X_EXT_NATT;
1132 if (iph2->ph1->natt_flags & NAT_DETECTED_ME)
1133 flags |= SADB_X_EXT_NATT_KEEPALIVE;
1134 else if (iph2->ph1->rmconf->natt_multiple_user == TRUE &&
1135 mode == IPSEC_MODE_TRANSPORT &&
1136 src->sa_family == AF_INET)
1137 flags |= SADB_X_EXT_NATT_MULTIPLEUSERS;
1138 } else {
1139 memset (&natt, 0, sizeof (natt));
1140 }
1141
1142 if (pfkey_send_update(
1143 lcconf->sock_pfkey,
1144 satype,
1145 mode,
1146 dst,
1147 src,
1148 pr->spi,
1149 pr->reqid_in,
1150 wsize,
1151 pr->keymat->v,
1152 e_type, e_keylen, a_type, a_keylen, flags,
1153 0, lifebyte, iph2->approval->lifetime, 0,
1154 iph2->seq, natt.sport) < 0) {
1155 plog(LLV_ERROR, LOCATION, NULL,
1156 "libipsec failed send update (%s)\n",
1157 ipsec_strerror());
1158 return -1;
1159 }
1160 #else
1161 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_update\n");
1162 if (pfkey_send_update(
1163 lcconf->sock_pfkey,
1164 satype,
1165 mode,
1166 dst,
1167 src,
1168 pr->spi,
1169 pr->reqid_in,
1170 wsize,
1171 pr->keymat->v,
1172 e_type, e_keylen, a_type, a_keylen, flags,
1173 0, lifebyte, iph2->approval->lifetime, 0,
1174 iph2->seq, 0) < 0) {
1175 plog(LLV_ERROR, LOCATION, NULL,
1176 "libipsec failed send update (%s)\n",
1177 ipsec_strerror());
1178 return -1;
1179 }
1180 #endif /* ENABLE_NATT */
1181 #else
1182 #ifdef ENABLE_NATT
1183 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_update_nat\n");
1184 if (pr->udp_encap) {
1185 memset (&natt, 0, sizeof (natt));
1186 natt.type = iph2->ph1->natt_options->encaps_type;
1187 natt.sport = extract_port (iph2->ph1->remote);
1188 natt.dport = extract_port (iph2->ph1->local);
1189 natt.oa = NULL; // FIXME: Here comes OA!!!
1190 natt.frag = iph2->ph1->rmconf->esp_frag;
1191 } else {
1192 memset (&natt, 0, sizeof (natt));
1193 }
1194
1195 if (pfkey_send_update_nat(
1196 lcconf->sock_pfkey,
1197 satype,
1198 mode,
1199 dst,
1200 src,
1201 pr->spi,
1202 pr->reqid_in,
1203 wsize,
1204 pr->keymat->v,
1205 e_type, e_keylen, a_type, a_keylen, flags,
1206 0, lifebyte, iph2->approval->lifetime, 0,
1207 iph2->seq,
1208 natt.type, natt.sport, natt.dport, natt.oa,
1209 natt.frag) < 0) {
1210 plog(LLV_ERROR, LOCATION, NULL,
1211 "libipsec failed send update_nat (%s)\n",
1212 ipsec_strerror());
1213 return -1;
1214 }
1215 #else
1216 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_update\n");
1217 if (pfkey_send_update(
1218 lcconf->sock_pfkey,
1219 satype,
1220 mode,
1221 dst,
1222 src,
1223 pr->spi,
1224 pr->reqid_in,
1225 wsize,
1226 pr->keymat->v,
1227 e_type, e_keylen, a_type, a_keylen, flags,
1228 0, lifebyte, iph2->approval->lifetime, 0,
1229 iph2->seq) < 0) {
1230 plog(LLV_ERROR, LOCATION, NULL,
1231 "libipsec failed send update (%s)\n",
1232 ipsec_strerror());
1233 return -1;
1234 }
1235 #endif /* ENABLE_NATT */
1236 #endif /* __APPLE__ */
1237
1238 if (!lcconf->pathinfo[LC_PATHTYPE_BACKUPSA])
1239 continue;
1240
1241 /*
1242 * It maybe good idea to call backupsa_to_file() after
1243 * racoon will receive the sadb_update messages.
1244 * But it is impossible because there is not key in the
1245 * information from the kernel.
1246 */
1247 if (backupsa_to_file(satype, mode, dst, src,
1248 pr->spi, pr->reqid_in, 4,
1249 pr->keymat->v,
1250 e_type, e_keylen, a_type, a_keylen, flags,
1251 0, iph2->approval->lifebyte * 1024,
1252 iph2->approval->lifetime, 0,
1253 iph2->seq) < 0) {
1254 plog(LLV_ERROR, LOCATION, NULL,
1255 "backuped SA failed: %s\n",
1256 sadbsecas2str(dst, src,
1257 satype, pr->spi, mode));
1258 }
1259 plog(LLV_DEBUG, LOCATION, NULL,
1260 "backuped SA: %s\n",
1261 sadbsecas2str(dst, src,
1262 satype, pr->spi, mode));
1263 }
1264
1265 return 0;
1266 }
1267
1268 static int
1269 pk_recvupdate(mhp)
1270 caddr_t *mhp;
1271 {
1272 struct sadb_msg *msg;
1273 struct sadb_sa *sa;
1274 struct sockaddr *src, *dst;
1275 struct ph2handle *iph2;
1276 u_int proto_id, encmode, sa_mode;
1277 int incomplete = 0;
1278 struct saproto *pr;
1279
1280 /* ignore this message because of local test mode. */
1281 if (f_local)
1282 return 0;
1283
1284 /* sanity check */
1285 if (mhp[0] == NULL
1286 || mhp[SADB_EXT_SA] == NULL
1287 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
1288 || mhp[SADB_EXT_ADDRESS_DST] == NULL) {
1289 plog(LLV_ERROR, LOCATION, NULL,
1290 "inappropriate sadb update message passed.\n");
1291 return -1;
1292 }
1293 msg = (struct sadb_msg *)mhp[0];
1294 src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]);
1295 dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]);
1296 sa = (struct sadb_sa *)mhp[SADB_EXT_SA];
1297
1298 sa_mode = mhp[SADB_X_EXT_SA2] == NULL
1299 ? IPSEC_MODE_ANY
1300 : ((struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode;
1301
1302 /* the message has to be processed or not ? */
1303 if (msg->sadb_msg_pid != getpid()) {
1304 plog(LLV_DEBUG, LOCATION, NULL,
1305 "%s message is not interesting "
1306 "because pid %d is not mine.\n",
1307 s_pfkey_type(msg->sadb_msg_type),
1308 msg->sadb_msg_pid);
1309 return -1;
1310 }
1311
1312 iph2 = getph2byseq(msg->sadb_msg_seq);
1313 if (iph2 == NULL) {
1314 plog(LLV_DEBUG, LOCATION, NULL,
1315 "seq %d of %s message not interesting.\n",
1316 msg->sadb_msg_seq,
1317 s_pfkey_type(msg->sadb_msg_type));
1318 return -1;
1319 }
1320
1321 if (iph2->status != PHASE2ST_ADDSA) {
1322 plog(LLV_ERROR, LOCATION, NULL,
1323 "status mismatch (db:%d msg:%d)\n",
1324 iph2->status, PHASE2ST_ADDSA);
1325 return -1;
1326 }
1327
1328 /* check to complete all keys ? */
1329 for (pr = iph2->approval->head; pr != NULL; pr = pr->next) {
1330 proto_id = pfkey2ipsecdoi_proto(msg->sadb_msg_satype);
1331 if (proto_id == ~0) {
1332 plog(LLV_ERROR, LOCATION, NULL,
1333 "invalid proto_id %d\n", msg->sadb_msg_satype);
1334 return -1;
1335 }
1336 encmode = pfkey2ipsecdoi_mode(sa_mode);
1337 if (encmode == ~0) {
1338 plog(LLV_ERROR, LOCATION, NULL,
1339 "invalid encmode %d\n", sa_mode);
1340 return -1;
1341 }
1342
1343 if (pr->proto_id == proto_id
1344 && pr->spi == sa->sadb_sa_spi) {
1345 pr->ok = 1;
1346 plog(LLV_DEBUG, LOCATION, NULL,
1347 "pfkey UPDATE succeeded: %s\n",
1348 sadbsecas2str(iph2->dst, iph2->src,
1349 msg->sadb_msg_satype,
1350 sa->sadb_sa_spi,
1351 sa_mode));
1352
1353 plog(LLV_INFO, LOCATION, NULL,
1354 "IPsec-SA established: %s\n",
1355 sadbsecas2str(iph2->dst, iph2->src,
1356 msg->sadb_msg_satype, sa->sadb_sa_spi,
1357 sa_mode));
1358 }
1359
1360 if (pr->ok == 0)
1361 incomplete = 1;
1362 }
1363
1364 if (incomplete)
1365 return 0;
1366
1367 /* turn off the timer for calling pfkey_timeover() */
1368 SCHED_KILL(iph2->sce);
1369
1370 /* update status */
1371 iph2->status = PHASE2ST_ESTABLISHED;
1372
1373 #ifdef ENABLE_STATS
1374 gettimeofday(&iph2->end, NULL);
1375 syslog(LOG_NOTICE, "%s(%s): %8.6f",
1376 "phase2", "quick", timedelta(&iph2->start, &iph2->end));
1377 #endif
1378
1379 /* count up */
1380 iph2->ph1->ph2cnt++;
1381
1382 /* turn off schedule */
1383 if (iph2->scr)
1384 SCHED_KILL(iph2->scr);
1385
1386 /*
1387 * since we are going to reuse the phase2 handler, we need to
1388 * remain it and refresh all the references between ph1 and ph2 to use.
1389 */
1390 unbindph12(iph2);
1391
1392 iph2->sce = sched_new(iph2->approval->lifetime,
1393 isakmp_ph2expire_stub, iph2);
1394
1395 plog(LLV_DEBUG, LOCATION, NULL, "===\n");
1396 return 0;
1397 }
1398
1399 /*
1400 * set outbound SA
1401 */
1402 int
1403 pk_sendadd(iph2)
1404 struct ph2handle *iph2;
1405 {
1406 struct saproto *pr;
1407 struct sockaddr *src = NULL, *dst = NULL;
1408 u_int e_type, e_keylen, a_type, a_keylen, flags;
1409 u_int satype, mode;
1410 u_int64_t lifebyte = 0;
1411 u_int wsize = 4; /* XXX static size of window */
1412 int proxy = 0;
1413 struct ph2natt natt;
1414
1415 /* sanity check */
1416 if (iph2->approval == NULL) {
1417 plog(LLV_ERROR, LOCATION, NULL,
1418 "no approvaled SAs found.\n");
1419 }
1420
1421 if (iph2->side == INITIATOR)
1422 proxy = iph2->ph1->rmconf->support_proxy;
1423 else if (iph2->sainfo && iph2->sainfo->id_i)
1424 proxy = 1;
1425
1426 /* for mobile IPv6 */
1427 if (proxy && iph2->src_id && iph2->dst_id &&
1428 ipsecdoi_transportmode(iph2->approval)) {
1429 src = iph2->src_id;
1430 dst = iph2->dst_id;
1431 } else {
1432 src = iph2->src;
1433 dst = iph2->dst;
1434 }
1435
1436 for (pr = iph2->approval->head; pr != NULL; pr = pr->next) {
1437 /* validity check */
1438 satype = ipsecdoi2pfkey_proto(pr->proto_id);
1439 if (satype == ~0) {
1440 plog(LLV_ERROR, LOCATION, NULL,
1441 "invalid proto_id %d\n", pr->proto_id);
1442 return -1;
1443 }
1444 else if (satype == SADB_X_SATYPE_IPCOMP) {
1445 /* no replay window for IPCOMP */
1446 wsize = 0;
1447 }
1448 #ifdef ENABLE_SAMODE_UNSPECIFIED
1449 mode = IPSEC_MODE_ANY;
1450 #else
1451 mode = ipsecdoi2pfkey_mode(pr->encmode);
1452 if (mode == ~0) {
1453 plog(LLV_ERROR, LOCATION, NULL,
1454 "invalid encmode %d\n", pr->encmode);
1455 return -1;
1456 }
1457 #endif
1458
1459 /* set algorithm type and key length */
1460 e_keylen = pr->head->encklen;
1461 if (pfkey_convertfromipsecdoi(
1462 pr->proto_id,
1463 pr->head->trns_id,
1464 pr->head->authtype,
1465 &e_type, &e_keylen,
1466 &a_type, &a_keylen, &flags) < 0)
1467 return -1;
1468
1469 #if 0
1470 lifebyte = iph2->approval->lifebyte * 1024,
1471 #else
1472 lifebyte = 0;
1473 #endif
1474
1475 #ifdef __APPLE__
1476 #ifdef ENABLE_NATT
1477 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_add\n");
1478
1479 if (pr->udp_encap) {
1480 memset (&natt, 0, sizeof (natt));
1481 natt.dport = extract_port (iph2->ph1->remote);
1482 flags |= SADB_X_EXT_NATT;
1483 if (iph2->ph1->natt_flags & NAT_DETECTED_ME)
1484 flags |= SADB_X_EXT_NATT_KEEPALIVE;
1485 else if (iph2->ph1->rmconf->natt_multiple_user == TRUE &&
1486 mode == IPSEC_MODE_TRANSPORT &&
1487 dst->sa_family == AF_INET)
1488 flags |= SADB_X_EXT_NATT_MULTIPLEUSERS;
1489 } else {
1490 memset (&natt, 0, sizeof (natt));
1491
1492 /* Remove port information, that SA doesn't use it */
1493 //set_port(src, 0);
1494 //set_port(dst, 0);
1495 }
1496
1497 if (pfkey_send_add(
1498 lcconf->sock_pfkey,
1499 satype,
1500 mode,
1501 src,
1502 dst,
1503 pr->spi_p,
1504 pr->reqid_out,
1505 wsize,
1506 pr->keymat_p->v,
1507 e_type, e_keylen, a_type, a_keylen, flags,
1508 0, lifebyte, iph2->approval->lifetime, 0,
1509 iph2->seq,natt.dport) < 0) {
1510 plog(LLV_ERROR, LOCATION, NULL,
1511 "libipsec failed send add (%s)\n",
1512 ipsec_strerror());
1513 return -1;
1514 }
1515 #else
1516 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_add\n");
1517
1518 /* Remove port information, it is not used without NAT-T */
1519 //set_port(src, 0);
1520 //set_port(dst, 0);
1521
1522 if (pfkey_send_add(
1523 lcconf->sock_pfkey,
1524 satype,
1525 mode,
1526 src,
1527 dst,
1528 pr->spi_p,
1529 pr->reqid_out,
1530 wsize,
1531 pr->keymat_p->v,
1532 e_type, e_keylen, a_type, a_keylen, flags,
1533 0, lifebyte, iph2->approval->lifetime, 0,
1534 iph2->seq, 0) < 0) {
1535 plog(LLV_ERROR, LOCATION, NULL,
1536 "libipsec failed send add (%s)\n",
1537 ipsec_strerror());
1538 return -1;
1539 }
1540 #endif /* ENABLE_NATT */
1541 #else /* __APPLE__ */
1542 #ifdef ENABLE_NATT
1543 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_add_nat\n");
1544
1545 if (pr->udp_encap) {
1546 memset (&natt, 0, sizeof (natt));
1547 natt.type = UDP_ENCAP_ESPINUDP;
1548 natt.sport = extract_port (iph2->ph1->local);
1549 natt.dport = extract_port (iph2->ph1->remote);
1550 natt.oa = NULL; // FIXME: Here comes OA!!!
1551 natt.frag = iph2->ph1->rmconf->esp_frag;
1552 } else {
1553 memset (&natt, 0, sizeof (natt));
1554
1555 /* Remove port information, that SA doesn't use it */
1556 set_port(src, 0);
1557 set_port(dst, 0);
1558 }
1559
1560 if (pfkey_send_add_nat(
1561 lcconf->sock_pfkey,
1562 satype,
1563 mode,
1564 src,
1565 dst,
1566 pr->spi_p,
1567 pr->reqid_out,
1568 wsize,
1569 pr->keymat_p->v,
1570 e_type, e_keylen, a_type, a_keylen, flags,
1571 0, lifebyte, iph2->approval->lifetime, 0,
1572 iph2->seq,
1573 natt.type, natt.sport, natt.dport, natt.oa,
1574 natt.frag) < 0) {
1575 plog(LLV_ERROR, LOCATION, NULL,
1576 "libipsec failed send add_nat (%s)\n",
1577 ipsec_strerror());
1578 return -1;
1579 }
1580 #else
1581 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_add\n");
1582
1583 /* Remove port information, it is not used without NAT-T */
1584 set_port(src, 0);
1585 set_port(dst, 0);
1586
1587 if (pfkey_send_add(
1588 lcconf->sock_pfkey,
1589 satype,
1590 mode,
1591 src,
1592 dst,
1593 pr->spi_p,
1594 pr->reqid_out,
1595 wsize,
1596 pr->keymat_p->v,
1597 e_type, e_keylen, a_type, a_keylen, flags,
1598 0, lifebyte, iph2->approval->lifetime, 0,
1599 iph2->seq) < 0) {
1600 plog(LLV_ERROR, LOCATION, NULL,
1601 "libipsec failed send add (%s)\n",
1602 ipsec_strerror());
1603 return -1;
1604 }
1605 #endif /* ENABLE_NATT */
1606 #endif /* __APPLE__ */
1607
1608 if (!lcconf->pathinfo[LC_PATHTYPE_BACKUPSA])
1609 continue;
1610
1611 /*
1612 * It maybe good idea to call backupsa_to_file() after
1613 * racoon will receive the sadb_update messages.
1614 * But it is impossible because there is not key in the
1615 * information from the kernel.
1616 */
1617 if (backupsa_to_file(satype, mode, src, dst,
1618 pr->spi_p, pr->reqid_out, 4,
1619 pr->keymat_p->v,
1620 e_type, e_keylen, a_type, a_keylen, flags,
1621 0, iph2->approval->lifebyte * 1024,
1622 iph2->approval->lifetime, 0,
1623 iph2->seq) < 0) {
1624 plog(LLV_ERROR, LOCATION, NULL,
1625 "backuped SA failed: %s\n",
1626 sadbsecas2str(src, dst,
1627 satype, pr->spi_p, mode));
1628 }
1629 plog(LLV_DEBUG, LOCATION, NULL,
1630 "backuped SA: %s\n",
1631 sadbsecas2str(src, dst,
1632 satype, pr->spi_p, mode));
1633 }
1634
1635 return 0;
1636 }
1637
1638 static int
1639 pk_recvadd(mhp)
1640 caddr_t *mhp;
1641 {
1642 struct sadb_msg *msg;
1643 struct sadb_sa *sa;
1644 struct sockaddr *src, *dst;
1645 struct ph2handle *iph2;
1646 u_int sa_mode;
1647
1648 /* ignore this message because of local test mode. */
1649 if (f_local)
1650 return 0;
1651
1652 /* sanity check */
1653 if (mhp[0] == NULL
1654 || mhp[SADB_EXT_SA] == NULL
1655 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
1656 || mhp[SADB_EXT_ADDRESS_DST] == NULL) {
1657 plog(LLV_ERROR, LOCATION, NULL,
1658 "inappropriate sadb add message passed.\n");
1659 return -1;
1660 }
1661 msg = (struct sadb_msg *)mhp[0];
1662 src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]);
1663 dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]);
1664 sa = (struct sadb_sa *)mhp[SADB_EXT_SA];
1665
1666 sa_mode = mhp[SADB_X_EXT_SA2] == NULL
1667 ? IPSEC_MODE_ANY
1668 : ((struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode;
1669
1670 /* the message has to be processed or not ? */
1671 if (msg->sadb_msg_pid != getpid()) {
1672 plog(LLV_DEBUG, LOCATION, NULL,
1673 "%s message is not interesting "
1674 "because pid %d is not mine.\n",
1675 s_pfkey_type(msg->sadb_msg_type),
1676 msg->sadb_msg_pid);
1677 return -1;
1678 }
1679
1680 iph2 = getph2byseq(msg->sadb_msg_seq);
1681 if (iph2 == NULL) {
1682 plog(LLV_DEBUG, LOCATION, NULL,
1683 "seq %d of %s message not interesting.\n",
1684 msg->sadb_msg_seq,
1685 s_pfkey_type(msg->sadb_msg_type));
1686 return -1;
1687 }
1688
1689 /*
1690 * NOTE don't update any status of phase2 handle
1691 * because they must be updated by SADB_UPDATE message
1692 */
1693
1694 plog(LLV_INFO, LOCATION, NULL,
1695 "IPsec-SA established: %s\n",
1696 sadbsecas2str(iph2->src, iph2->dst,
1697 msg->sadb_msg_satype, sa->sadb_sa_spi, sa_mode));
1698
1699 #ifdef ENABLE_VPNCONTROL_PORT
1700 {
1701 u_int32_t address;
1702
1703 if (iph2->dst->sa_family == AF_INET)
1704 address = ((struct sockaddr_in *)iph2->dst)->sin_addr.s_addr;
1705 else
1706 address = 0;
1707 vpncontrol_notify_phase_change(0, FROM_LOCAL, NULL, iph2);
1708 }
1709 #endif
1710
1711 plog(LLV_DEBUG, LOCATION, NULL, "===\n");
1712 return 0;
1713 }
1714
1715 static int
1716 pk_recvexpire(mhp)
1717 caddr_t *mhp;
1718 {
1719 struct sadb_msg *msg;
1720 struct sadb_sa *sa;
1721 struct sockaddr *src, *dst;
1722 struct ph2handle *iph2;
1723 u_int proto_id, sa_mode;
1724
1725 /* sanity check */
1726 if (mhp[0] == NULL
1727 || mhp[SADB_EXT_SA] == NULL
1728 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
1729 || mhp[SADB_EXT_ADDRESS_DST] == NULL
1730 || (mhp[SADB_EXT_LIFETIME_HARD] != NULL
1731 && mhp[SADB_EXT_LIFETIME_SOFT] != NULL)) {
1732 plog(LLV_ERROR, LOCATION, NULL,
1733 "inappropriate sadb expire message passed.\n");
1734 return -1;
1735 }
1736 msg = (struct sadb_msg *)mhp[0];
1737 sa = (struct sadb_sa *)mhp[SADB_EXT_SA];
1738 src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]);
1739 dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]);
1740
1741 sa_mode = mhp[SADB_X_EXT_SA2] == NULL
1742 ? IPSEC_MODE_ANY
1743 : ((struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode;
1744
1745 proto_id = pfkey2ipsecdoi_proto(msg->sadb_msg_satype);
1746 if (proto_id == ~0) {
1747 plog(LLV_ERROR, LOCATION, NULL,
1748 "invalid proto_id %d\n", msg->sadb_msg_satype);
1749 return -1;
1750 }
1751
1752 plog(LLV_INFO, LOCATION, NULL,
1753 "IPsec-SA expired: %s\n",
1754 sadbsecas2str(src, dst,
1755 msg->sadb_msg_satype, sa->sadb_sa_spi, sa_mode));
1756
1757 iph2 = getph2bysaidx(src, dst, proto_id, sa->sadb_sa_spi);
1758 if (iph2 == NULL) {
1759 /*
1760 * Ignore it because two expire messages are come up.
1761 * phase2 handler has been deleted already when 2nd message
1762 * is received.
1763 */
1764 plog(LLV_DEBUG, LOCATION, NULL,
1765 "no such a SA found: %s\n",
1766 sadbsecas2str(src, dst,
1767 msg->sadb_msg_satype, sa->sadb_sa_spi,
1768 sa_mode));
1769 return 0;
1770 }
1771 if (iph2->status != PHASE2ST_ESTABLISHED) {
1772 /*
1773 * If the status is not equal to PHASE2ST_ESTABLISHED,
1774 * racoon ignores this expire message. There are two reason.
1775 * One is that the phase 2 probably starts because there is
1776 * a potential that racoon receives the acquire message
1777 * without receiving a expire message. Another is that racoon
1778 * may receive the multiple expire messages from the kernel.
1779 */
1780 plog(LLV_WARNING, LOCATION, NULL,
1781 "the expire message is received "
1782 "but the handler has not been established.\n");
1783 return 0;
1784 }
1785
1786 /* turn off the timer for calling isakmp_ph2expire() */
1787 SCHED_KILL(iph2->sce);
1788
1789 iph2->status = PHASE2ST_EXPIRED;
1790
1791 /* INITIATOR, begin phase 2 exchange. */
1792 /* allocate buffer for status management of pfkey message */
1793 if (iph2->side == INITIATOR) {
1794
1795 initph2(iph2);
1796
1797 /* update status for re-use */
1798 iph2->status = PHASE2ST_STATUS2;
1799
1800 /* start isakmp initiation by using ident exchange */
1801 if (isakmp_post_acquire(iph2) < 0) {
1802 plog(LLV_ERROR, LOCATION, iph2->dst,
1803 "failed to begin ipsec sa "
1804 "re-negotication.\n");
1805 unbindph12(iph2);
1806 remph2(iph2);
1807 delph2(iph2);
1808 return -1;
1809 }
1810
1811 return 0;
1812 /*NOTREACHED*/
1813 }
1814
1815 /* If not received SADB_EXPIRE, INITIATOR delete ph2handle. */
1816 /* RESPONDER always delete ph2handle, keep silent. RESPONDER doesn't
1817 * manage IPsec SA, so delete the list */
1818 unbindph12(iph2);
1819 remph2(iph2);
1820 delph2(iph2);
1821
1822 return 0;
1823 }
1824
1825 static int
1826 pk_recvacquire(mhp)
1827 caddr_t *mhp;
1828 {
1829 struct sadb_msg *msg;
1830 struct sadb_x_policy *xpl;
1831 struct secpolicy *sp_out = NULL, *sp_in = NULL;
1832 #define MAXNESTEDSA 5 /* XXX */
1833 struct ph2handle *iph2[MAXNESTEDSA];
1834 struct sockaddr *src, *dst;
1835 int n; /* # of phase 2 handler */
1836
1837 /* ignore this message because of local test mode. */
1838 if (f_local)
1839 return 0;
1840
1841 /* sanity check */
1842 if (mhp[0] == NULL
1843 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
1844 || mhp[SADB_EXT_ADDRESS_DST] == NULL
1845 || mhp[SADB_X_EXT_POLICY] == NULL) {
1846 plog(LLV_ERROR, LOCATION, NULL,
1847 "inappropriate sadb acquire message passed.\n");
1848 return -1;
1849 }
1850 msg = (struct sadb_msg *)mhp[0];
1851 xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY];
1852 src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]);
1853 dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]);
1854
1855 /* ignore if type is not IPSEC_POLICY_IPSEC */
1856 if (xpl->sadb_x_policy_type != IPSEC_POLICY_IPSEC) {
1857 plog(LLV_DEBUG, LOCATION, NULL,
1858 "ignore ACQUIRE message. type is not IPsec.\n");
1859 return 0;
1860 }
1861
1862 /* ignore it if src is multicast address */
1863 {
1864 struct sockaddr *sa = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]);
1865
1866 if ((sa->sa_family == AF_INET
1867 && IN_MULTICAST(ntohl(((struct sockaddr_in *)sa)->sin_addr.s_addr)))
1868 #ifdef INET6
1869 || (sa->sa_family == AF_INET6
1870 && IN6_IS_ADDR_MULTICAST(&((struct sockaddr_in6 *)sa)->sin6_addr))
1871 #endif
1872 ) {
1873 plog(LLV_DEBUG, LOCATION, NULL,
1874 "ignore due to multicast address: %s.\n",
1875 saddrwop2str(sa));
1876 return 0;
1877 }
1878 }
1879
1880 /* ignore, if we do not listen on source address */
1881 {
1882 /* reasons behind:
1883 * - if we'll contact peer from address we do not listen -
1884 * we will be unable to complete negotiation;
1885 * - if we'll negotiate using address we're listening -
1886 * remote peer will send packets to address different
1887 * than one in the policy, so kernel will drop them;
1888 * => therefore this acquire is not for us! --Aidas
1889 */
1890 struct sockaddr *sa = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]);
1891 struct myaddrs *p;
1892 int do_listen = 0;
1893 for (p = lcconf->myaddrs; p; p = p->next) {
1894 if (!cmpsaddrwop(p->addr, sa)) {
1895 do_listen = 1;
1896 break;
1897 }
1898 }
1899
1900 if (!do_listen) {
1901 plog(LLV_DEBUG, LOCATION, NULL,
1902 "ignore because do not listen on source address : %s.\n",
1903 saddrwop2str(sa));
1904 return 0;
1905 }
1906 }
1907
1908 /*
1909 * If there is a phase 2 handler against the policy identifier in
1910 * the acquire message, and if
1911 * 1. its state is less than PHASE2ST_ESTABLISHED, then racoon
1912 * should ignore such a acquire message because the phase 2
1913 * is just negotiating.
1914 * 2. its state is equal to PHASE2ST_ESTABLISHED, then racoon
1915 * has to prcesss such a acquire message because racoon may
1916 * lost the expire message.
1917 */
1918 iph2[0] = getph2byid(src, dst, xpl->sadb_x_policy_id);
1919 if (iph2[0] != NULL) {
1920 if (iph2[0]->status < PHASE2ST_ESTABLISHED) {
1921 plog(LLV_DEBUG, LOCATION, NULL,
1922 "ignore the acquire because ph2 found\n");
1923 return -1;
1924 }
1925 if (iph2[0]->status == PHASE2ST_EXPIRED)
1926 iph2[0] = NULL;
1927 /*FALLTHROUGH*/
1928 }
1929
1930 /* search for proper policyindex */
1931 sp_out = getspbyspid(xpl->sadb_x_policy_id);
1932 if (sp_out == NULL) {
1933 plog(LLV_ERROR, LOCATION, NULL, "no policy found: id:%d.\n",
1934 xpl->sadb_x_policy_id);
1935 return -1;
1936 }
1937 plog(LLV_DEBUG, LOCATION, NULL,
1938 "suitable outbound SP found: %s.\n", spidx2str(&sp_out->spidx));
1939
1940 /* get inbound policy */
1941 {
1942 struct policyindex spidx;
1943
1944 spidx.dir = IPSEC_DIR_INBOUND;
1945 memcpy(&spidx.src, &sp_out->spidx.dst, sizeof(spidx.src));
1946 memcpy(&spidx.dst, &sp_out->spidx.src, sizeof(spidx.dst));
1947 spidx.prefs = sp_out->spidx.prefd;
1948 spidx.prefd = sp_out->spidx.prefs;
1949 spidx.ul_proto = sp_out->spidx.ul_proto;
1950
1951 sp_in = getsp(&spidx);
1952 if (sp_in) {
1953 plog(LLV_DEBUG, LOCATION, NULL,
1954 "suitable inbound SP found: %s.\n",
1955 spidx2str(&sp_in->spidx));
1956 } else {
1957 plog(LLV_NOTIFY, LOCATION, NULL,
1958 "no in-bound policy found: %s\n",
1959 spidx2str(&spidx));
1960 }
1961 }
1962
1963 memset(iph2, 0, MAXNESTEDSA);
1964
1965 n = 0;
1966
1967 /* allocate a phase 2 */
1968 iph2[n] = newph2();
1969 if (iph2[n] == NULL) {
1970 plog(LLV_ERROR, LOCATION, NULL,
1971 "failed to allocate phase2 entry.\n");
1972 return -1;
1973 }
1974 iph2[n]->side = INITIATOR;
1975 iph2[n]->spid = xpl->sadb_x_policy_id;
1976 iph2[n]->satype = msg->sadb_msg_satype;
1977 iph2[n]->seq = msg->sadb_msg_seq;
1978 iph2[n]->status = PHASE2ST_STATUS2;
1979
1980 /* set end addresses of SA */
1981 iph2[n]->dst = dupsaddr(PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]));
1982 if (iph2[n]->dst == NULL) {
1983 delph2(iph2[n]);
1984 return -1;
1985 }
1986 iph2[n]->src = dupsaddr(PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]));
1987 if (iph2[n]->src == NULL) {
1988 delph2(iph2[n]);
1989 return -1;
1990 }
1991
1992 plog(LLV_DEBUG, LOCATION, NULL,
1993 "new acquire %s\n", spidx2str(&sp_out->spidx));
1994
1995 /* get sainfo */
1996 {
1997 vchar_t *idsrc, *iddst;
1998
1999 idsrc = ipsecdoi_sockaddr2id((struct sockaddr *)&sp_out->spidx.src,
2000 sp_out->spidx.prefs, sp_out->spidx.ul_proto);
2001 if (idsrc == NULL) {
2002 plog(LLV_ERROR, LOCATION, NULL,
2003 "failed to get ID for %s\n",
2004 spidx2str(&sp_out->spidx));
2005 delph2(iph2[n]);
2006 return -1;
2007 }
2008 iddst = ipsecdoi_sockaddr2id((struct sockaddr *)&sp_out->spidx.dst,
2009 sp_out->spidx.prefd, sp_out->spidx.ul_proto);
2010 if (iddst == NULL) {
2011 plog(LLV_ERROR, LOCATION, NULL,
2012 "failed to get ID for %s\n",
2013 spidx2str(&sp_out->spidx));
2014 vfree(idsrc);
2015 delph2(iph2[n]);
2016 return -1;
2017 }
2018 iph2[n]->sainfo = getsainfo(idsrc, iddst, NULL, 0);
2019 vfree(idsrc);
2020 vfree(iddst);
2021 if (iph2[n]->sainfo == NULL) {
2022 plog(LLV_ERROR, LOCATION, NULL,
2023 "failed to get sainfo.\n");
2024 delph2(iph2[n]);
2025 return -1;
2026 /* XXX should use the algorithm list from register message */
2027 }
2028 }
2029
2030 if (set_proposal_from_policy(iph2[n], sp_out, sp_in) < 0) {
2031 plog(LLV_ERROR, LOCATION, NULL,
2032 "failed to create saprop.\n");
2033 delph2(iph2[n]);
2034 return -1;
2035 }
2036 insph2(iph2[n]);
2037
2038 /* start isakmp initiation by using ident exchange */
2039 /* XXX should be looped if there are multiple phase 2 handler. */
2040 if (isakmp_post_acquire(iph2[n]) < 0) {
2041 plog(LLV_ERROR, LOCATION, NULL,
2042 "failed to begin ipsec sa negotication.\n");
2043 goto err;
2044 }
2045
2046 return 0;
2047
2048 err:
2049 while (n >= 0) {
2050 unbindph12(iph2[n]);
2051 remph2(iph2[n]);
2052 delph2(iph2[n]);
2053 iph2[n] = NULL;
2054 n--;
2055 }
2056 return -1;
2057 }
2058
2059 static int
2060 pk_recvdelete(mhp)
2061 caddr_t *mhp;
2062 {
2063 struct sadb_msg *msg;
2064 struct sadb_sa *sa;
2065 struct sockaddr *src, *dst;
2066 struct ph2handle *iph2 = NULL;
2067 u_int proto_id;
2068
2069 /* ignore this message because of local test mode. */
2070 if (f_local)
2071 return 0;
2072
2073 /* sanity check */
2074 if (mhp[0] == NULL
2075 || mhp[SADB_EXT_SA] == NULL
2076 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
2077 || mhp[SADB_EXT_ADDRESS_DST] == NULL) {
2078 plog(LLV_ERROR, LOCATION, NULL,
2079 "inappropriate sadb delete message passed.\n");
2080 return -1;
2081 }
2082 msg = (struct sadb_msg *)mhp[0];
2083 sa = (struct sadb_sa *)mhp[SADB_EXT_SA];
2084 src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]);
2085 dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]);
2086
2087 /* the message has to be processed or not ? */
2088 if (msg->sadb_msg_pid == getpid()) {
2089 plog(LLV_DEBUG, LOCATION, NULL,
2090 "%s message is not interesting "
2091 "because the message was originated by me.\n",
2092 s_pfkey_type(msg->sadb_msg_type));
2093 return -1;
2094 }
2095
2096 proto_id = pfkey2ipsecdoi_proto(msg->sadb_msg_satype);
2097 if (proto_id == ~0) {
2098 plog(LLV_ERROR, LOCATION, NULL,
2099 "invalid proto_id %d\n", msg->sadb_msg_satype);
2100 return -1;
2101 }
2102
2103 iph2 = getph2bysaidx(src, dst, proto_id, sa->sadb_sa_spi);
2104 if (iph2 == NULL) {
2105 /* ignore */
2106 plog(LLV_ERROR, LOCATION, NULL,
2107 "no iph2 found: %s\n",
2108 sadbsecas2str(src, dst, msg->sadb_msg_satype,
2109 sa->sadb_sa_spi, IPSEC_MODE_ANY));
2110 return 0;
2111 }
2112
2113 plog(LLV_ERROR, LOCATION, NULL,
2114 "pfkey DELETE received: %s\n",
2115 sadbsecas2str(iph2->src, iph2->dst,
2116 msg->sadb_msg_satype, sa->sadb_sa_spi, IPSEC_MODE_ANY));
2117
2118 /* send delete information */
2119 if (iph2->status == PHASE2ST_ESTABLISHED)
2120 isakmp_info_send_d2(iph2);
2121
2122 unbindph12(iph2);
2123 remph2(iph2);
2124 delph2(iph2);
2125
2126 return 0;
2127 }
2128
2129 static int
2130 pk_recvflush(mhp)
2131 caddr_t *mhp;
2132 {
2133 /* ignore this message because of local test mode. */
2134 if (f_local)
2135 return 0;
2136
2137 /* sanity check */
2138 if (mhp[0] == NULL) {
2139 plog(LLV_ERROR, LOCATION, NULL,
2140 "inappropriate sadb flush message passed.\n");
2141 return -1;
2142 }
2143
2144 flushph2();
2145
2146 return 0;
2147 }
2148
2149 static int
2150 getsadbpolicy(policy0, policylen0, type, iph2)
2151 caddr_t *policy0;
2152 int *policylen0, type;
2153 struct ph2handle *iph2;
2154 {
2155 struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen;
2156 struct sadb_x_policy *xpl;
2157 struct sadb_x_ipsecrequest *xisr;
2158 struct saproto *pr;
2159 caddr_t policy, p;
2160 int policylen;
2161 int xisrlen;
2162 u_int satype, mode;
2163
2164 /* get policy buffer size */
2165 policylen = sizeof(struct sadb_x_policy);
2166 if (type != SADB_X_SPDDELETE) {
2167 for (pr = iph2->approval->head; pr; pr = pr->next) {
2168 xisrlen = sizeof(*xisr);
2169 if (pr->encmode == IPSECDOI_ATTR_ENC_MODE_TUNNEL) {
2170 xisrlen += (sysdep_sa_len(iph2->src)
2171 + sysdep_sa_len(iph2->dst));
2172 }
2173
2174 policylen += PFKEY_ALIGN8(xisrlen);
2175 }
2176 }
2177
2178 /* make policy structure */
2179 policy = racoon_malloc(policylen);
2180 if (!policy) {
2181 plog(LLV_ERROR, LOCATION, NULL,
2182 "buffer allocation failed.\n");
2183 return -1;
2184 }
2185
2186 xpl = (struct sadb_x_policy *)policy;
2187 xpl->sadb_x_policy_len = PFKEY_UNIT64(policylen);
2188 xpl->sadb_x_policy_exttype = SADB_X_EXT_POLICY;
2189 xpl->sadb_x_policy_type = IPSEC_POLICY_IPSEC;
2190 xpl->sadb_x_policy_dir = spidx->dir;
2191 xpl->sadb_x_policy_id = 0;
2192 #ifdef HAVE_PFKEY_POLICY_PRIORITY
2193 xpl->sadb_x_policy_priority = PRIORITY_DEFAULT;
2194 #endif
2195
2196 /* no need to append policy information any more if type is SPDDELETE */
2197 if (type == SADB_X_SPDDELETE)
2198 goto end;
2199
2200 xisr = (struct sadb_x_ipsecrequest *)(xpl + 1);
2201
2202 for (pr = iph2->approval->head; pr; pr = pr->next) {
2203
2204 satype = doi2ipproto(pr->proto_id);
2205 if (satype == ~0) {
2206 plog(LLV_ERROR, LOCATION, NULL,
2207 "invalid proto_id %d\n", pr->proto_id);
2208 goto err;
2209 }
2210 mode = ipsecdoi2pfkey_mode(pr->encmode);
2211 if (mode == ~0) {
2212 plog(LLV_ERROR, LOCATION, NULL,
2213 "invalid encmode %d\n", pr->encmode);
2214 goto err;
2215 }
2216
2217 /*
2218 * the policy level cannot be unique because the policy
2219 * is defined later than SA, so req_id cannot be bound to SA.
2220 */
2221 xisr->sadb_x_ipsecrequest_proto = satype;
2222 xisr->sadb_x_ipsecrequest_mode = mode;
2223 xisr->sadb_x_ipsecrequest_level = IPSEC_LEVEL_REQUIRE;
2224 xisr->sadb_x_ipsecrequest_reqid = 0;
2225 p = (caddr_t)(xisr + 1);
2226
2227 xisrlen = sizeof(*xisr);
2228
2229 if (pr->encmode == IPSECDOI_ATTR_ENC_MODE_TUNNEL) {
2230 int src_len, dst_len;
2231
2232 src_len = sysdep_sa_len(iph2->src);
2233 dst_len = sysdep_sa_len(iph2->dst);
2234 xisrlen += src_len + dst_len;
2235
2236 memcpy(p, iph2->src, src_len);
2237 p += src_len;
2238
2239 memcpy(p, iph2->dst, dst_len);
2240 p += dst_len;
2241 }
2242
2243 xisr->sadb_x_ipsecrequest_len = PFKEY_ALIGN8(xisrlen);
2244 }
2245
2246 end:
2247 *policy0 = policy;
2248 *policylen0 = policylen;
2249
2250 return 0;
2251
2252 err:
2253 if (policy)
2254 racoon_free(policy);
2255
2256 return -1;
2257 }
2258
2259 int
2260 pk_sendspdupdate2(iph2)
2261 struct ph2handle *iph2;
2262 {
2263 struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen;
2264 caddr_t policy = NULL;
2265 int policylen = 0;
2266 u_int64_t ltime, vtime;
2267
2268 ltime = iph2->approval->lifetime;
2269 vtime = 0;
2270
2271 if (getsadbpolicy(&policy, &policylen, SADB_X_SPDUPDATE, iph2)) {
2272 plog(LLV_ERROR, LOCATION, NULL,
2273 "getting sadb policy failed.\n");
2274 return -1;
2275 }
2276
2277 if (pfkey_send_spdupdate2(
2278 lcconf->sock_pfkey,
2279 (struct sockaddr *)&spidx->src,
2280 spidx->prefs,
2281 (struct sockaddr *)&spidx->dst,
2282 spidx->prefd,
2283 spidx->ul_proto,
2284 ltime, vtime,
2285 policy, policylen, 0) < 0) {
2286 plog(LLV_ERROR, LOCATION, NULL,
2287 "libipsec failed send spdupdate2 (%s)\n",
2288 ipsec_strerror());
2289 goto end;
2290 }
2291 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_spdupdate2\n");
2292
2293 end:
2294 if (policy)
2295 racoon_free(policy);
2296
2297 return 0;
2298 }
2299
2300 static int
2301 pk_recvspdupdate(mhp)
2302 caddr_t *mhp;
2303 {
2304 struct sadb_address *saddr, *daddr;
2305 struct sadb_x_policy *xpl;
2306 struct policyindex spidx;
2307 struct secpolicy *sp;
2308
2309 /* sanity check */
2310 if (mhp[0] == NULL
2311 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
2312 || mhp[SADB_EXT_ADDRESS_DST] == NULL
2313 || mhp[SADB_X_EXT_POLICY] == NULL) {
2314 plog(LLV_ERROR, LOCATION, NULL,
2315 "inappropriate sadb spdupdate message passed.\n");
2316 return -1;
2317 }
2318 saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC];
2319 daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST];
2320 xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY];
2321
2322 #ifdef HAVE_PFKEY_POLICY_PRIORITY
2323 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2324 saddr + 1,
2325 daddr + 1,
2326 saddr->sadb_address_prefixlen,
2327 daddr->sadb_address_prefixlen,
2328 saddr->sadb_address_proto,
2329 xpl->sadb_x_policy_priority,
2330 &spidx);
2331 #else
2332 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2333 saddr + 1,
2334 daddr + 1,
2335 saddr->sadb_address_prefixlen,
2336 daddr->sadb_address_prefixlen,
2337 saddr->sadb_address_proto,
2338 &spidx);
2339 #endif
2340
2341 sp = getsp(&spidx);
2342 if (sp == NULL) {
2343 plog(LLV_ERROR, LOCATION, NULL,
2344 "such policy does not already exist: \"%s\"\n",
2345 spidx2str(&spidx));
2346 } else {
2347 remsp(sp);
2348 delsp(sp);
2349 }
2350
2351 if (addnewsp(mhp) < 0)
2352 return -1;
2353
2354 return 0;
2355 }
2356
2357 /*
2358 * this function has to be used by responder side.
2359 */
2360 int
2361 pk_sendspdadd2(iph2)
2362 struct ph2handle *iph2;
2363 {
2364 struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen;
2365 caddr_t policy = NULL;
2366 int policylen = 0;
2367 u_int64_t ltime, vtime;
2368
2369 ltime = iph2->approval->lifetime;
2370 vtime = 0;
2371
2372 if (getsadbpolicy(&policy, &policylen, SADB_X_SPDADD, iph2)) {
2373 plog(LLV_ERROR, LOCATION, NULL,
2374 "getting sadb policy failed.\n");
2375 return -1;
2376 }
2377
2378 if (pfkey_send_spdadd2(
2379 lcconf->sock_pfkey,
2380 (struct sockaddr *)&spidx->src,
2381 spidx->prefs,
2382 (struct sockaddr *)&spidx->dst,
2383 spidx->prefd,
2384 spidx->ul_proto,
2385 ltime, vtime,
2386 policy, policylen, 0) < 0) {
2387 plog(LLV_ERROR, LOCATION, NULL,
2388 "libipsec failed send spdadd2 (%s)\n",
2389 ipsec_strerror());
2390 goto end;
2391 }
2392 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_spdadd2\n");
2393
2394 end:
2395 if (policy)
2396 racoon_free(policy);
2397
2398 return 0;
2399 }
2400
2401 static int
2402 pk_recvspdadd(mhp)
2403 caddr_t *mhp;
2404 {
2405 struct sadb_address *saddr, *daddr;
2406 struct sadb_x_policy *xpl;
2407 struct policyindex spidx;
2408 struct secpolicy *sp;
2409
2410 /* sanity check */
2411 if (mhp[0] == NULL
2412 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
2413 || mhp[SADB_EXT_ADDRESS_DST] == NULL
2414 || mhp[SADB_X_EXT_POLICY] == NULL) {
2415 plog(LLV_ERROR, LOCATION, NULL,
2416 "inappropriate sadb spdadd message passed.\n");
2417 return -1;
2418 }
2419 saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC];
2420 daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST];
2421 xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY];
2422
2423 #ifdef HAVE_PFKEY_POLICY_PRIORITY
2424 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2425 saddr + 1,
2426 daddr + 1,
2427 saddr->sadb_address_prefixlen,
2428 daddr->sadb_address_prefixlen,
2429 saddr->sadb_address_proto,
2430 xpl->sadb_x_policy_priority,
2431 &spidx);
2432 #else
2433 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2434 saddr + 1,
2435 daddr + 1,
2436 saddr->sadb_address_prefixlen,
2437 daddr->sadb_address_prefixlen,
2438 saddr->sadb_address_proto,
2439 &spidx);
2440 #endif
2441
2442 sp = getsp(&spidx);
2443 if (sp != NULL) {
2444 plog(LLV_ERROR, LOCATION, NULL,
2445 "such policy already exists. "
2446 "anyway replace it: %s\n",
2447 spidx2str(&spidx));
2448 remsp(sp);
2449 delsp(sp);
2450 }
2451
2452 if (addnewsp(mhp) < 0)
2453 return -1;
2454
2455 return 0;
2456 }
2457
2458 /*
2459 * this function has to be used by responder side.
2460 */
2461 int
2462 pk_sendspddelete(iph2)
2463 struct ph2handle *iph2;
2464 {
2465 struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen;
2466 caddr_t policy = NULL;
2467 int policylen;
2468
2469 if (getsadbpolicy(&policy, &policylen, SADB_X_SPDDELETE, iph2)) {
2470 plog(LLV_ERROR, LOCATION, NULL,
2471 "getting sadb policy failed.\n");
2472 return -1;
2473 }
2474
2475 if (pfkey_send_spddelete(
2476 lcconf->sock_pfkey,
2477 (struct sockaddr *)&spidx->src,
2478 spidx->prefs,
2479 (struct sockaddr *)&spidx->dst,
2480 spidx->prefd,
2481 spidx->ul_proto,
2482 policy, policylen, 0) < 0) {
2483 plog(LLV_ERROR, LOCATION, NULL,
2484 "libipsec failed send spddelete (%s)\n",
2485 ipsec_strerror());
2486 goto end;
2487 }
2488 plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_spddelete\n");
2489
2490 end:
2491 if (policy)
2492 racoon_free(policy);
2493
2494 return 0;
2495 }
2496
2497 static int
2498 pk_recvspddelete(mhp)
2499 caddr_t *mhp;
2500 {
2501 struct sadb_address *saddr, *daddr;
2502 struct sadb_x_policy *xpl;
2503 struct policyindex spidx;
2504 struct secpolicy *sp;
2505
2506 /* sanity check */
2507 if (mhp[0] == NULL
2508 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
2509 || mhp[SADB_EXT_ADDRESS_DST] == NULL
2510 || mhp[SADB_X_EXT_POLICY] == NULL) {
2511 plog(LLV_ERROR, LOCATION, NULL,
2512 "inappropriate sadb spddelete message passed.\n");
2513 return -1;
2514 }
2515 saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC];
2516 daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST];
2517 xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY];
2518
2519 #ifdef HAVE_PFKEY_POLICY_PRIORITY
2520 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2521 saddr + 1,
2522 daddr + 1,
2523 saddr->sadb_address_prefixlen,
2524 daddr->sadb_address_prefixlen,
2525 saddr->sadb_address_proto,
2526 xpl->sadb_x_policy_priority,
2527 &spidx);
2528 #else
2529 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2530 saddr + 1,
2531 daddr + 1,
2532 saddr->sadb_address_prefixlen,
2533 daddr->sadb_address_prefixlen,
2534 saddr->sadb_address_proto,
2535 &spidx);
2536 #endif
2537
2538 sp = getsp(&spidx);
2539 if (sp == NULL) {
2540 plog(LLV_ERROR, LOCATION, NULL,
2541 "no policy found: %s\n",
2542 spidx2str(&spidx));
2543 return -1;
2544 }
2545
2546 remsp(sp);
2547 delsp(sp);
2548
2549 return 0;
2550 }
2551
2552 static int
2553 pk_recvspdexpire(mhp)
2554 caddr_t *mhp;
2555 {
2556 struct sadb_address *saddr, *daddr;
2557 struct sadb_x_policy *xpl;
2558 struct policyindex spidx;
2559 struct secpolicy *sp;
2560
2561 /* sanity check */
2562 if (mhp[0] == NULL
2563 || mhp[SADB_EXT_ADDRESS_SRC] == NULL
2564 || mhp[SADB_EXT_ADDRESS_DST] == NULL
2565 || mhp[SADB_X_EXT_POLICY] == NULL) {
2566 plog(LLV_ERROR, LOCATION, NULL,
2567 "inappropriate sadb spdexpire message passed.\n");
2568 return -1;
2569 }
2570 saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC];
2571 daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST];
2572 xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY];
2573
2574 #ifdef HAVE_PFKEY_POLICY_PRIORITY
2575 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2576 saddr + 1,
2577 daddr + 1,
2578 saddr->sadb_address_prefixlen,
2579 daddr->sadb_address_prefixlen,
2580 saddr->sadb_address_proto,
2581 xpl->sadb_x_policy_priority,
2582 &spidx);
2583 #else
2584 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2585 saddr + 1,
2586 daddr + 1,
2587 saddr->sadb_address_prefixlen,
2588 daddr->sadb_address_prefixlen,
2589 saddr->sadb_address_proto,
2590 &spidx);
2591 #endif
2592
2593 sp = getsp(&spidx);
2594 if (sp == NULL) {
2595 plog(LLV_ERROR, LOCATION, NULL,
2596 "no policy found: %s\n",
2597 spidx2str(&spidx));
2598 return -1;
2599 }
2600
2601 remsp(sp);
2602 delsp(sp);
2603
2604 return 0;
2605 }
2606
2607 static int
2608 pk_recvspdget(mhp)
2609 caddr_t *mhp;
2610 {
2611 /* sanity check */
2612 if (mhp[0] == NULL) {
2613 plog(LLV_ERROR, LOCATION, NULL,
2614 "inappropriate sadb spdget message passed.\n");
2615 return -1;
2616 }
2617
2618 return 0;
2619 }
2620
2621 static int
2622 pk_recvspddump(mhp)
2623 caddr_t *mhp;
2624 {
2625 struct sadb_msg *msg;
2626 struct sadb_address *saddr, *daddr;
2627 struct sadb_x_policy *xpl;
2628 struct policyindex spidx;
2629 struct secpolicy *sp;
2630
2631 /* sanity check */
2632 if (mhp[0] == NULL) {
2633 plog(LLV_ERROR, LOCATION, NULL,
2634 "inappropriate sadb spddump message passed.\n");
2635 return -1;
2636 }
2637 msg = (struct sadb_msg *)mhp[0];
2638
2639 saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC];
2640 daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST];
2641 xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY];
2642
2643 if (saddr == NULL || daddr == NULL || xpl == NULL) {
2644 plog(LLV_ERROR, LOCATION, NULL,
2645 "inappropriate sadb spddump message passed.\n");
2646 return -1;
2647 }
2648
2649 #ifdef HAVE_PFKEY_POLICY_PRIORITY
2650 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2651 saddr + 1,
2652 daddr + 1,
2653 saddr->sadb_address_prefixlen,
2654 daddr->sadb_address_prefixlen,
2655 saddr->sadb_address_proto,
2656 xpl->sadb_x_policy_priority,
2657 &spidx);
2658 #else
2659 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
2660 saddr + 1,
2661 daddr + 1,
2662 saddr->sadb_address_prefixlen,
2663 daddr->sadb_address_prefixlen,
2664 saddr->sadb_address_proto,
2665 &spidx);
2666 #endif
2667
2668 sp = getsp(&spidx);
2669 if (sp != NULL) {
2670 plog(LLV_ERROR, LOCATION, NULL,
2671 "such policy already exists. "
2672 "anyway replace it: %s\n",
2673 spidx2str(&spidx));
2674 remsp(sp);
2675 delsp(sp);
2676 }
2677
2678 if (addnewsp(mhp) < 0)
2679 return -1;
2680
2681 return 0;
2682 }
2683
2684 static int
2685 pk_recvspdflush(mhp)
2686 caddr_t *mhp;
2687 {
2688 /* sanity check */
2689 if (mhp[0] == NULL) {
2690 plog(LLV_ERROR, LOCATION, NULL,
2691 "inappropriate sadb spdflush message passed.\n");
2692 return -1;
2693 }
2694
2695 flushsp();
2696
2697 return 0;
2698 }
2699
2700 /*
2701 * send error against acquire message to kenrel.
2702 */
2703 int
2704 pk_sendeacquire(iph2)
2705 struct ph2handle *iph2;
2706 {
2707 struct sadb_msg *newmsg;
2708 int len;
2709
2710 len = sizeof(struct sadb_msg);
2711 newmsg = racoon_calloc(1, len);
2712 if (newmsg == NULL) {
2713 plog(LLV_ERROR, LOCATION, NULL,
2714 "failed to get buffer to send acquire.\n");
2715 return -1;
2716 }
2717
2718 memset(newmsg, 0, len);
2719 newmsg->sadb_msg_version = PF_KEY_V2;
2720 newmsg->sadb_msg_type = SADB_ACQUIRE;
2721 newmsg->sadb_msg_errno = ENOENT; /* XXX */
2722 newmsg->sadb_msg_satype = iph2->satype;
2723 newmsg->sadb_msg_len = PFKEY_UNIT64(len);
2724 newmsg->sadb_msg_reserved = 0;
2725 newmsg->sadb_msg_seq = iph2->seq;
2726 newmsg->sadb_msg_pid = (u_int32_t)getpid();
2727
2728 /* send message */
2729 len = pfkey_send(lcconf->sock_pfkey, newmsg, len);
2730
2731 racoon_free(newmsg);
2732
2733 return 0;
2734 }
2735
2736 /*
2737 * check if the algorithm is supported or not.
2738 * OUT 0: ok
2739 * -1: ng
2740 */
2741 int
2742 pk_checkalg(class, calg, keylen)
2743 int class, calg, keylen;
2744 {
2745 int sup, error;
2746 u_int alg;
2747 struct sadb_alg alg0;
2748
2749 switch (algclass2doi(class)) {
2750 case IPSECDOI_PROTO_IPSEC_ESP:
2751 sup = SADB_EXT_SUPPORTED_ENCRYPT;
2752 break;
2753 case IPSECDOI_ATTR_AUTH:
2754 sup = SADB_EXT_SUPPORTED_AUTH;
2755 break;
2756 case IPSECDOI_PROTO_IPCOMP:
2757 plog(LLV_DEBUG, LOCATION, NULL,
2758 "compression algorithm can not be checked "
2759 "because sadb message doesn't support it.\n");
2760 return 0;
2761 default:
2762 plog(LLV_ERROR, LOCATION, NULL,
2763 "invalid algorithm class.\n");
2764 return -1;
2765 }
2766 alg = ipsecdoi2pfkey_alg(algclass2doi(class), algtype2doi(class, calg));
2767 if (alg == ~0)
2768 return -1;
2769
2770 if (keylen == 0) {
2771 if (ipsec_get_keylen(sup, alg, &alg0)) {
2772 plog(LLV_ERROR, LOCATION, NULL,
2773 "%s.\n", ipsec_strerror());
2774 return -1;
2775 }
2776 keylen = alg0.sadb_alg_minbits;
2777 }
2778
2779 error = ipsec_check_keylen(sup, alg, keylen);
2780 if (error)
2781 plog(LLV_ERROR, LOCATION, NULL,
2782 "%s.\n", ipsec_strerror());
2783
2784 return error;
2785 }
2786
2787 /*
2788 * differences with pfkey_recv() in libipsec/pfkey.c:
2789 * - never performs busy wait loop.
2790 * - returns NULL and set *lenp to negative on fatal failures
2791 * - returns NULL and set *lenp to non-negative on non-fatal failures
2792 * - returns non-NULL on success
2793 */
2794 static struct sadb_msg *
2795 pk_recv(so, lenp)
2796 int so;
2797 int *lenp;
2798 {
2799 struct sadb_msg *newmsg;
2800 int reallen = 0;
2801 socklen_t optlen = sizeof(reallen);
2802
2803 if (getsockopt(so, SOL_SOCKET, SO_NREAD, &reallen, &optlen) < 0)
2804 return NULL; /*fatal*/
2805
2806 if (reallen == 0)
2807 return NULL;
2808
2809 if ((newmsg = racoon_calloc(1, reallen)) == NULL)
2810 return NULL;
2811
2812 *lenp = recv(so, (caddr_t)newmsg, reallen, 0);
2813 if (*lenp < 0) {
2814 racoon_free(newmsg);
2815 return NULL; /*fatal*/
2816 } else if (*lenp != reallen || *lenp < sizeof(struct sadb_msg)) {
2817 racoon_free(newmsg);
2818 return NULL;
2819 }
2820
2821 return newmsg;
2822 }
2823
2824
2825
2826 /* see handler.h */
2827 u_int32_t
2828 pk_getseq()
2829 {
2830 return eay_random();
2831 }
2832
2833 static int
2834 addnewsp(mhp)
2835 caddr_t *mhp;
2836 {
2837 struct secpolicy *new;
2838 struct sadb_address *saddr, *daddr;
2839 struct sadb_x_policy *xpl;
2840
2841 /* sanity check */
2842 if (mhp[SADB_EXT_ADDRESS_SRC] == NULL
2843 || mhp[SADB_EXT_ADDRESS_DST] == NULL
2844 || mhp[SADB_X_EXT_POLICY] == NULL) {
2845 plog(LLV_ERROR, LOCATION, NULL,
2846 "inappropriate sadb spd management message passed.\n");
2847 return -1;
2848 }
2849
2850 saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC];
2851 daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST];
2852 xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY];
2853
2854 #ifdef __linux__
2855 /* bsd skips over per-socket policies because there will be no
2856 * src and dst extensions in spddump messages. On Linux the only
2857 * way to achieve the same is check for policy id.
2858 */
2859 if (xpl->sadb_x_policy_id % 8 >= 3) return 0;
2860 #endif
2861
2862 new = newsp();
2863 if (new == NULL) {
2864 plog(LLV_ERROR, LOCATION, NULL,
2865 "failed to allocate buffer\n");
2866 return -1;
2867 }
2868
2869 new->spidx.dir = xpl->sadb_x_policy_dir;
2870 new->id = xpl->sadb_x_policy_id;
2871 new->policy = xpl->sadb_x_policy_type;
2872 new->req = NULL;
2873
2874 /* check policy */
2875 switch (xpl->sadb_x_policy_type) {
2876 case IPSEC_POLICY_DISCARD:
2877 case IPSEC_POLICY_GENERATE:
2878 case IPSEC_POLICY_NONE:
2879 case IPSEC_POLICY_ENTRUST:
2880 case IPSEC_POLICY_BYPASS:
2881 break;
2882
2883 case IPSEC_POLICY_IPSEC:
2884 {
2885 int tlen;
2886 struct sadb_x_ipsecrequest *xisr;
2887 struct ipsecrequest **p_isr = &new->req;
2888
2889 /* validity check */
2890 if (PFKEY_EXTLEN(xpl) < sizeof(*xpl)) {
2891 plog(LLV_ERROR, LOCATION, NULL,
2892 "invalid msg length.\n");
2893 return -1;
2894 }
2895
2896 tlen = PFKEY_EXTLEN(xpl) - sizeof(*xpl);
2897 xisr = (struct sadb_x_ipsecrequest *)(xpl + 1);
2898
2899 while (tlen > 0) {
2900
2901 /* length check */
2902 if (xisr->sadb_x_ipsecrequest_len < sizeof(*xisr)) {
2903 plog(LLV_ERROR, LOCATION, NULL,
2904 "invalid msg length.\n");
2905 return -1;
2906 }
2907
2908 /* allocate request buffer */
2909 *p_isr = newipsecreq();
2910 if (*p_isr == NULL) {
2911 plog(LLV_ERROR, LOCATION, NULL,
2912 "failed to get new ipsecreq.\n");
2913 return -1;
2914 }
2915
2916 /* set values */
2917 (*p_isr)->next = NULL;
2918
2919 switch (xisr->sadb_x_ipsecrequest_proto) {
2920 case IPPROTO_ESP:
2921 case IPPROTO_AH:
2922 case IPPROTO_IPCOMP:
2923 break;
2924 default:
2925 plog(LLV_ERROR, LOCATION, NULL,
2926 "invalid proto type: %u\n",
2927 xisr->sadb_x_ipsecrequest_proto);
2928 return -1;
2929 }
2930 (*p_isr)->saidx.proto = xisr->sadb_x_ipsecrequest_proto;
2931
2932 switch (xisr->sadb_x_ipsecrequest_mode) {
2933 case IPSEC_MODE_TRANSPORT:
2934 case IPSEC_MODE_TUNNEL:
2935 break;
2936 case IPSEC_MODE_ANY:
2937 default:
2938 plog(LLV_ERROR, LOCATION, NULL,
2939 "invalid mode: %u\n",
2940 xisr->sadb_x_ipsecrequest_mode);
2941 return -1;
2942 }
2943 (*p_isr)->saidx.mode = xisr->sadb_x_ipsecrequest_mode;
2944
2945 switch (xisr->sadb_x_ipsecrequest_level) {
2946 case IPSEC_LEVEL_DEFAULT:
2947 case IPSEC_LEVEL_USE:
2948 case IPSEC_LEVEL_REQUIRE:
2949 break;
2950 case IPSEC_LEVEL_UNIQUE:
2951 (*p_isr)->saidx.reqid =
2952 xisr->sadb_x_ipsecrequest_reqid;
2953 break;
2954
2955 default:
2956 plog(LLV_ERROR, LOCATION, NULL,
2957 "invalid level: %u\n",
2958 xisr->sadb_x_ipsecrequest_level);
2959 return -1;
2960 }
2961 (*p_isr)->level = xisr->sadb_x_ipsecrequest_level;
2962
2963 /* set IP addresses if there */
2964 if (xisr->sadb_x_ipsecrequest_len > sizeof(*xisr)) {
2965 struct sockaddr *paddr;
2966
2967 paddr = (struct sockaddr *)(xisr + 1);
2968 bcopy(paddr, &(*p_isr)->saidx.src,
2969 sysdep_sa_len(paddr));
2970
2971 paddr = (struct sockaddr *)((caddr_t)paddr
2972 + sysdep_sa_len(paddr));
2973 bcopy(paddr, &(*p_isr)->saidx.dst,
2974 sysdep_sa_len(paddr));
2975 }
2976
2977 (*p_isr)->sp = new;
2978
2979 /* initialization for the next. */
2980 p_isr = &(*p_isr)->next;
2981 tlen -= xisr->sadb_x_ipsecrequest_len;
2982
2983 /* validity check */
2984 if (tlen < 0) {
2985 plog(LLV_ERROR, LOCATION, NULL,
2986 "becoming tlen < 0\n");
2987 }
2988
2989 xisr = (struct sadb_x_ipsecrequest *)((caddr_t)xisr
2990 + xisr->sadb_x_ipsecrequest_len);
2991 }
2992 }
2993 break;
2994 default:
2995 plog(LLV_ERROR, LOCATION, NULL,
2996 "invalid policy type.\n");
2997 return -1;
2998 }
2999
3000 #ifdef HAVE_PFKEY_POLICY_PRIORITY
3001 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
3002 saddr + 1,
3003 daddr + 1,
3004 saddr->sadb_address_prefixlen,
3005 daddr->sadb_address_prefixlen,
3006 saddr->sadb_address_proto,
3007 xpl->sadb_x_policy_priority,
3008 &new->spidx);
3009 #else
3010 KEY_SETSECSPIDX(xpl->sadb_x_policy_dir,
3011 saddr + 1,
3012 daddr + 1,
3013 saddr->sadb_address_prefixlen,
3014 daddr->sadb_address_prefixlen,
3015 saddr->sadb_address_proto,
3016 &new->spidx);
3017 #endif
3018
3019 inssp(new);
3020
3021 return 0;
3022 }
3023
3024 /* proto/mode/src->dst spi */
3025 const char *
3026 sadbsecas2str(src, dst, proto, spi, mode)
3027 struct sockaddr *src, *dst;
3028 int proto;
3029 u_int32_t spi;
3030 int mode;
3031 {
3032 static char buf[256];
3033 u_int doi_proto, doi_mode = 0;
3034 char *p;
3035 int blen, i;
3036
3037 doi_proto = pfkey2ipsecdoi_proto(proto);
3038 if (doi_proto == ~0)
3039 return NULL;
3040 if (mode) {
3041 doi_mode = pfkey2ipsecdoi_mode(mode);
3042 if (doi_mode == ~0)
3043 return NULL;
3044 }
3045
3046 blen = sizeof(buf) - 1;
3047 p = buf;
3048
3049 i = snprintf(p, blen, "%s%s%s ",
3050 s_ipsecdoi_proto(doi_proto),
3051 mode ? "/" : "",
3052 mode ? s_ipsecdoi_encmode(doi_mode) : "");
3053 if (i < 0 || i >= blen)
3054 return NULL;
3055 p += i;
3056 blen -= i;
3057
3058 i = snprintf(p, blen, "%s->", saddr2str(src));
3059 if (i < 0 || i >= blen)
3060 return NULL;
3061 p += i;
3062 blen -= i;
3063
3064 i = snprintf(p, blen, "%s ", saddr2str(dst));
3065 if (i < 0 || i >= blen)
3066 return NULL;
3067 p += i;
3068 blen -= i;
3069
3070 if (spi) {
3071 snprintf(p, blen, "spi=%lu(0x%lx)", (unsigned long)ntohl(spi),
3072 (unsigned long)ntohl(spi));
3073 }
3074
3075 return buf;
3076 }