X-Git-Url: https://git.saurik.com/apple/ipsec.git/blobdiff_plain/e8d9021d008d9729f3dfcdc16bb03a990513b007..c8d8bee0bee0298e25cb827876f57e58cc0a938c:/ipsec-tools/racoon/pfkey_racoon.c diff --git a/ipsec-tools/racoon/pfkey_racoon.c b/ipsec-tools/racoon/pfkey_racoon.c index aa10d6d..63c61dd 100644 --- a/ipsec-tools/racoon/pfkey_racoon.c +++ b/ipsec-tools/racoon/pfkey_racoon.c @@ -30,6 +30,7 @@ */ #include "config.h" +#include "racoon_types.h" #include #include @@ -54,7 +55,7 @@ #include #include -#include +#include #include #ifndef HAVE_NETINET6_IPSEC @@ -71,6 +72,8 @@ #include "plog.h" #include "sockmisc.h" #include "debug.h" +#include "fsm.h" +#include "ike_session.h" #include "schedule.h" #include "localconf.h" @@ -86,10 +89,7 @@ #include "algorithm.h" #include "sainfo.h" #include "proposal.h" -#include "admin.h" -#include "privsep.h" #include "strnames.h" -#include "backupsa.h" #include "gcmalloc.h" #include "nattraversal.h" #include "crypto_openssl.h" @@ -100,38 +100,39 @@ #include "ipsecSessionTracer.h" #include "ipsecMessageTracer.h" #include "power_mgmt.h" +#include "session.h" #if defined(SADB_X_EALG_RIJNDAELCBC) && !defined(SADB_X_EALG_AESCBC) #define SADB_X_EALG_AESCBC SADB_X_EALG_RIJNDAELCBC #endif /* prototype */ -static u_int ipsecdoi2pfkey_aalg __P((u_int)); -static u_int ipsecdoi2pfkey_ealg __P((u_int)); -static u_int ipsecdoi2pfkey_calg __P((u_int)); -static u_int ipsecdoi2pfkey_alg __P((u_int, u_int)); -static u_int keylen_aalg __P((u_int)); -static u_int keylen_ealg __P((u_int, int)); - -static int pk_recvgetspi __P((caddr_t *)); -static int pk_recvupdate __P((caddr_t *)); -static int pk_recvadd __P((caddr_t *)); -static int pk_recvdelete __P((caddr_t *)); -static int pk_recvacquire __P((caddr_t *)); -static int pk_recvexpire __P((caddr_t *)); -static int pk_recvflush __P((caddr_t *)); -static int getsadbpolicy __P((caddr_t *, int *, int, struct ph2handle *)); -static int pk_recvspdupdate __P((caddr_t *)); -static int pk_recvspdadd __P((caddr_t *)); -static int pk_recvspddelete __P((caddr_t *)); -static int pk_recvspdexpire __P((caddr_t *)); -static int pk_recvspdget __P((caddr_t *)); -static int pk_recvspddump __P((caddr_t *)); -static int pk_recvspdflush __P((caddr_t *)); -static int pk_recvgetsastat __P((caddr_t *)); -static struct sadb_msg *pk_recv __P((int, int *)); - -static int (*pkrecvf[]) __P((caddr_t *)) = { +static u_int ipsecdoi2pfkey_aalg (u_int); +static u_int ipsecdoi2pfkey_ealg (u_int); +static u_int ipsecdoi2pfkey_calg (u_int); +static u_int ipsecdoi2pfkey_alg (u_int, u_int); +static u_int keylen_aalg (u_int); +static u_int keylen_ealg (u_int, int); + +static int pk_recvgetspi (caddr_t *); +static int pk_recvupdate (caddr_t *); +static int pk_recvadd (caddr_t *); +static int pk_recvdelete (caddr_t *); +static int pk_recvacquire (caddr_t *); +static int pk_recvexpire (caddr_t *); +static int pk_recvflush (caddr_t *); +static int getsadbpolicy (caddr_t *, int *, int, phase2_handle_t *); +static int pk_recvspdupdate (caddr_t *); +static int pk_recvspdadd (caddr_t *); +static int pk_recvspddelete (caddr_t *); +static int pk_recvspdexpire (caddr_t *); +static int pk_recvspdget (caddr_t *); +static int pk_recvspddump (caddr_t *); +static int pk_recvspdflush (caddr_t *); +static int pk_recvgetsastat (caddr_t *); +static struct sadb_msg *pk_recv (int, ssize_t *); + +static int (*pkrecvf[]) (caddr_t *) = { NULL, pk_recvgetspi, pk_recvupdate, @@ -156,14 +157,15 @@ NULL, /* SADB_X_SPDSETIDX */ pk_recvspdexpire, NULL, /* SADB_X_SPDDELETE2 */ pk_recvgetsastat, /* SADB_GETSASTAT */ -NULL, /* SADB_X_NAT_T_NEW_MAPPING */ -NULL, /* SADB_X_MIGRATE */ -#if (SADB_MAX > 25) -#error "SADB extra message?" +NULL, /* SADB_X_SPDENABLE */ +NULL, /* SADB_X_SPDDISNABLE */ +NULL, /* SADB_MIGRATE */ +#if (SADB_MAX > 26) +#warning "SADB extra message?" #endif }; -static int addnewsp __P((caddr_t *)); +static int addnewsp (caddr_t *); /* cope with old kame headers - ugly */ #ifndef SADB_X_AALG_MD5 @@ -195,54 +197,53 @@ pfkey_process(msg) caddr_t mhp[SADB_EXT_MAX + 1]; int error = -1; - plog(LLV_DEBUG, LOCATION, NULL, "get pfkey %s message\n", - s_pfkey_type(msg->sadb_msg_type)); - plogdump(LLV_DEBUG2, msg, msg->sadb_msg_len << 3); + // Special debug use only - creates large logs + // plogdump(ASL_LEVEL_DEBUG, msg, msg->sadb_msg_len << 3, "get pfkey %s message\n", + // s_pfkey_type(msg->sadb_msg_type)); /* validity check */ + /* check pfkey message. */ + if (pfkey_align(msg, mhp)) { + plog(ASL_LEVEL_ERR, + "libipsec failed pfkey align (%s)\n", + ipsec_strerror()); + goto end; + } + if (pfkey_check(mhp)) { + plog(ASL_LEVEL_ERR, + "libipsec failed pfkey check (%s)\n", + ipsec_strerror()); + goto end; + } + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + if (msg->sadb_msg_errno) { int pri; /* when SPD is empty, treat the state as no error. */ if (msg->sadb_msg_type == SADB_X_SPDDUMP && msg->sadb_msg_errno == ENOENT) - pri = LLV_DEBUG; + pri = ASL_LEVEL_DEBUG; else - pri = LLV_ERROR; + pri = ASL_LEVEL_ERR; - plog(pri, LOCATION, NULL, + plog(pri, "pfkey %s failed: %s\n", s_pfkey_type(msg->sadb_msg_type), strerror(msg->sadb_msg_errno)); - - goto end; - } - - /* check pfkey message. */ - if (pfkey_align(msg, mhp)) { - plog(LLV_ERROR, LOCATION, NULL, - "libipsec failed pfkey align (%s)\n", - ipsec_strerror()); - goto end; - } - if (pfkey_check(mhp)) { - plog(LLV_ERROR, LOCATION, NULL, - "libipsec failed pfkey check (%s)\n", - ipsec_strerror()); goto end; } - msg = (struct sadb_msg *)mhp[0]; - + /* safety check */ if (msg->sadb_msg_type >= ARRAYLEN(pkrecvf)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "unknown PF_KEY message type=%u\n", msg->sadb_msg_type); goto end; } if (pkrecvf[msg->sadb_msg_type] == NULL) { - plog(LLV_INFO, LOCATION, NULL, + plog(ASL_LEVEL_INFO, "unsupported PF_KEY message %s\n", s_pfkey_type(msg->sadb_msg_type)); goto end; @@ -263,33 +264,37 @@ end: * 0: success * -1: fail */ -int -pfkey_handler() + +//%%%%%%%%%%%%%%%%%% need to handle errors encountered here - this no longer returns a result +void +pfkey_handler(void *unused) { struct sadb_msg *msg; - int len; + ssize_t len; if (slept_at || woke_at) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "ignoring pfkey port until power-mgmt event is handled.\n"); - return 0; + return; } /* receive pfkey message. */ len = 0; msg = (struct sadb_msg *)pk_recv(lcconf->sock_pfkey, &len); + if (msg == NULL) { if (len < 0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "failed to recv from pfkey (%s)\n", strerror(errno)); - return -1; + return; } else { /* short message - msg not ready */ - return 0; + plog(ASL_LEVEL_DEBUG, "recv short message from pfkey\n"); + return; } } - return pfkey_process(msg); + pfkey_process(msg); } void @@ -299,9 +304,9 @@ pfkey_post_handler() struct saved_msg_elem *elem_tmp = NULL; if (slept_at || woke_at) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "ignoring (saved) pfkey messages until power-mgmt event is handled.\n"); - return 0; + return; } TAILQ_FOREACH_SAFE(elem, &lcconf->saved_msg_queue, chain, elem_tmp) { @@ -338,18 +343,18 @@ pfkey_dump_sadb(satype) pid_t pid = getpid(); struct sadb_msg *msg = NULL; size_t bl, ml; - int len; + ssize_t len; - if ((s = privsep_pfkey_open()) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + if ((s = pfkey_open()) < 0) { + plog(ASL_LEVEL_ERR, "libipsec failed pfkey open: %s\n", ipsec_strerror()); return NULL; } - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_dump\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_dump\n"); if (pfkey_send_dump(s, satype) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "libipsec failed dump: %s\n", ipsec_strerror()); goto fail; } @@ -383,7 +388,7 @@ pfkey_dump_sadb(satype) bl = buf ? buf->l : 0; buf = vrealloc(buf, bl + ml); if (buf == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "failed to reallocate buffer to dump.\n"); goto fail; } @@ -402,34 +407,10 @@ done: if (msg) racoon_free(msg); if (s >= 0) - privsep_pfkey_close(s); + pfkey_close_sock(s); return buf; } -#ifdef ENABLE_ADMINPORT -/* - * flush SADB - */ -void -pfkey_flush_sadb(proto) - u_int proto; -{ - int satype; - - /* convert to SADB_SATYPE */ - if ((satype = admin2pfkey_proto(proto)) < 0) - return; - - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_flush\n"); - if (pfkey_send_flush(lcconf->sock_pfkey, satype) < 0) { - plog(LLV_ERROR, LOCATION, NULL, - "libipsec failed send flush (%s)\n", ipsec_strerror()); - return; - } - - return; -} -#endif /* * These are the SATYPEs that we manage. We register to get @@ -449,24 +430,24 @@ const int pfkey_nsatypes = * PF_KEY initialization */ int -pfkey_init() +pfkey_init(void) { - int i, reg_fail; + int i, reg_fail, sock; - if ((lcconf->sock_pfkey = privsep_pfkey_open()) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + if ((lcconf->sock_pfkey = pfkey_open()) < 0) { + plog(ASL_LEVEL_ERR, "libipsec failed pfkey open (%s)\n", ipsec_strerror()); return -1; } for (i = 0, reg_fail = 0; i < pfkey_nsatypes; i++) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "call pfkey_send_register for %s\n", pfkey_satypes[i].ps_name); if (pfkey_send_register(lcconf->sock_pfkey, pfkey_satypes[i].ps_satype) < 0 || pfkey_recv_register(lcconf->sock_pfkey) < 0) { - plog(LLV_WARNING, LOCATION, NULL, + plog(ASL_LEVEL_WARNING, "failed to register %s (%s)\n", pfkey_satypes[i].ps_name, ipsec_strerror()); @@ -475,30 +456,50 @@ pfkey_init() } if (reg_fail == pfkey_nsatypes) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "failed to regist any protocol.\n"); - pfkey_close(lcconf->sock_pfkey); + close(lcconf->sock_pfkey); return -1; } - - initsp(); + initsp(); + + lcconf->pfkey_source = dispatch_source_create(DISPATCH_SOURCE_TYPE_READ, lcconf->sock_pfkey, 0, dispatch_get_main_queue()); + if (lcconf->pfkey_source == NULL) { + plog(ASL_LEVEL_ERR, "could not create pfkey socket source."); + return -1; + } + dispatch_source_set_event_handler_f(lcconf->pfkey_source, pfkey_handler); + sock = lcconf->sock_pfkey; + dispatch_source_set_cancel_handler(lcconf->pfkey_source, + ^{ + pfkey_close_sock(sock); + }); + dispatch_resume(lcconf->pfkey_source); if (pfkey_send_spddump(lcconf->sock_pfkey) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "libipsec sending spddump failed: %s\n", ipsec_strerror()); - pfkey_close(lcconf->sock_pfkey); + pfkey_close(); return -1; } #if 0 if (pfkey_promisc_toggle(1) < 0) { - pfkey_close(lcconf->sock_pfkey); + pfkey_close(); return -1; } #endif + return 0; } +void +pfkey_close(void) +{ + dispatch_source_cancel(lcconf->pfkey_source); + lcconf->pfkey_source = NULL; +} + /* %%% for conversion */ /* IPSECDOI_ATTR_AUTH -> SADB_AALG */ static u_int @@ -506,44 +507,46 @@ ipsecdoi2pfkey_aalg(hashtype) u_int hashtype; { switch (hashtype) { - case IPSECDOI_ATTR_AUTH_HMAC_MD5: - return SADB_AALG_MD5HMAC; - case IPSECDOI_ATTR_AUTH_HMAC_SHA1: - return SADB_AALG_SHA1HMAC; - case IPSECDOI_ATTR_AUTH_HMAC_SHA2_256: + case IPSECDOI_ATTR_AUTH_HMAC_MD5: + case IPSECDOI_ATTR_AUTH_HMAC_MD5_96: + return SADB_AALG_MD5HMAC; + case IPSECDOI_ATTR_AUTH_HMAC_SHA1: + case IPSECDOI_ATTR_AUTH_HMAC_SHA1_96: + return SADB_AALG_SHA1HMAC; + case IPSECDOI_ATTR_AUTH_HMAC_SHA2_256: #if (defined SADB_X_AALG_SHA2_256) && !defined(SADB_X_AALG_SHA2_256HMAC) - return SADB_X_AALG_SHA2_256; + return SADB_X_AALG_SHA2_256; #else - return SADB_X_AALG_SHA2_256HMAC; + return SADB_X_AALG_SHA2_256HMAC; #endif - case IPSECDOI_ATTR_AUTH_HMAC_SHA2_384: + case IPSECDOI_ATTR_AUTH_HMAC_SHA2_384: #if (defined SADB_X_AALG_SHA2_384) && !defined(SADB_X_AALG_SHA2_384HMAC) - return SADB_X_AALG_SHA2_384; + return SADB_X_AALG_SHA2_384; #else - return SADB_X_AALG_SHA2_384HMAC; + return SADB_X_AALG_SHA2_384HMAC; #endif - case IPSECDOI_ATTR_AUTH_HMAC_SHA2_512: + case IPSECDOI_ATTR_AUTH_HMAC_SHA2_512: #if (defined SADB_X_AALG_SHA2_512) && !defined(SADB_X_AALG_SHA2_512HMAC) - return SADB_X_AALG_SHA2_512; + return SADB_X_AALG_SHA2_512; #else - return SADB_X_AALG_SHA2_512HMAC; + return SADB_X_AALG_SHA2_512HMAC; #endif - case IPSECDOI_ATTR_AUTH_KPDK: /* need special care */ - return SADB_AALG_NONE; - - /* not supported */ - case IPSECDOI_ATTR_AUTH_DES_MAC: - plog(LLV_ERROR, LOCATION, NULL, - "Not supported hash type: %u\n", hashtype); - return ~0; - - case 0: /* reserved */ - default: - return SADB_AALG_NONE; - - plog(LLV_ERROR, LOCATION, NULL, - "Invalid hash type: %u\n", hashtype); - return ~0; + case IPSECDOI_ATTR_AUTH_KPDK: /* need special care */ + return SADB_AALG_NONE; + + /* not supported */ + case IPSECDOI_ATTR_AUTH_DES_MAC: + plog(ASL_LEVEL_ERR, + "Not supported hash type: %u\n", hashtype); + return ~0; + + case 0: /* reserved */ + default: + return SADB_AALG_NONE; + + plog(ASL_LEVEL_ERR, + "Invalid hash type: %u\n", hashtype); + return ~0; } /*NOTREACHED*/ } @@ -586,13 +589,13 @@ ipsecdoi2pfkey_ealg(t_id) case IPSECDOI_ESP_3IDEA: case IPSECDOI_ESP_IDEA: case IPSECDOI_ESP_RC4: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "Not supported transform: %u\n", t_id); return ~0; case 0: /* reserved */ default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "Invalid transform id: %u\n", t_id); return ~0; } @@ -614,7 +617,7 @@ ipsecdoi2pfkey_calg(t_id) case 0: /* reserved */ default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "Invalid transform id: %u\n", t_id); return ~0; } @@ -635,7 +638,7 @@ ipsecdoi2pfkey_proto(proto) return SADB_X_SATYPE_IPCOMP; default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "Invalid ipsec_doi proto: %u\n", proto); return ~0; } @@ -654,7 +657,7 @@ ipsecdoi2pfkey_alg(algclass, type) case IPSECDOI_PROTO_IPCOMP: return ipsecdoi2pfkey_calg(type); default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "Invalid ipsec_doi algclass: %u\n", algclass); return ~0; } @@ -675,7 +678,7 @@ pfkey2ipsecdoi_proto(satype) return IPSECDOI_PROTO_IPCOMP; default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "Invalid pfkey proto: %u\n", satype); return ~0; } @@ -701,7 +704,7 @@ ipsecdoi2pfkey_mode(mode) #endif return IPSEC_MODE_TRANSPORT; default: - plog(LLV_ERROR, LOCATION, NULL, "Invalid mode type: %u\n", mode); + plog(ASL_LEVEL_ERR, "Invalid mode type: %u\n", mode); return ~0; } /*NOTREACHED*/ @@ -720,7 +723,7 @@ pfkey2ipsecdoi_mode(mode) case IPSEC_MODE_ANY: return IPSECDOI_ATTR_ENC_MODE_ANY; default: - plog(LLV_ERROR, LOCATION, NULL, "Invalid mode type: %u\n", mode); + plog(ASL_LEVEL_ERR, "Invalid mode type: %u\n", mode); return ~0; } /*NOTREACHED*/ @@ -738,7 +741,7 @@ keylen_aalg(hashtype) res = alg_ipsec_hmacdef_hashlen(hashtype); if (res == -1) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid hmac algorithm %u.\n", hashtype); return ~0; } @@ -755,7 +758,7 @@ keylen_ealg(enctype, encklen) res = alg_ipsec_encdef_keylen(enctype, encklen); if (res == -1) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid encryption algorithm %u.\n", enctype); return ~0; } @@ -763,8 +766,9 @@ keylen_ealg(enctype, encklen) } int -pfkey_convertfromipsecdoi(proto_id, t_id, hashtype, +pfkey_convertfromipsecdoi(iph2, proto_id, t_id, hashtype, e_type, e_keylen, a_type, a_keylen, flags) + phase2_handle_t *iph2; u_int proto_id; u_int t_id; u_int hashtype; @@ -788,9 +792,9 @@ pfkey_convertfromipsecdoi(proto_id, t_id, hashtype, if ((*a_keylen = keylen_aalg(hashtype)) == ~0) goto bad; *a_keylen >>= 3; - + if (*e_type == SADB_EALG_NONE) { - plog(LLV_ERROR, LOCATION, NULL, "no ESP algorithm.\n"); + plog(ASL_LEVEL_ERR, "no ESP algorithm.\n"); goto bad; } break; @@ -811,7 +815,7 @@ pfkey_convertfromipsecdoi(proto_id, t_id, hashtype, *e_type = SADB_EALG_NONE; *e_keylen = 0; if (*a_type == SADB_AALG_NONE) { - plog(LLV_ERROR, LOCATION, NULL, "no AH algorithm.\n"); + plog(ASL_LEVEL_ERR, "no AH algorithm.\n"); goto bad; } break; @@ -826,13 +830,13 @@ pfkey_convertfromipsecdoi(proto_id, t_id, hashtype, *a_type = SADB_AALG_NONE; *a_keylen = 0; if (*e_type == SADB_X_CALG_NONE) { - plog(LLV_ERROR, LOCATION, NULL, "no IPCOMP algorithm.\n"); + plog(ASL_LEVEL_ERR, "no IPCOMP algorithm.\n"); goto bad; } break; default: - plog(LLV_ERROR, LOCATION, NULL, "unknown IPsec protocol.\n"); + plog(ASL_LEVEL_ERR, "unknown IPsec protocol.\n"); goto bad; } @@ -849,25 +853,23 @@ pfkey_timeover_stub(p) void *p; { - pfkey_timeover((struct ph2handle *)p); + pfkey_timeover((phase2_handle_t *)p); } void pfkey_timeover(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "%s give up to get IPsec-SA due to time up to wait.\n", - saddrwop2str(iph2->dst)); + saddrwop2str((struct sockaddr *)iph2->dst)); SCHED_KILL(iph2->sce); /* If initiator side, send error to kernel by SADB_ACQUIRE. */ if (iph2->side == INITIATOR) pk_sendeacquire(iph2); - unbindph12(iph2); - remph2(iph2); - delph2(iph2); + ike_session_unlink_phase2(iph2); return; } @@ -881,9 +883,9 @@ pfkey_timeover(iph2) */ int pk_sendgetspi(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { - struct sockaddr *src = NULL, *dst = NULL; + struct sockaddr_storage *src = NULL, *dst = NULL; u_int satype, mode; struct saprop *pp; struct saproto *pr; @@ -914,7 +916,7 @@ pk_sendgetspi(iph2) /* validity check */ satype = ipsecdoi2pfkey_proto(pr->proto_id); if (satype == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid proto_id %d\n", pr->proto_id); return -1; } @@ -930,12 +932,12 @@ pk_sendgetspi(iph2) } mode = ipsecdoi2pfkey_mode(pr->encmode); if (mode == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid encmode %d\n", pr->encmode); return -1; } - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_getspi\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_getspi\n"); if (pfkey_send_getspi( lcconf->sock_pfkey, satype, @@ -943,13 +945,14 @@ pk_sendgetspi(iph2) dst, /* src of SA */ src, /* dst of SA */ minspi, maxspi, - pr->reqid_in, iph2->seq) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + pr->reqid_in, 0, 0, iph2->seq, 0) < 0) { + plog(ASL_LEVEL_ERR, "ipseclib failed send getspi (%s)\n", ipsec_strerror()); return -1; } - plog(LLV_DEBUG, LOCATION, NULL, + + plog(ASL_LEVEL_DEBUG, "pfkey GETSPI sent: %s\n", sadbsecas2str(dst, src, satype, 0, mode)); } @@ -966,8 +969,8 @@ pk_recvgetspi(mhp) { struct sadb_msg *msg; struct sadb_sa *sa; - struct ph2handle *iph2; - struct sockaddr *dst; + phase2_handle_t *iph2; + struct sockaddr_storage *dst; int proto_id; int allspiok, notfound; struct saprop *pp; @@ -976,17 +979,17 @@ pk_recvgetspi(mhp) /* validity check */ if (mhp[SADB_EXT_SA] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, - "inappropriate sadb getspi message passed.\n"); + plog(ASL_LEVEL_ERR, + "Inappropriate sadb getspi message passed.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; - sa = (struct sadb_sa *)mhp[SADB_EXT_SA]; - dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); /* note SA dir */ + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + sa = ALIGNED_CAST(struct sadb_sa *)mhp[SADB_EXT_SA]; + dst = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); /* note SA dir */ /* the message has to be processed or not ? */ if (msg->sadb_msg_pid != getpid()) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "%s message is not interesting " "because pid %d is not mine.\n", s_pfkey_type(msg->sadb_msg_type), @@ -994,40 +997,43 @@ pk_recvgetspi(mhp) return -1; } - iph2 = getph2byseq(msg->sadb_msg_seq); + iph2 = ike_session_getph2byseq(msg->sadb_msg_seq); if (iph2 == NULL) { - plog(LLV_DEBUG, LOCATION, NULL, - "seq %d of %s message not interesting.\n", + plog(ASL_LEVEL_DEBUG, + "Seq %d of %s message not interesting.\n", msg->sadb_msg_seq, s_pfkey_type(msg->sadb_msg_type)); return -1; } if (iph2->is_dying) { - plog(LLV_ERROR, LOCATION, NULL, - "status mismatch phase2 dying (db:%d msg:%d)\n", - iph2->status, PHASE2ST_GETSPISENT); - return -1; - } - - if (iph2->status != PHASE2ST_GETSPISENT) { - plog(LLV_ERROR, LOCATION, NULL, - "status mismatch (db:%d msg:%d)\n", - iph2->status, PHASE2ST_GETSPISENT); + plog(ASL_LEVEL_ERR, + "Status mismatch Phase 2 dying (db:%d)\n", + iph2->status); return -1; } - - // check the underlying iph2->ph1 - if (!iph2->ph1) { - if (!ike_session_update_ph2_ph1bind(iph2)) { - plog(LLV_ERROR, LOCATION, NULL, - "can't proceed with getspi for %s. no suitable ISAKMP-SA found \n", - saddrwop2str(iph2->dst)); - unbindph12(iph2); - remph2(iph2); - delph2(iph2); + + switch (iph2->version) { + case ISAKMP_VERSION_NUMBER_IKEV1: + if (iph2->status != IKEV1_STATE_QUICK_I_GETSPISENT && + iph2->status != IKEV1_STATE_QUICK_R_GETSPISENT) { + plog(ASL_LEVEL_ERR, "Status mismatch (db:%d)\n", iph2->status); + return -1; + } + // check the underlying iph2->ph1 + if (!iph2->ph1) { + if (!ike_session_update_ph2_ph1bind(iph2)) { + plog(ASL_LEVEL_ERR, + "Can't proceed with getspi for %s. no suitable ISAKMP-SA found \n", + saddrwop2str((struct sockaddr *)iph2->dst)); + ike_session_unlink_phase2(iph2); + return -1; + } + } + break; + default: + plog(ASL_LEVEL_ERR, "Internal error: invalid IKE major version %d\n", iph2->version); return -1; - } } /* set SPI, and check to get all spi whether or not */ @@ -1040,7 +1046,7 @@ pk_recvgetspi(mhp) if (pr->proto_id == proto_id && pr->spi == 0) { pr->spi = sa->sadb_sa_spi; notfound = 0; - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "pfkey GETSPI succeeded: %s\n", sadbsecas2str(iph2->dst, iph2->src, msg->sadb_msg_satype, @@ -1052,29 +1058,25 @@ pk_recvgetspi(mhp) } if (notfound) { - plog(LLV_ERROR, LOCATION, NULL, - "get spi for unknown address %s\n", - saddrwop2str(iph2->dst)); - unbindph12(iph2); - remph2(iph2); - delph2(iph2); + plog(ASL_LEVEL_ERR, + "Get spi for unknown address %s\n", + saddrwop2str((struct sockaddr *)iph2->dst)); + ike_session_unlink_phase2(iph2); return -1; } if (allspiok) { - /* update status */ - iph2->status = PHASE2ST_GETSPIDONE; - if (isakmp_post_getspi(iph2) < 0) { - plog(LLV_ERROR, LOCATION, NULL, - "failed to start post getspi.\n"); - unbindph12(iph2); - remph2(iph2); - delph2(iph2); - iph2 = NULL; - return -1; - } - } - + switch (iph2->version) { + case ISAKMP_VERSION_NUMBER_IKEV1: + if (isakmp_post_getspi(iph2) < 0) { + plog(ASL_LEVEL_ERR, "IKEv1 post getspi failed.\n"); + ike_session_unlink_phase2(iph2); + iph2 = NULL; + return -1; + } + break; + } + } return 0; } @@ -1083,21 +1085,22 @@ pk_recvgetspi(mhp) */ int pk_sendupdate(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { struct saproto *pr; - struct sockaddr *src = NULL, *dst = NULL; + struct sockaddr_storage *src = NULL, *dst = NULL; u_int e_type, e_keylen, a_type, a_keylen, flags; u_int satype, mode; u_int64_t lifebyte = 0; u_int wsize = 4; /* XXX static size of window */ int proxy = 0; struct ph2natt natt; + int authtype; /* sanity check */ if (iph2->approval == NULL) { - plog(LLV_ERROR, LOCATION, NULL, - "no approvaled SAs found.\n"); + plog(ASL_LEVEL_ERR, + "No approved SAs found.\n"); } if (iph2->side == INITIATOR) @@ -1119,8 +1122,8 @@ pk_sendupdate(iph2) /* validity check */ satype = ipsecdoi2pfkey_proto(pr->proto_id); if (satype == ~0) { - plog(LLV_ERROR, LOCATION, NULL, - "invalid proto_id %d\n", pr->proto_id); + plog(ASL_LEVEL_ERR, + "Invalid proto_id %d\n", pr->proto_id); return -1; } else if (satype == SADB_X_SATYPE_IPCOMP) { @@ -1132,18 +1135,21 @@ pk_sendupdate(iph2) #else mode = ipsecdoi2pfkey_mode(pr->encmode); if (mode == ~0) { - plog(LLV_ERROR, LOCATION, NULL, - "invalid encmode %d\n", pr->encmode); + plog(ASL_LEVEL_ERR, + "Invalid encmode %d\n", pr->encmode); return -1; } #endif /* set algorithm type and key length */ e_keylen = pr->head->encklen; + authtype = pr->head->authtype; + a_keylen = 0; if (pfkey_convertfromipsecdoi( + iph2, pr->proto_id, pr->head->trns_id, - pr->head->authtype, + authtype, &e_type, &e_keylen, &a_type, &a_keylen, &flags) < 0) return -1; @@ -1155,20 +1161,25 @@ pk_sendupdate(iph2) #endif #ifdef ENABLE_NATT - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_update\n"); + //plog(ASL_LEVEL_DEBUG, "call pfkey_send_update\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_update: e_type %d, e_klen %d, a_type %d, a_klen %d\n", + e_type, e_keylen, a_type, a_keylen); if (pr->udp_encap) { memset (&natt, 0, sizeof (natt)); natt.sport = extract_port (iph2->ph1->remote); flags |= SADB_X_EXT_NATT; - if (iph2->ph1->natt_flags & NAT_DETECTED_ME) { + if (iph2->ph1->rmconf->natt_multiple_user == TRUE && + mode == IPSEC_MODE_TRANSPORT && + src->ss_family == AF_INET) { + flags |= SADB_X_EXT_NATT_MULTIPLEUSERS; + if (iph2->ph1->natt_flags & NAT_DETECTED_PEER) { + // is mutually exclusive with SADB_X_EXT_NATT_KEEPALIVE + flags |= SADB_X_EXT_NATT_DETECTED_PEER; + } + } else if (iph2->ph1->natt_flags & NAT_DETECTED_ME) { if (iph2->ph1->rmconf->natt_keepalive == TRUE) flags |= SADB_X_EXT_NATT_KEEPALIVE; } else { - if (iph2->ph1->rmconf->natt_multiple_user == TRUE && - mode == IPSEC_MODE_TRANSPORT && - src->sa_family == AF_INET) { - flags |= SADB_X_EXT_NATT_MULTIPLEUSERS; - } if (iph2->ph1->natt_flags & NAT_DETECTED_PEER) { // is mutually exclusive with SADB_X_EXT_NATT_KEEPALIVE flags |= SADB_X_EXT_NATT_DETECTED_PEER; @@ -1190,14 +1201,14 @@ pk_sendupdate(iph2) pr->keymat->v, e_type, e_keylen, a_type, a_keylen, flags, 0, lifebyte, iph2->approval->lifetime, 0, - iph2->seq, natt.sport) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + iph2->seq, natt.sport, 0) < 0) { + plog(ASL_LEVEL_ERR, "libipsec failed send update (%s)\n", ipsec_strerror()); return -1; } #else - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_update\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_update\n"); if (pfkey_send_update( lcconf->sock_pfkey, satype, @@ -1210,39 +1221,15 @@ pk_sendupdate(iph2) pr->keymat->v, e_type, e_keylen, a_type, a_keylen, flags, 0, lifebyte, iph2->approval->lifetime, 0, - iph2->seq, 0) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + iph2->seq, 0, 0) < 0) { + plog(ASL_LEVEL_ERR, "libipsec failed send update (%s)\n", ipsec_strerror()); return -1; } #endif /* ENABLE_NATT */ - if (!lcconf->pathinfo[LC_PATHTYPE_BACKUPSA]) - continue; - /* - * It maybe good idea to call backupsa_to_file() after - * racoon will receive the sadb_update messages. - * But it is impossible because there is not key in the - * information from the kernel. - */ - if (backupsa_to_file(satype, mode, dst, src, - pr->spi, pr->reqid_in, 4, - pr->keymat->v, - e_type, e_keylen, a_type, a_keylen, flags, - 0, iph2->approval->lifebyte * 1024, - iph2->approval->lifetime, 0, - iph2->seq) < 0) { - plog(LLV_ERROR, LOCATION, NULL, - "backuped SA failed: %s\n", - sadbsecas2str(dst, src, - satype, pr->spi, mode)); - } - plog(LLV_DEBUG, LOCATION, NULL, - "backuped SA: %s\n", - sadbsecas2str(dst, src, - satype, pr->spi, mode)); } return 0; @@ -1254,8 +1241,8 @@ pk_recvupdate(mhp) { struct sadb_msg *msg; struct sadb_sa *sa; - struct sockaddr *src, *dst; - struct ph2handle *iph2; + struct sockaddr_storage *src, *dst; + phase2_handle_t *iph2; u_int proto_id, encmode, sa_mode; int incomplete = 0; struct saproto *pr; @@ -1269,22 +1256,22 @@ pk_recvupdate(mhp) || mhp[SADB_EXT_SA] == NULL || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb update message passed.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; - src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); - dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); - sa = (struct sadb_sa *)mhp[SADB_EXT_SA]; + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + src = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); + dst = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); + sa = ALIGNED_CAST(struct sadb_sa *)mhp[SADB_EXT_SA]; sa_mode = mhp[SADB_X_EXT_SA2] == NULL ? IPSEC_MODE_ANY - : ((struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode; + : (ALIGNED_CAST(struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode; /* the message has to be processed or not ? */ if (msg->sadb_msg_pid != getpid()) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "%s message is not interesting " "because pid %d is not mine.\n", s_pfkey_type(msg->sadb_msg_type), @@ -1292,26 +1279,26 @@ pk_recvupdate(mhp) return -1; } - iph2 = getph2byseq(msg->sadb_msg_seq); + iph2 = ike_session_getph2byseq(msg->sadb_msg_seq); if (iph2 == NULL) { - plog(LLV_DEBUG, LOCATION, NULL, - "seq %d of %s message not interesting.\n", + plog(ASL_LEVEL_DEBUG, + "Seq %d of %s message not interesting.\n", msg->sadb_msg_seq, s_pfkey_type(msg->sadb_msg_type)); return -1; } if (iph2->is_dying) { - plog(LLV_ERROR, LOCATION, NULL, - "status mismatch phase2 dying (db:%d msg:%d)\n", - iph2->status, PHASE2ST_ADDSA); + plog(ASL_LEVEL_ERR, + "Status mismatch Phase 2 dying (db:%d)\n", + iph2->status); return -1; } - - if (iph2->status != PHASE2ST_ADDSA) { - plog(LLV_ERROR, LOCATION, NULL, - "status mismatch (db:%d msg:%d)\n", - iph2->status, PHASE2ST_ADDSA); + if (iph2->status != IKEV1_STATE_QUICK_I_ADDSA && + iph2->status != IKEV1_STATE_QUICK_R_ADDSA) { + plog(ASL_LEVEL_ERR, + "Status mismatch (db:%d)\n", + iph2->status); return -1; } @@ -1319,13 +1306,13 @@ pk_recvupdate(mhp) for (pr = iph2->approval->head; pr != NULL; pr = pr->next) { proto_id = pfkey2ipsecdoi_proto(msg->sadb_msg_satype); if (proto_id == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid proto_id %d\n", msg->sadb_msg_satype); return -1; } encmode = pfkey2ipsecdoi_mode(sa_mode); if (encmode == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid encmode %d\n", sa_mode); return -1; } @@ -1333,14 +1320,14 @@ pk_recvupdate(mhp) if (pr->proto_id == proto_id && pr->spi == sa->sadb_sa_spi) { pr->ok = 1; - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "pfkey UPDATE succeeded: %s\n", sadbsecas2str(iph2->dst, iph2->src, msg->sadb_msg_satype, sa->sadb_sa_spi, sa_mode)); - plog(LLV_INFO, LOCATION, NULL, + plog(ASL_LEVEL_INFO, "IPsec-SA established: %s\n", sadbsecas2str(iph2->dst, iph2->src, msg->sadb_msg_satype, sa->sadb_sa_spi, @@ -1358,7 +1345,7 @@ pk_recvupdate(mhp) SCHED_KILL(iph2->sce); /* update status */ - iph2->status = PHASE2ST_ESTABLISHED; + fsm_set_state(&iph2->status, IKEV1_STATE_PHASE2_ESTABLISHED); if (iph2->side == INITIATOR) { IPSECSESSIONTRACEREVENT(iph2->parent_session, @@ -1374,13 +1361,13 @@ pk_recvupdate(mhp) ike_session_ph2_established(iph2); - IPSECLOGASLMSG("IPSec Phase2 established (Initiated by %s).\n", + IPSECLOGASLMSG("IPSec Phase 2 established (Initiated by %s).\n", (iph2->side == INITIATOR)? "me" : "peer"); #ifdef ENABLE_STATS gettimeofday(&iph2->end, NULL); - syslog(LOG_NOTICE, "%s(%s): %8.6f", - "phase2", "quick", timedelta(&iph2->start, &iph2->end)); + plog(ASL_LEVEL_NOTICE, "%s(%s): %8.6f", + "Phase 2", "quick", timedelta(&iph2->start, &iph2->end)); #endif /* count up */ @@ -1395,12 +1382,12 @@ pk_recvupdate(mhp) * since we are going to reuse the phase2 handler, we need to * remain it and refresh all the references between ph1 and ph2 to use. */ - unbindph12(iph2); + ike_session_unbindph12(iph2); //%%%%% fix this iph2->sce = sched_new(iph2->approval->lifetime, isakmp_ph2expire_stub, iph2); - plog(LLV_DEBUG, LOCATION, NULL, "===\n"); + plog(ASL_LEVEL_DEBUG, "===\n"); return 0; } @@ -1409,20 +1396,21 @@ pk_recvupdate(mhp) */ int pk_sendadd(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { struct saproto *pr; - struct sockaddr *src = NULL, *dst = NULL; + struct sockaddr_storage *src = NULL, *dst = NULL; u_int e_type, e_keylen, a_type, a_keylen, flags; u_int satype, mode; u_int64_t lifebyte = 0; u_int wsize = 4; /* XXX static size of window */ int proxy = 0; struct ph2natt natt; + int authtype; /* sanity check */ if (iph2->approval == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "no approvaled SAs found.\n"); } @@ -1445,7 +1433,7 @@ pk_sendadd(iph2) /* validity check */ satype = ipsecdoi2pfkey_proto(pr->proto_id); if (satype == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid proto_id %d\n", pr->proto_id); return -1; } @@ -1458,7 +1446,7 @@ pk_sendadd(iph2) #else mode = ipsecdoi2pfkey_mode(pr->encmode); if (mode == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid encmode %d\n", pr->encmode); return -1; } @@ -1466,10 +1454,13 @@ pk_sendadd(iph2) /* set algorithm type and key length */ e_keylen = pr->head->encklen; + authtype = pr->head->authtype; + a_keylen = 0; if (pfkey_convertfromipsecdoi( + iph2, pr->proto_id, pr->head->trns_id, - pr->head->authtype, + authtype, &e_type, &e_keylen, &a_type, &a_keylen, &flags) < 0) return -1; @@ -1481,21 +1472,26 @@ pk_sendadd(iph2) #endif #ifdef ENABLE_NATT - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_add\n"); + //plog(ASL_LEVEL_DEBUG, "call pfkey_send_add\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_add: e_type %d, e_klen %d, a_type %d, a_klen %d\n", + e_type, e_keylen, a_type, a_keylen); if (pr->udp_encap) { memset (&natt, 0, sizeof (natt)); natt.dport = extract_port (iph2->ph1->remote); flags |= SADB_X_EXT_NATT; - if (iph2->ph1->natt_flags & NAT_DETECTED_ME) { + if (iph2->ph1->rmconf->natt_multiple_user == TRUE && + mode == IPSEC_MODE_TRANSPORT && + src->ss_family == AF_INET) { + flags |= SADB_X_EXT_NATT_MULTIPLEUSERS; + if (iph2->ph1->natt_flags & NAT_DETECTED_PEER) { + // is mutually exclusive with SADB_X_EXT_NATT_KEEPALIVE + flags |= SADB_X_EXT_NATT_DETECTED_PEER; + } + } else if (iph2->ph1->natt_flags & NAT_DETECTED_ME) { if (iph2->ph1->rmconf->natt_keepalive == TRUE) flags |= SADB_X_EXT_NATT_KEEPALIVE; } else { - if (iph2->ph1->rmconf->natt_multiple_user == TRUE && - mode == IPSEC_MODE_TRANSPORT && - dst->sa_family == AF_INET) { - flags |= SADB_X_EXT_NATT_MULTIPLEUSERS; - } if (iph2->ph1->natt_flags & NAT_DETECTED_PEER) { // is mutually exclusive with SADB_X_EXT_NATT_KEEPALIVE flags |= SADB_X_EXT_NATT_DETECTED_PEER; @@ -1521,14 +1517,14 @@ pk_sendadd(iph2) pr->keymat_p->v, e_type, e_keylen, a_type, a_keylen, flags, 0, lifebyte, iph2->approval->lifetime, 0, - iph2->seq,natt.dport) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + iph2->seq,natt.dport, 0) < 0) { + plog(ASL_LEVEL_ERR, "libipsec failed send add (%s)\n", ipsec_strerror()); return -1; } #else - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_add\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_add\n"); /* Remove port information, it is not used without NAT-T */ //set_port(src, 0); @@ -1546,38 +1542,13 @@ pk_sendadd(iph2) pr->keymat_p->v, e_type, e_keylen, a_type, a_keylen, flags, 0, lifebyte, iph2->approval->lifetime, 0, - iph2->seq, 0) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + iph2->seq, 0, 0) < 0) { + plog(ASL_LEVEL_ERR, "libipsec failed send add (%s)\n", ipsec_strerror()); return -1; } #endif /* ENABLE_NATT */ - if (!lcconf->pathinfo[LC_PATHTYPE_BACKUPSA]) - continue; - - /* - * It maybe good idea to call backupsa_to_file() after - * racoon will receive the sadb_update messages. - * But it is impossible because there is not key in the - * information from the kernel. - */ - if (backupsa_to_file(satype, mode, src, dst, - pr->spi_p, pr->reqid_out, 4, - pr->keymat_p->v, - e_type, e_keylen, a_type, a_keylen, flags, - 0, iph2->approval->lifebyte * 1024, - iph2->approval->lifetime, 0, - iph2->seq) < 0) { - plog(LLV_ERROR, LOCATION, NULL, - "backuped SA failed: %s\n", - sadbsecas2str(src, dst, - satype, pr->spi_p, mode)); - } - plog(LLV_DEBUG, LOCATION, NULL, - "backuped SA: %s\n", - sadbsecas2str(src, dst, - satype, pr->spi_p, mode)); } return 0; @@ -1589,8 +1560,8 @@ pk_recvadd(mhp) { struct sadb_msg *msg; struct sadb_sa *sa; - struct sockaddr *src, *dst; - struct ph2handle *iph2; + struct sockaddr_storage *src, *dst; + phase2_handle_t *iph2; u_int sa_mode; /* ignore this message because of local test mode. */ @@ -1602,22 +1573,22 @@ pk_recvadd(mhp) || mhp[SADB_EXT_SA] == NULL || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb add message passed.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; - src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); - dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); - sa = (struct sadb_sa *)mhp[SADB_EXT_SA]; + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + src = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); + dst = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); + sa = ALIGNED_CAST(struct sadb_sa *)mhp[SADB_EXT_SA]; sa_mode = mhp[SADB_X_EXT_SA2] == NULL ? IPSEC_MODE_ANY - : ((struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode; + : (ALIGNED_CAST(struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode; /* the message has to be processed or not ? */ if (msg->sadb_msg_pid != getpid()) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "%s message is not interesting " "because pid %d is not mine.\n", s_pfkey_type(msg->sadb_msg_type), @@ -1625,21 +1596,20 @@ pk_recvadd(mhp) return -1; } - iph2 = getph2byseq(msg->sadb_msg_seq); + iph2 = ike_session_getph2byseq(msg->sadb_msg_seq); if (iph2 == NULL) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "seq %d of %s message not interesting.\n", msg->sadb_msg_seq, s_pfkey_type(msg->sadb_msg_type)); return -1; } - /* * NOTE don't update any status of phase2 handle * because they must be updated by SADB_UPDATE message */ - plog(LLV_INFO, LOCATION, NULL, + plog(ASL_LEVEL_INFO, "IPsec-SA established: %s\n", sadbsecas2str(iph2->src, iph2->dst, msg->sadb_msg_satype, sa->sadb_sa_spi, sa_mode)); @@ -1650,7 +1620,7 @@ pk_recvadd(mhp) { u_int32_t address; - if (iph2->dst->sa_family == AF_INET) + if (iph2->dst->ss_family == AF_INET) address = ((struct sockaddr_in *)iph2->dst)->sin_addr.s_addr; else address = 0; @@ -1658,7 +1628,7 @@ pk_recvadd(mhp) } #endif - plog(LLV_DEBUG, LOCATION, NULL, "===\n"); + plog(ASL_LEVEL_DEBUG, "===\n"); return 0; } @@ -1668,8 +1638,8 @@ pk_recvexpire(mhp) { struct sadb_msg *msg; struct sadb_sa *sa; - struct sockaddr *src, *dst; - struct ph2handle *iph2; + struct sockaddr_storage *src, *dst; + phase2_handle_t *iph2; u_int proto_id, sa_mode; /* sanity check */ @@ -1679,46 +1649,46 @@ pk_recvexpire(mhp) || mhp[SADB_EXT_ADDRESS_DST] == NULL || (mhp[SADB_EXT_LIFETIME_HARD] != NULL && mhp[SADB_EXT_LIFETIME_SOFT] != NULL)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb expire message passed.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; - sa = (struct sadb_sa *)mhp[SADB_EXT_SA]; - src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); - dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + sa = ALIGNED_CAST(struct sadb_sa *)mhp[SADB_EXT_SA]; + src = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); + dst = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); sa_mode = mhp[SADB_X_EXT_SA2] == NULL ? IPSEC_MODE_ANY - : ((struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode; + : (ALIGNED_CAST(struct sadb_x_sa2 *)mhp[SADB_X_EXT_SA2])->sadb_x_sa2_mode; proto_id = pfkey2ipsecdoi_proto(msg->sadb_msg_satype); if (proto_id == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid proto_id %d\n", msg->sadb_msg_satype); return -1; } - plog(LLV_INFO, LOCATION, NULL, + plog(ASL_LEVEL_INFO, "IPsec-SA expired: %s\n", sadbsecas2str(src, dst, msg->sadb_msg_satype, sa->sadb_sa_spi, sa_mode)); - iph2 = getph2bysaidx(src, dst, proto_id, sa->sadb_sa_spi); + iph2 = ike_session_getph2bysaidx(src, dst, proto_id, sa->sadb_sa_spi); if (iph2 == NULL) { /* * Ignore it because two expire messages are come up. * phase2 handler has been deleted already when 2nd message * is received. */ - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "no such a SA found: %s\n", sadbsecas2str(src, dst, msg->sadb_msg_satype, sa->sadb_sa_spi, sa_mode)); return 0; } - if (iph2->is_dying || iph2->status != PHASE2ST_ESTABLISHED) { + if (iph2->is_dying || !FSM_STATE_IS_ESTABLISHED(iph2->status)) { /* * If the status is not equal to PHASE2ST_ESTABLISHED, * racoon ignores this expire message. There are two reason. @@ -1727,36 +1697,31 @@ pk_recvexpire(mhp) * without receiving a expire message. Another is that racoon * may receive the multiple expire messages from the kernel. */ - plog(LLV_WARNING, LOCATION, NULL, - "the expire message is received " - "but the handler is dying or has not been established.\n"); + plog(ASL_LEVEL_WARNING, + "The expire message is received but the handler %s (status = 0x%x).\n", + iph2->is_dying ? "is dying" : "has not been established", iph2->status); return 0; } /* turn off the timer for calling isakmp_ph2expire() */ SCHED_KILL(iph2->sce); - - iph2->status = PHASE2ST_EXPIRED; - + + fsm_set_state(&iph2->status, IKEV1_STATE_PHASE2_EXPIRED); + /* INITIATOR, begin phase 2 exchange only if there's no other established ph2. */ /* allocate buffer for status management of pfkey message */ if (iph2->side == INITIATOR && !ike_session_has_other_established_ph2(iph2->parent_session, iph2) && !ike_session_drop_rekey(iph2->parent_session, IKE_SESSION_REKEY_TYPE_PH2)) { - initph2(iph2); - - /* update status for re-use */ - iph2->status = PHASE2ST_STATUS2; + ike_session_initph2(iph2); /* start isakmp initiation by using ident exchange */ if (isakmp_post_acquire(iph2) < 0) { - plog(LLV_ERROR, LOCATION, iph2->dst, + plog(ASL_LEVEL_ERR, "failed to begin ipsec sa " "re-negotiation.\n"); - unbindph12(iph2); - remph2(iph2); - delph2(iph2); + ike_session_unlink_phase2(iph2); return -1; } @@ -1764,12 +1729,11 @@ pk_recvexpire(mhp) /*NOTREACHED*/ } + /* If not received SADB_EXPIRE, INITIATOR delete ph2handle. */ /* RESPONDER always delete ph2handle, keep silent. RESPONDER doesn't * manage IPsec SA, so delete the list */ - unbindph12(iph2); - remph2(iph2); - delph2(iph2); + ike_session_unlink_phase2(iph2); return 0; } @@ -1781,10 +1745,10 @@ pk_recvacquire(mhp) struct sadb_msg *msg; struct sadb_x_policy *xpl; struct secpolicy *sp_out = NULL, *sp_in = NULL; -#define MAXNESTEDSA 5 /* XXX */ - struct ph2handle *iph2[MAXNESTEDSA]; - struct sockaddr *src, *dst; - int n; /* # of phase 2 handler */ + phase2_handle_t *iph2; + struct sockaddr_storage *src, *dst; + ike_session_t *session = NULL; + struct remoteconf *rmconf; /* ignore this message because of local test mode. */ if (f_local) @@ -1795,36 +1759,36 @@ pk_recvacquire(mhp) || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL || mhp[SADB_X_EXT_POLICY] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb acquire message passed.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; - xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; - src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); - dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + xpl = ALIGNED_CAST(struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; + src = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); + dst = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); /* ignore if type is not IPSEC_POLICY_IPSEC */ if (xpl->sadb_x_policy_type != IPSEC_POLICY_IPSEC) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "ignore ACQUIRE message. type is not IPsec.\n"); return 0; } /* ignore it if src is multicast address */ { - struct sockaddr *sa = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); + struct sockaddr_storage *sa = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); - if ((sa->sa_family == AF_INET + if ((sa->ss_family == AF_INET && IN_MULTICAST(ntohl(((struct sockaddr_in *)sa)->sin_addr.s_addr))) #ifdef INET6 - || (sa->sa_family == AF_INET6 + || (sa->ss_family == AF_INET6 && IN6_IS_ADDR_MULTICAST(&((struct sockaddr_in6 *)sa)->sin6_addr)) #endif ) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "ignore due to multicast address: %s.\n", - saddrwop2str(sa)); + saddrwop2str((struct sockaddr *)sa)); return 0; } } @@ -1839,10 +1803,16 @@ pk_recvacquire(mhp) * than one in the policy, so kernel will drop them; * => therefore this acquire is not for us! --Aidas */ - struct sockaddr *sa = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); + // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + struct sockaddr_storage *sa = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); struct myaddrs *p; int do_listen = 0; + char * str; for (p = lcconf->myaddrs; p; p = p->next) { + str = saddr2str((struct sockaddr *)p->addr); + plog(ASL_LEVEL_DEBUG, + "checking listen addrs: %s", str); + if (!cmpsaddrwop(p->addr, sa)) { do_listen = 1; break; @@ -1850,9 +1820,9 @@ pk_recvacquire(mhp) } if (!do_listen) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "ignore because do not listen on source address : %s.\n", - saddrwop2str(sa)); + saddrwop2str((struct sockaddr *)sa)); return 0; } } @@ -1867,137 +1837,148 @@ pk_recvacquire(mhp) * has to process such a acquire message because racoon may * have lost the expire message. */ - iph2[0] = getph2byid(src, dst, xpl->sadb_x_policy_id); - if (iph2[0] != NULL) { - if (iph2[0]->status < PHASE2ST_ESTABLISHED) { - plog(LLV_DEBUG, LOCATION, NULL, + iph2 = ike_session_getph2byid(src, dst, xpl->sadb_x_policy_id); + if (iph2 != NULL) { + session = iph2->parent_session; + if (!FSM_STATE_IS_ESTABLISHED(iph2->status)) { + plog(ASL_LEVEL_DEBUG, "ignore the acquire because ph2 found\n"); return -1; } - if (iph2[0]->status == PHASE2ST_EXPIRED) - iph2[0] = NULL; + if (FSM_STATE_IS_EXPIRED(iph2->status)) + iph2 = NULL; /*FALLTHROUGH*/ } /* search for proper policyindex */ sp_out = getspbyspid(xpl->sadb_x_policy_id); if (sp_out == NULL) { - plog(LLV_ERROR, LOCATION, NULL, "no policy found: id:%d.\n", + plog(ASL_LEVEL_ERR, "no policy found: id:%d.\n", xpl->sadb_x_policy_id); return -1; } - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "suitable outbound SP found: %s.\n", spidx2str(&sp_out->spidx)); /* get inbound policy */ { - struct policyindex spidx; - - spidx.dir = IPSEC_DIR_INBOUND; - memcpy(&spidx.src, &sp_out->spidx.dst, sizeof(spidx.src)); - memcpy(&spidx.dst, &sp_out->spidx.src, sizeof(spidx.dst)); - spidx.prefs = sp_out->spidx.prefd; - spidx.prefd = sp_out->spidx.prefs; - spidx.ul_proto = sp_out->spidx.ul_proto; - - sp_in = getsp(&spidx); - if (sp_in) { - plog(LLV_DEBUG, LOCATION, NULL, - "suitable inbound SP found: %s.\n", - spidx2str(&sp_in->spidx)); - } else { - plog(LLV_NOTIFY, LOCATION, NULL, - "no in-bound policy found: %s\n", - spidx2str(&spidx)); - } + struct policyindex spidx; + + spidx.dir = IPSEC_DIR_INBOUND; + memcpy(&spidx.src, &sp_out->spidx.dst, sizeof(spidx.src)); + memcpy(&spidx.dst, &sp_out->spidx.src, sizeof(spidx.dst)); + spidx.prefs = sp_out->spidx.prefd; + spidx.prefd = sp_out->spidx.prefs; + spidx.ul_proto = sp_out->spidx.ul_proto; + + sp_in = getsp(&spidx); + if (sp_in) { + plog(ASL_LEVEL_DEBUG, + "Suitable inbound SP found: %s.\n", + spidx2str(&sp_in->spidx)); + } else { + plog(ASL_LEVEL_NOTICE, + "No in-bound policy found: %s\n", + spidx2str(&spidx)); + } } - - memset(iph2, 0, MAXNESTEDSA); - - n = 0; - + /* allocate a phase 2 */ - iph2[n] = newph2(); - if (iph2[n] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, - "failed to allocate phase2 entry.\n"); + rmconf = getrmconf(dst); + if (rmconf == NULL) { + plog(ASL_LEVEL_ERR, "No configuration found for %s.\n", + saddrwop2str((struct sockaddr *)dst)); + return -1; + } + + iph2 = ike_session_newph2(rmconf->ike_version, PHASE2_TYPE_SA); + if (iph2 == NULL) { + plog(ASL_LEVEL_ERR, + "Failed to allocate Phase 2 entry.\n"); return -1; } - iph2[n]->side = INITIATOR; - iph2[n]->spid = xpl->sadb_x_policy_id; - iph2[n]->satype = msg->sadb_msg_satype; - iph2[n]->seq = msg->sadb_msg_seq; - iph2[n]->status = PHASE2ST_STATUS2; + plog(ASL_LEVEL_DEBUG, "Got new Phase 2 version %d\n", iph2->version); + iph2->version = rmconf->ike_version; + iph2->side = INITIATOR; + iph2->spid = xpl->sadb_x_policy_id; + iph2->satype = msg->sadb_msg_satype; + iph2->seq = msg->sadb_msg_seq; /* set end addresses of SA */ - iph2[n]->dst = dupsaddr(PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST])); - if (iph2[n]->dst == NULL) { - delph2(iph2[n]); + // Wcast_align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + iph2->src = dupsaddr(ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC])); + if (iph2->src == NULL) { + ike_session_delph2(iph2); return -1; } - iph2[n]->src = dupsaddr(PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC])); - if (iph2[n]->src == NULL) { - delph2(iph2[n]); + iph2->dst = dupsaddr(ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST])); + if (iph2->dst == NULL) { + ike_session_delph2(iph2); return -1; + } + + if (iph2->version == ISAKMP_VERSION_NUMBER_IKEV1) { + fsm_set_state(&iph2->status, IKEV1_STATE_QUICK_I_START); } - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "new acquire %s\n", spidx2str(&sp_out->spidx)); /* get sainfo */ { - vchar_t *idsrc, *iddst; - - idsrc = ipsecdoi_sockaddr2id((struct sockaddr *)&sp_out->spidx.src, - sp_out->spidx.prefs, sp_out->spidx.ul_proto); - if (idsrc == NULL) { - plog(LLV_ERROR, LOCATION, NULL, - "failed to get ID for %s\n", - spidx2str(&sp_out->spidx)); - delph2(iph2[n]); - return -1; - } - iddst = ipsecdoi_sockaddr2id((struct sockaddr *)&sp_out->spidx.dst, - sp_out->spidx.prefd, sp_out->spidx.ul_proto); - if (iddst == NULL) { - plog(LLV_ERROR, LOCATION, NULL, - "failed to get ID for %s\n", - spidx2str(&sp_out->spidx)); - vfree(idsrc); - delph2(iph2[n]); - return -1; - } - iph2[n]->sainfo = getsainfo(idsrc, iddst, NULL, 0); - vfree(idsrc); - vfree(iddst); - if (iph2[n]->sainfo == NULL) { - plog(LLV_ERROR, LOCATION, NULL, - "failed to get sainfo.\n"); - delph2(iph2[n]); - return -1; - /* XXX should use the algorithm list from register message */ - } - if (link_sainfo_to_ph2(iph2[n]->sainfo) != 0) { - plog(LLV_ERROR, LOCATION, NULL, - "failed to link sainfo\n"); - iph2[n]->sainfo = NULL; - delph2(iph2[n]); - return -1; - } + vchar_t *idsrc, *iddst; + + idsrc = ipsecdoi_sockaddr2id(&sp_out->spidx.src, + sp_out->spidx.prefs, sp_out->spidx.ul_proto); + if (idsrc == NULL) { + plog(ASL_LEVEL_ERR, + "failed to get ID for %s\n", + spidx2str(&sp_out->spidx)); + ike_session_delph2(iph2); + return -1; + } + iddst = ipsecdoi_sockaddr2id(&sp_out->spidx.dst, + sp_out->spidx.prefd, sp_out->spidx.ul_proto); + if (iddst == NULL) { + plog(ASL_LEVEL_ERR, + "failed to get ID for %s\n", + spidx2str(&sp_out->spidx)); + vfree(idsrc); + ike_session_delph2(iph2); + return -1; + } + iph2->sainfo = getsainfo(idsrc, iddst, NULL, 0); + vfree(idsrc); + vfree(iddst); + if (iph2->sainfo == NULL) { + plog(ASL_LEVEL_ERR, + "failed to get sainfo.\n"); + ike_session_delph2(iph2); + return -1; + /* XXX should use the algorithm list from register message */ + } } + retain_sainfo(iph2->sainfo); - if (set_proposal_from_policy(iph2[n], sp_out, sp_in) < 0) { - plog(LLV_ERROR, LOCATION, NULL, - "failed to create saprop.\n"); - delph2(iph2[n]); + if (set_proposal_from_policy(iph2, sp_out, sp_in) < 0) { + plog(ASL_LEVEL_ERR, + "failed to create saprop.\n"); + ike_session_delph2(iph2); return -1; } - insph2(iph2[n]); + + if (session == NULL) + session = ike_session_get_session(iph2->src, iph2->dst, 1, NULL); + if (session == NULL) + fatal_error(-1); + + if (ike_session_link_phase2(session, iph2)) + fatal_error(-1); //????? fix ??? /* start isakmp initiation by using ident exchange */ /* XXX should be looped if there are multiple phase 2 handler. */ - if (isakmp_post_acquire(iph2[n]) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + if (isakmp_post_acquire(iph2) < 0) { + plog(ASL_LEVEL_ERR, "failed to begin ipsec sa negotiation.\n"); goto err; } @@ -2005,7 +1986,7 @@ pk_recvacquire(mhp) #if !TARGET_OS_EMBEDDED if ( lcconf->vt == NULL){ if (!(lcconf->vt = vproc_transaction_begin(NULL))) - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "vproc_transaction_begin returns NULL.\n"); } #endif @@ -2014,13 +1995,7 @@ pk_recvacquire(mhp) return 0; err: - while (n >= 0) { - unbindph12(iph2[n]); - remph2(iph2[n]); - delph2(iph2[n]); - iph2[n] = NULL; - n--; - } + ike_session_unlink_phase2(iph2); return -1; } @@ -2030,8 +2005,8 @@ pk_recvdelete(mhp) { struct sadb_msg *msg; struct sadb_sa *sa; - struct sockaddr *src, *dst; - struct ph2handle *iph2 = NULL; + struct sockaddr_storage *src, *dst; + phase2_handle_t *iph2 = NULL; u_int proto_id; /* ignore this message because of local test mode. */ @@ -2042,18 +2017,18 @@ pk_recvdelete(mhp) if (mhp[0] == NULL || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb delete message passed.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; - sa = (struct sadb_sa *)mhp[SADB_EXT_SA]; - src = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); - dst = PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + sa = ALIGNED_CAST(struct sadb_sa *)mhp[SADB_EXT_SA]; + src = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_SRC]); + dst = ALIGNED_CAST(struct sockaddr_storage *)PFKEY_ADDR_SADDR(mhp[SADB_EXT_ADDRESS_DST]); /* the message has to be processed or not ? */ if (msg->sadb_msg_pid == getpid()) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "%s message is not interesting " "because the message was originated by me.\n", s_pfkey_type(msg->sadb_msg_type)); @@ -2062,44 +2037,44 @@ pk_recvdelete(mhp) proto_id = pfkey2ipsecdoi_proto(msg->sadb_msg_satype); if (proto_id == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid proto_id %d\n", msg->sadb_msg_satype); return -1; } - plog(LLV_DEBUG2, LOCATION, NULL, "SADB delete message: proto-id %d\n", proto_id); - plog(LLV_DEBUG2, LOCATION, NULL, "src: %s\n", saddr2str(src)); - plog(LLV_DEBUG2, LOCATION, NULL, "dst: %s\n", saddr2str(dst)); + plog(ASL_LEVEL_DEBUG, "SADB delete message: proto-id %d\n", proto_id); + plog(ASL_LEVEL_DEBUG, "src: %s\n", saddr2str((struct sockaddr *)src)); + plog(ASL_LEVEL_DEBUG, "dst: %s\n", saddr2str((struct sockaddr *)dst)); if (!sa) { - deleteallph2(src, dst, proto_id); - deleteallph1(src, dst); + ike_session_deleteallph2(src, dst, proto_id); + ike_session_deleteallph1(src, dst); return 0; } - iph2 = getph2bysaidx(src, dst, proto_id, sa->sadb_sa_spi); + iph2 = ike_session_getph2bysaidx(src, dst, proto_id, sa->sadb_sa_spi); if (iph2 == NULL) { /* ignore */ - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "no iph2 found: %s\n", sadbsecas2str(src, dst, msg->sadb_msg_satype, sa->sadb_sa_spi, IPSEC_MODE_ANY)); return 0; } - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "pfkey DELETE received: %s\n", sadbsecas2str(iph2->src, iph2->dst, msg->sadb_msg_satype, sa->sadb_sa_spi, IPSEC_MODE_ANY)); /* send delete information */ - if (iph2->status == PHASE2ST_ESTABLISHED) + + /* TODO: Look into handling this properly. Currently, if we get here, we can end up sending delete messages to the server for their own SAs, which is rejected. */ + /*if (FSM_STATE_IS_ESTABLISHED(iph2->status)) isakmp_info_send_d2(iph2); ike_session_cleanup_ph1s_by_ph2(iph2); - unbindph12(iph2); - remph2(iph2); - delph2(iph2); + ike_session_unlink_phase2(iph2);*/ return 0; } @@ -2108,19 +2083,15 @@ static int pk_recvflush(mhp) caddr_t *mhp; { - /* ignore this message because of local test mode. */ - if (f_local) - return 0; - /* sanity check */ if (mhp[0] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb flush message passed.\n"); return -1; } - flushph2(false); - flushph1(false); + ike_session_flush_all_phase2(false); + ike_session_flush_all_phase1(false); return 0; } @@ -2129,9 +2100,9 @@ static int getsadbpolicy(policy0, policylen0, type, iph2) caddr_t *policy0; int *policylen0, type; - struct ph2handle *iph2; + phase2_handle_t *iph2; { - struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen; + struct policyindex *spidx = iph2->spidx_gen; struct sadb_x_policy *xpl; struct sadb_x_ipsecrequest *xisr; struct saproto *pr; @@ -2146,8 +2117,8 @@ getsadbpolicy(policy0, policylen0, type, iph2) for (pr = iph2->approval->head; pr; pr = pr->next) { xisrlen = sizeof(*xisr); if (pr->encmode == IPSECDOI_ATTR_ENC_MODE_TUNNEL) { - xisrlen += (sysdep_sa_len(iph2->src) - + sysdep_sa_len(iph2->dst)); + xisrlen += (sysdep_sa_len((struct sockaddr *)iph2->src) + + sysdep_sa_len((struct sockaddr *)iph2->dst)); } policylen += PFKEY_ALIGN8(xisrlen); @@ -2157,12 +2128,12 @@ getsadbpolicy(policy0, policylen0, type, iph2) /* make policy structure */ policy = racoon_malloc(policylen); if (!policy) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "buffer allocation failed.\n"); return -1; } - xpl = (struct sadb_x_policy *)policy; + xpl = ALIGNED_CAST(struct sadb_x_policy *)policy; xpl->sadb_x_policy_len = PFKEY_UNIT64(policylen); xpl->sadb_x_policy_exttype = SADB_X_EXT_POLICY; xpl->sadb_x_policy_type = IPSEC_POLICY_IPSEC; @@ -2182,13 +2153,13 @@ getsadbpolicy(policy0, policylen0, type, iph2) satype = doi2ipproto(pr->proto_id); if (satype == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid proto_id %d\n", pr->proto_id); goto err; } mode = ipsecdoi2pfkey_mode(pr->encmode); if (mode == ~0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid encmode %d\n", pr->encmode); goto err; } @@ -2208,8 +2179,8 @@ getsadbpolicy(policy0, policylen0, type, iph2) if (pr->encmode == IPSECDOI_ATTR_ENC_MODE_TUNNEL) { int src_len, dst_len; - src_len = sysdep_sa_len(iph2->src); - dst_len = sysdep_sa_len(iph2->dst); + src_len = sysdep_sa_len((struct sockaddr *)iph2->src); + dst_len = sysdep_sa_len((struct sockaddr *)iph2->dst); xisrlen += src_len + dst_len; memcpy(p, iph2->src, src_len); @@ -2237,9 +2208,9 @@ err: int pk_sendspdupdate2(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { - struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen; + struct policyindex *spidx = iph2->spidx_gen; caddr_t policy = NULL; int policylen = 0; u_int64_t ltime, vtime; @@ -2248,26 +2219,26 @@ pk_sendspdupdate2(iph2) vtime = 0; if (getsadbpolicy(&policy, &policylen, SADB_X_SPDUPDATE, iph2)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "getting sadb policy failed.\n"); return -1; } if (pfkey_send_spdupdate2( lcconf->sock_pfkey, - (struct sockaddr *)&spidx->src, + &spidx->src, spidx->prefs, - (struct sockaddr *)&spidx->dst, + &spidx->dst, spidx->prefd, spidx->ul_proto, ltime, vtime, policy, policylen, 0) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "libipsec failed send spdupdate2 (%s)\n", ipsec_strerror()); goto end; } - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_spdupdate2\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_spdupdate2\n"); end: if (policy) @@ -2290,13 +2261,13 @@ pk_recvspdupdate(mhp) || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL || mhp[SADB_X_EXT_POLICY] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spdupdate message passed.\n"); return -1; } - saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; - daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; - xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; + saddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + daddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; + xpl = ALIGNED_CAST(struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; #ifdef HAVE_PFKEY_POLICY_PRIORITY KEY_SETSECSPIDX(xpl->sadb_x_policy_dir, @@ -2319,7 +2290,7 @@ pk_recvspdupdate(mhp) sp = getsp(&spidx); if (sp == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "such policy does not already exist: \"%s\"\n", spidx2str(&spidx)); } else { @@ -2338,9 +2309,9 @@ pk_recvspdupdate(mhp) */ int pk_sendspdadd2(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { - struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen; + struct policyindex *spidx = iph2->spidx_gen; caddr_t policy = NULL; int policylen = 0; u_int64_t ltime, vtime; @@ -2349,26 +2320,26 @@ pk_sendspdadd2(iph2) vtime = 0; if (getsadbpolicy(&policy, &policylen, SADB_X_SPDADD, iph2)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "getting sadb policy failed.\n"); return -1; } if (pfkey_send_spdadd2( lcconf->sock_pfkey, - (struct sockaddr *)&spidx->src, + &spidx->src, spidx->prefs, - (struct sockaddr *)&spidx->dst, + &spidx->dst, spidx->prefd, spidx->ul_proto, ltime, vtime, policy, policylen, 0) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "libipsec failed send spdadd2 (%s)\n", ipsec_strerror()); goto end; } - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_spdadd2\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_spdadd2\n"); end: if (policy) @@ -2391,13 +2362,13 @@ pk_recvspdadd(mhp) || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL || mhp[SADB_X_EXT_POLICY] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spdadd message passed.\n"); return -1; } - saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; - daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; - xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; + saddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + daddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; + xpl = ALIGNED_CAST(struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; #ifdef HAVE_PFKEY_POLICY_PRIORITY KEY_SETSECSPIDX(xpl->sadb_x_policy_dir, @@ -2420,7 +2391,7 @@ pk_recvspdadd(mhp) sp = getsp(&spidx); if (sp != NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "such policy already exists. " "anyway replace it: %s\n", spidx2str(&spidx)); @@ -2439,32 +2410,32 @@ pk_recvspdadd(mhp) */ int pk_sendspddelete(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { - struct policyindex *spidx = (struct policyindex *)iph2->spidx_gen; + struct policyindex *spidx = iph2->spidx_gen; caddr_t policy = NULL; int policylen; if (getsadbpolicy(&policy, &policylen, SADB_X_SPDDELETE, iph2)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "getting sadb policy failed.\n"); return -1; } if (pfkey_send_spddelete( lcconf->sock_pfkey, - (struct sockaddr *)&spidx->src, + &spidx->src, spidx->prefs, - (struct sockaddr *)&spidx->dst, + &spidx->dst, spidx->prefd, spidx->ul_proto, policy, policylen, 0) < 0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "libipsec failed send spddelete (%s)\n", ipsec_strerror()); goto end; } - plog(LLV_DEBUG, LOCATION, NULL, "call pfkey_send_spddelete\n"); + plog(ASL_LEVEL_DEBUG, "call pfkey_send_spddelete\n"); end: if (policy) @@ -2487,13 +2458,13 @@ pk_recvspddelete(mhp) || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL || mhp[SADB_X_EXT_POLICY] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spddelete message passed.\n"); return -1; } - saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; - daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; - xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; + saddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + daddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; + xpl = ALIGNED_CAST(struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; #ifdef HAVE_PFKEY_POLICY_PRIORITY KEY_SETSECSPIDX(xpl->sadb_x_policy_dir, @@ -2516,13 +2487,13 @@ pk_recvspddelete(mhp) sp = getsp(&spidx); if (sp == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "no policy found: %s\n", spidx2str(&spidx)); return -1; } - purgephXbyspid(xpl->sadb_x_policy_id, true); + ike_session_purgephXbyspid(xpl->sadb_x_policy_id, true); remsp(sp); delsp(sp); @@ -2544,13 +2515,13 @@ pk_recvspdexpire(mhp) || mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL || mhp[SADB_X_EXT_POLICY] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spdexpire message passed.\n"); return -1; } - saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; - daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; - xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; + saddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + daddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; + xpl = ALIGNED_CAST(struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; #ifdef HAVE_PFKEY_POLICY_PRIORITY KEY_SETSECSPIDX(xpl->sadb_x_policy_dir, @@ -2573,13 +2544,13 @@ pk_recvspdexpire(mhp) sp = getsp(&spidx); if (sp == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "no policy found: %s\n", spidx2str(&spidx)); return -1; } - purgephXbyspid(xpl->sadb_x_policy_id, false); + ike_session_purgephXbyspid(xpl->sadb_x_policy_id, false); remsp(sp); delsp(sp); @@ -2593,7 +2564,7 @@ pk_recvspdget(mhp) { /* sanity check */ if (mhp[0] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spdget message passed.\n"); return -1; } @@ -2613,18 +2584,18 @@ pk_recvspddump(mhp) /* sanity check */ if (mhp[0] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spddump message passed.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer - saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; - daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; - xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; + saddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; + daddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; + xpl = ALIGNED_CAST(struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; if (saddr == NULL || daddr == NULL || xpl == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spddump message passed.\n"); return -1; } @@ -2650,7 +2621,7 @@ pk_recvspddump(mhp) sp = getsp(&spidx); if (sp != NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "such policy already exists. " "anyway replace it: %s\n", spidx2str(&spidx)); @@ -2670,13 +2641,13 @@ pk_recvspdflush(mhp) { /* sanity check */ if (mhp[0] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spdflush message passed.\n"); return -1; } - flushph2(false); - flushph1(false); + ike_session_flush_all_phase2(false); + ike_session_flush_all_phase1(false); flushsp(); return 0; @@ -2687,7 +2658,7 @@ pk_recvspdflush(mhp) */ int pk_sendeacquire(iph2) - struct ph2handle *iph2; + phase2_handle_t *iph2; { struct sadb_msg *newmsg; int len; @@ -2695,7 +2666,7 @@ pk_sendeacquire(iph2) len = sizeof(struct sadb_msg); newmsg = racoon_calloc(1, len); if (newmsg == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "failed to get buffer to send acquire.\n"); return -1; } @@ -2725,7 +2696,7 @@ pk_sendget_inbound_sastats(ike_session_t *session) u_int32_t seq; if (!session) { - plog(LLV_DEBUG, LOCATION, NULL, "invalid args in %s \n", __FUNCTION__); + plog(ASL_LEVEL_DEBUG, "invalid args in %s \n", __FUNCTION__); return -1; } @@ -2741,7 +2712,7 @@ pk_sendget_inbound_sastats(ike_session_t *session) max_stats))) { u_int64_t session_ids[] = {(u_int64_t)session, 0}; - plog(LLV_DEBUG, LOCATION, NULL, "about to call %s\n", __FUNCTION__); + //plog(ASL_LEVEL_DEBUG, "about to call %s\n", __FUNCTION__); if (pfkey_send_getsastats(lcconf->sock_pfkey, seq, @@ -2752,7 +2723,7 @@ pk_sendget_inbound_sastats(ike_session_t *session) session->traffic_monitor.num_in_curr_req) < 0) { return -1; } - plog(LLV_DEBUG, LOCATION, NULL, "%s successful\n", __FUNCTION__); + //plog(ASL_LEVEL_DEBUG, "%s successful\n", __FUNCTION__); return session->traffic_monitor.num_in_curr_req; } @@ -2766,7 +2737,7 @@ pk_sendget_outbound_sastats(ike_session_t *session) u_int32_t seq; if (!session) { - plog(LLV_DEBUG, LOCATION, NULL, "invalid args in %s \n", __FUNCTION__); + plog(ASL_LEVEL_DEBUG, "invalid args in %s \n", __FUNCTION__); return -1; } @@ -2782,7 +2753,7 @@ pk_sendget_outbound_sastats(ike_session_t *session) max_stats))) { u_int64_t session_ids[] = {(u_int64_t)session, 0}; - plog(LLV_DEBUG, LOCATION, NULL, "about to call %s\n", __FUNCTION__); + //plog(ASL_LEVEL_DEBUG, "about to call %s\n", __FUNCTION__); if (pfkey_send_getsastats(lcconf->sock_pfkey, seq, @@ -2793,7 +2764,7 @@ pk_sendget_outbound_sastats(ike_session_t *session) session->traffic_monitor.num_out_curr_req) < 0) { return -1; } - plog(LLV_DEBUG, LOCATION, NULL, "%s successful\n", __FUNCTION__); + //plog(ASL_LEVEL_DEBUG, "%s successful\n", __FUNCTION__); return session->traffic_monitor.num_out_curr_req; } @@ -2816,17 +2787,17 @@ caddr_t *mhp; if (mhp[0] == NULL || mhp[SADB_EXT_SESSION_ID] == NULL || mhp[SADB_EXT_SASTAT] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb getsastat response.\n"); return -1; } - msg = (struct sadb_msg *)mhp[0]; - session_id = (ike_session_t *)mhp[SADB_EXT_SESSION_ID]; - stat_resp = (struct sadb_sastat *)mhp[SADB_EXT_SASTAT]; + msg = ALIGNED_CAST(struct sadb_msg *)mhp[0]; // Wcast-align fix (void*) - mhp contains pointers to structs in an aligned buffer + session_id = ALIGNED_CAST(struct sadb_session_id *)mhp[SADB_EXT_SESSION_ID]; + stat_resp = ALIGNED_CAST(struct sadb_sastat *)mhp[SADB_EXT_SASTAT]; /* the message has to be processed or not ? */ if (msg->sadb_msg_pid != getpid()) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "%s message is not interesting " "because pid %d is not mine.\n", s_pfkey_type(msg->sadb_msg_type), @@ -2834,16 +2805,16 @@ caddr_t *mhp; return -1; } if (!session_id->sadb_session_id_v[0]) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "%s message is bad " "because session-id[0] is invalid.\n", s_pfkey_type(msg->sadb_msg_type)); return -1; } - session = (__typeof__(session))session_id->sadb_session_id_v[0]; + session = ALIGNED_CAST(__typeof__(session))session_id->sadb_session_id_v[0]; if (!stat_resp->sadb_sastat_list_len) { - plog(LLV_DEBUG, LOCATION, NULL, + plog(ASL_LEVEL_DEBUG, "%s message is bad " "because it has no sastats.\n", s_pfkey_type(msg->sadb_msg_type)); @@ -2878,12 +2849,9 @@ pk_checkalg(class, calg, keylen) sup = SADB_EXT_SUPPORTED_AUTH; break; case IPSECDOI_PROTO_IPCOMP: - plog(LLV_DEBUG, LOCATION, NULL, - "compression algorithm can not be checked " - "because sadb message doesn't support it.\n"); return 0; default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid algorithm class.\n"); return -1; } @@ -2893,7 +2861,7 @@ pk_checkalg(class, calg, keylen) if (keylen == 0) { if (ipsec_get_keylen(sup, alg, &alg0)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "%s.\n", ipsec_strerror()); return -1; } @@ -2902,7 +2870,7 @@ pk_checkalg(class, calg, keylen) error = ipsec_check_keylen(sup, alg, keylen); if (error) - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "%s.\n", ipsec_strerror()); return error; @@ -2918,7 +2886,7 @@ pk_checkalg(class, calg, keylen) static struct sadb_msg * pk_recv(so, lenp) int so; - int *lenp; + ssize_t *lenp; { struct sadb_msg *newmsg; int reallen = 0; @@ -2933,7 +2901,12 @@ pk_recv(so, lenp) if ((newmsg = racoon_calloc(1, reallen)) == NULL) return NULL; - *lenp = recv(so, (caddr_t)newmsg, reallen, 0); + while ((*lenp = recv(so, (caddr_t)newmsg, reallen, 0)) < 0) { + if (errno == EINTR) + continue; + plog(ASL_LEVEL_ERR, "failed to recv pfkey message: %s\n", strerror(errno)); + break; + } if (*lenp < 0) { racoon_free(newmsg); return NULL; /*fatal*/ @@ -2964,18 +2937,18 @@ addnewsp(mhp) if (mhp[SADB_EXT_ADDRESS_SRC] == NULL || mhp[SADB_EXT_ADDRESS_DST] == NULL || mhp[SADB_X_EXT_POLICY] == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "inappropriate sadb spd management message passed.\n"); return -1; } - saddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; - daddr = (struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; - xpl = (struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; + saddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_SRC]; // Wcast-align fix (void*) - mhp contains pointers to aligned structs in malloc'd msg buffer + daddr = ALIGNED_CAST(struct sadb_address *)mhp[SADB_EXT_ADDRESS_DST]; + xpl = ALIGNED_CAST(struct sadb_x_policy *)mhp[SADB_X_EXT_POLICY]; new = newsp(); if (new == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "failed to allocate buffer\n"); return -1; } @@ -3002,7 +2975,7 @@ addnewsp(mhp) /* validity check */ if (PFKEY_EXTLEN(xpl) < sizeof(*xpl)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid msg length.\n"); return -1; } @@ -3014,7 +2987,7 @@ addnewsp(mhp) /* length check */ if (xisr->sadb_x_ipsecrequest_len < sizeof(*xisr)) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid msg length.\n"); return -1; } @@ -3022,7 +2995,7 @@ addnewsp(mhp) /* allocate request buffer */ *p_isr = newipsecreq(); if (*p_isr == NULL) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "failed to get new ipsecreq.\n"); return -1; } @@ -3036,7 +3009,7 @@ addnewsp(mhp) case IPPROTO_IPCOMP: break; default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid proto type: %u\n", xisr->sadb_x_ipsecrequest_proto); return -1; @@ -3049,7 +3022,7 @@ addnewsp(mhp) break; case IPSEC_MODE_ANY: default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid mode: %u\n", xisr->sadb_x_ipsecrequest_mode); return -1; @@ -3067,7 +3040,7 @@ addnewsp(mhp) break; default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid level: %u\n", xisr->sadb_x_ipsecrequest_level); return -1; @@ -3096,17 +3069,17 @@ addnewsp(mhp) /* validity check */ if (tlen < 0) { - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "becoming tlen < 0\n"); } - xisr = (struct sadb_x_ipsecrequest *)((caddr_t)xisr + xisr = ALIGNED_CAST(struct sadb_x_ipsecrequest *)((caddr_t)xisr + xisr->sadb_x_ipsecrequest_len); } } break; default: - plog(LLV_ERROR, LOCATION, NULL, + plog(ASL_LEVEL_ERR, "invalid policy type.\n"); return -1; } @@ -3138,7 +3111,7 @@ addnewsp(mhp) /* proto/mode/src->dst spi */ const char * sadbsecas2str(src, dst, proto, spi, mode) - struct sockaddr *src, *dst; + struct sockaddr_storage *src, *dst; int proto; u_int32_t spi; int mode; @@ -3169,13 +3142,13 @@ sadbsecas2str(src, dst, proto, spi, mode) p += i; blen -= i; - i = snprintf(p, blen, "%s->", saddr2str(src)); + i = snprintf(p, blen, "%s->", saddr2str((struct sockaddr *)src)); if (i < 0 || i >= blen) return NULL; p += i; blen -= i; - i = snprintf(p, blen, "%s ", saddr2str(dst)); + i = snprintf(p, blen, "%s ", saddr2str((struct sockaddr *)dst)); if (i < 0 || i >= blen) return NULL; p += i;