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