diff options
author | Florian Obser <florian@cvs.openbsd.org> | 2016-06-15 13:49:44 +0000 |
---|---|---|
committer | Florian Obser <florian@cvs.openbsd.org> | 2016-06-15 13:49:44 +0000 |
commit | f32a12864b5c2cf4262a8f7a4b4908afbad077fc (patch) | |
tree | 0a75aa079d777d7cb0af27299f6463e55dd0b2db | |
parent | 2b577d2f16cab096c1aaeefe9c11ebd3b9043d35 (diff) |
With the introduction of ip6_output_ipsec_lookup() we didn't exit the
loop when we worked out that no IPsec is needed which led to a NULL
de-ref on the next iteration.
Fix this by making the code more similar to the IPv4 case.
Found the hard way by me, OK mpi@
-rw-r--r-- | sys/netinet6/ip6_output.c | 30 |
1 files changed, 15 insertions, 15 deletions
diff --git a/sys/netinet6/ip6_output.c b/sys/netinet6/ip6_output.c index 4f7b9806383..d3936180d7c 100644 --- a/sys/netinet6/ip6_output.c +++ b/sys/netinet6/ip6_output.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ip6_output.c,v 1.208 2016/06/15 11:49:34 mpi Exp $ */ +/* $OpenBSD: ip6_output.c,v 1.209 2016/06/15 13:49:43 florian Exp $ */ /* $KAME: ip6_output.c,v 1.172 2001/03/25 09:55:56 itojun Exp $ */ /* @@ -2882,21 +2882,21 @@ ip6_output_ipsec_lookup(struct mbuf *m, int *error, struct inpcb *inp) tdb = ipsp_spd_lookup(m, AF_INET6, sizeof(struct ip6_hdr), error, IPSP_DIRECTION_OUT, NULL, inp, 0); - if (tdb != NULL) { - /* Loop detection */ - for (mtag = m_tag_first(m); mtag != NULL; - mtag = m_tag_next(m, mtag)) { - if (mtag->m_tag_id != PACKET_TAG_IPSEC_OUT_DONE) - continue; - tdbi = (struct tdb_ident *)(mtag + 1); - if (tdbi->spi == tdb->tdb_spi && - tdbi->proto == tdb->tdb_sproto && - tdbi->rdomain == tdb->tdb_rdomain && - !bcmp(&tdbi->dst, &tdb->tdb_dst, - sizeof(union sockaddr_union))) - tdb = NULL; + if (tdb == NULL) + return NULL; + /* Loop detection */ + for (mtag = m_tag_first(m); mtag != NULL; mtag = m_tag_next(m, mtag)) { + if (mtag->m_tag_id != PACKET_TAG_IPSEC_OUT_DONE) + continue; + tdbi = (struct tdb_ident *)(mtag + 1); + if (tdbi->spi == tdb->tdb_spi && + tdbi->proto == tdb->tdb_sproto && + tdbi->rdomain == tdb->tdb_rdomain && + !memcmp(&tdbi->dst, &tdb->tdb_dst, + sizeof(union sockaddr_union))) { + /* no IPsec needed */ + return NULL; } - /* We need to do IPsec */ } return tdb; } |