diff options
author | Natanael Copa <ncopa@alpinelinux.org> | 2009-07-24 08:01:31 +0000 |
---|---|---|
committer | Natanael Copa <ncopa@alpinelinux.org> | 2009-07-24 08:01:31 +0000 |
commit | b70981b68efcce5256eb11c6cd26ae123b10b6ea (patch) | |
tree | a38be6efae5e2ba15c2e839504632f9b7bfd5f91 /main/ipsec-tools/50-reverse-connect.patch | |
parent | 2b4df81538b8398442d5296650905c70341dd8d3 (diff) | |
download | aports-b70981b68efcce5256eb11c6cd26ae123b10b6ea.tar.bz2 aports-b70981b68efcce5256eb11c6cd26ae123b10b6ea.tar.xz |
moved extra/* to main/
and fixed misc build issues
Diffstat (limited to 'main/ipsec-tools/50-reverse-connect.patch')
-rw-r--r-- | main/ipsec-tools/50-reverse-connect.patch | 207 |
1 files changed, 207 insertions, 0 deletions
diff --git a/main/ipsec-tools/50-reverse-connect.patch b/main/ipsec-tools/50-reverse-connect.patch new file mode 100644 index 000000000..c49eae347 --- /dev/null +++ b/main/ipsec-tools/50-reverse-connect.patch @@ -0,0 +1,207 @@ +When new ISAKMP is required, allow incoming reverse connection to take + +From: Timo Teras <timo.teras@iki.fi> + +over pending phase1:s. Useful when the other party is firewalled or NATted. +--- + + src/racoon/admin.c | 12 ++++++++++++ + src/racoon/evt.c | 13 +++++++++++++ + src/racoon/evt.h | 3 +++ + src/racoon/handler.c | 28 +++++++++++++++++++++------- + src/racoon/isakmp.c | 39 ++++++++++++++++++++++++++++++++++----- + 5 files changed, 83 insertions(+), 12 deletions(-) + + +diff --git a/src/racoon/admin.c b/src/racoon/admin.c +index b67e545..710c9bf 100644 +--- a/src/racoon/admin.c ++++ b/src/racoon/admin.c +@@ -414,11 +414,23 @@ admin_process(so2, combuf) + struct sockaddr *dst; + struct sockaddr *src; + char *name = NULL; ++ char *loc, *rem; + + ndx = (struct admin_com_indexes *) ((caddr_t)com + sizeof(*com)); + src = (struct sockaddr *) &ndx->src; + dst = (struct sockaddr *) &ndx->dst; + ++ loc = racoon_strdup(saddr2str(src)); ++ rem = racoon_strdup(saddr2str(dst)); ++ STRDUP_FATAL(loc); ++ STRDUP_FATAL(rem); ++ ++ plog(LLV_INFO, LOCATION, NULL, ++ "admin establish-sa %x %s %s\n", ++ com->ac_proto, loc, rem); ++ racoon_free(loc); ++ racoon_free(rem); ++ + if (com->ac_cmd == ADMIN_ESTABLISH_SA && + com->ac_len > sizeof(*com) + sizeof(*ndx)) + name = (char *) ((caddr_t) ndx + sizeof(*ndx)); +diff --git a/src/racoon/evt.c b/src/racoon/evt.c +index 4ce1334..000c1f8 100644 +--- a/src/racoon/evt.c ++++ b/src/racoon/evt.c +@@ -396,4 +396,17 @@ evt_list_cleanup(list) + evt_unsubscribe(LIST_FIRST(list)); + } + ++void ++evt_list_move(from, to) ++ struct evt_listener_list *from, *to; ++{ ++ struct evt_listener *l; ++ ++ while (!LIST_EMPTY(from)) { ++ l = LIST_FIRST(from); ++ LIST_REMOVE(l, ll_chain); ++ LIST_INSERT_HEAD(to, l, ll_chain); ++ } ++} ++ + #endif /* ENABLE_ADMINPORT */ +diff --git a/src/racoon/evt.h b/src/racoon/evt.h +index 0ce65bd..ba7fb57 100644 +--- a/src/racoon/evt.h ++++ b/src/racoon/evt.h +@@ -124,6 +124,8 @@ void evt_phase2 __P((const struct ph2handle *ph2, int type, vchar_t *optdata)); + vchar_t *evt_dump __P((void)); + + int evt_subscribe __P((struct evt_listener_list *list, int fd)); ++void evt_list_move __P((struct evt_listener_list *from, ++ struct evt_listener_list *to)); + void evt_list_init __P((struct evt_listener_list *list)); + void evt_list_cleanup __P((struct evt_listener_list *list)); + +@@ -136,6 +138,7 @@ void evt_list_cleanup __P((struct evt_listener_list *list)); + #define evt_phase2(ph2, type, optdata) ; + + #define evt_subscribe(eventlist, fd) ; ++#deifne evt_list_move(from, to) ; + #define evt_list_init(eventlist) ; + #define evt_list_cleanup(eventlist) ; + #define evt_get_fdmask(nfds, fdset) nfds +diff --git a/src/racoon/handler.c b/src/racoon/handler.c +index b33986f..9fd3817 100644 +--- a/src/racoon/handler.c ++++ b/src/racoon/handler.c +@@ -269,26 +269,40 @@ migrate_ph12(old_iph1, new_iph1) + } + + /* +- * the iph1 is new, migrate all phase2s that belong to a dying or dead ph1 ++ * the iph1 is new, migrate all phase2s that belong to a dying or dead ph1. + */ + void migrate_dying_ph12(iph1) + struct ph1handle *iph1; + { +- struct ph1handle *p; ++ struct ph1handle *p, *next; + +- LIST_FOREACH(p, &ph1tree, chain) { ++ for (p = LIST_FIRST(&ph1tree); p; p = next) { ++ next = LIST_NEXT(p, chain); + if (p == iph1) + continue; +- if (p->status < PHASE1ST_DYING) ++ ++ /* Same remote? */ ++ if (cmpsaddr(iph1->local, p->local) > CMPSADDR_WOP_MATCH || ++ cmpsaddr(iph1->remote, p->remote) > CMPSADDR_WOP_MATCH || ++ iph1->rmconf != p->rmconf) + continue; + +- if (cmpsaddr(iph1->local, p->local) == 0 +- && cmpsaddr(iph1->remote, p->remote) == 0) ++ /* migrate phase2:s from expiring entries */ ++ if (p->status >= PHASE1ST_DYING) + migrate_ph12(p, iph1); ++ ++ /* and allow reverse connections to release ++ * pending connections that do not work due ++ * to firewall or nat */ ++ if (iph1->side == RESPONDER && p->side == INITIATOR && ++ p->status < PHASE1ST_MSG3RECEIVED) { ++ evt_list_move(&p->evt_listeners, &iph1->evt_listeners); ++ remph1(p); ++ delph1(p); ++ } + } + } + +- + /* + * dump isakmp-sa + */ +diff --git a/src/racoon/isakmp.c b/src/racoon/isakmp.c +index 0de16d1..2dfda2f 100644 +--- a/src/racoon/isakmp.c ++++ b/src/racoon/isakmp.c +@@ -2138,13 +2138,33 @@ isakmp_ph2delete(iph2) + + remph2(iph2); + delph2(iph2); +- +- return; + } + + /* %%% + * Interface between PF_KEYv2 and ISAKMP + */ ++ ++static void ++isakmp_chkph2there(p) ++ struct sched *p; ++{ ++ struct ph2handle *iph2 = container_of(p, struct ph2handle, sce); ++ struct ph2handle *tmp; ++ ++ /* Check if a similar phase2 appared meanwhile */ ++ remph2(iph2); ++ tmp = getph2byid(iph2->src, iph2->dst, iph2->spid); ++ if (tmp == NULL) { ++ /* Nope, lets start this then */ ++ insph2(iph2); ++ isakmp_chkph1there(iph2); ++ } else { ++ /* Yes, delete this initiation attempt as redundant */ ++ evt_phase2(iph2, EVT_PHASE2_UP, NULL); ++ delph2(iph2); ++ } ++} ++ + /* + * receive ACQUIRE from kernel, and begin either phase1 or phase2. + * if phase1 has been finished, begin phase2. +@@ -2220,8 +2240,14 @@ isakmp_post_acquire(iph2) + /*NOTREACHED*/ + } + +- /* found established ISAKMP-SA */ +- /* i.e. iph1->status == PHASE1ST_ESTABLISHED */ ++ /* found established ISAKMP-SA, if this is a RESPONDER ISAKMP-SA ++ * add a small delay; this will make sure the initiator gets ++ * an first attempt at rekeying, and usually avoids duplicate ph2:s */ ++ if (iph1->side == RESPONDER) { ++ iph2->retry_checkph1 = 1; ++ sched_schedule(&iph2->sce, 1, isakmp_chkph2there); ++ return 0; ++ } + + /* found ISAKMP-SA. */ + plog(LLV_DEBUG, LOCATION, NULL, "begin QUICK mode.\n"); +@@ -2388,7 +2414,10 @@ isakmp_chkph1there(iph2) + plog(LLV_DEBUG2, LOCATION, NULL, "dst: %s\n", saddr2str(iph2->dst)); + + /* begin quick mode */ +- (void)isakmp_ph2begin_i(iph1, iph2); ++ if (isakmp_ph2begin_i(iph1, iph2)) { ++ remph2(iph2); ++ delph2(iph2); ++ } + return; + } + |