summaryrefslogtreecommitdiffstats
path: root/sys/netinet/ipsec_input.c
diff options
context:
space:
mode:
authormarkus <markus@openbsd.org>2003-07-08 11:01:20 +0000
committermarkus <markus@openbsd.org>2003-07-08 11:01:20 +0000
commit9a1357f896eff67579f04cd2fcb12e4bcf37a032 (patch)
tree5ca50b3820f686b8df2d65107a21c4ea455d8408 /sys/netinet/ipsec_input.c
parentprint ip_{src,dst} again; ok henning@ (diff)
downloadwireguard-openbsd-9a1357f896eff67579f04cd2fcb12e4bcf37a032.tar.xz
wireguard-openbsd-9a1357f896eff67579f04cd2fcb12e4bcf37a032.zip
make sure the packets contains a complete inner header
for ip{4,6}-in-ip{4,6} encapsulation; fixes panic for truncated ip-in-ip over ipsec; ok angelos@
Diffstat (limited to 'sys/netinet/ipsec_input.c')
-rw-r--r--sys/netinet/ipsec_input.c34
1 files changed, 31 insertions, 3 deletions
diff --git a/sys/netinet/ipsec_input.c b/sys/netinet/ipsec_input.c
index a279ec95167..4a8e58fc620 100644
--- a/sys/netinet/ipsec_input.c
+++ b/sys/netinet/ipsec_input.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ipsec_input.c,v 1.65 2003/07/04 16:40:55 markus Exp $ */
+/* $OpenBSD: ipsec_input.c,v 1.66 2003/07/08 11:01:20 markus Exp $ */
/*
* The authors of this code are John Ioannidis (ji@tla.org),
* Angelos D. Keromytis (kermit@csd.uch.gr) and
@@ -314,8 +314,15 @@ ipsec_common_input_cb(struct mbuf *m, struct tdb *tdbp, int skip, int protoff,
/* IP-in-IP encapsulation */
if (prot == IPPROTO_IPIP) {
+ if (m->m_pkthdr.len - skip < sizeof(struct ip)) {
+ m_freem(m);
+ IPSEC_ISTAT(espstat.esps_hdrops,
+ ahstat.ahs_hdrops,
+ ipcompstat.ipcomps_hdrops);
+ return EINVAL;
+ }
/* ipn will now contain the inner IPv4 header */
- m_copydata(m, ip->ip_hl << 2, sizeof(struct ip),
+ m_copydata(m, skip, sizeof(struct ip),
(caddr_t) &ipn);
/*
@@ -349,8 +356,15 @@ ipsec_common_input_cb(struct mbuf *m, struct tdb *tdbp, int skip, int protoff,
#if INET6
/* IPv6-in-IP encapsulation. */
if (prot == IPPROTO_IPV6) {
+ if (m->m_pkthdr.len - skip < sizeof(struct ip6_hdr)) {
+ m_freem(m);
+ IPSEC_ISTAT(espstat.esps_hdrops,
+ ahstat.ahs_hdrops,
+ ipcompstat.ipcomps_hdrops);
+ return EINVAL;
+ }
/* ip6n will now contain the inner IPv6 header. */
- m_copydata(m, ip->ip_hl << 2, sizeof(struct ip6_hdr),
+ m_copydata(m, skip, sizeof(struct ip6_hdr),
(caddr_t) &ip6n);
/*
@@ -409,6 +423,13 @@ ipsec_common_input_cb(struct mbuf *m, struct tdb *tdbp, int skip, int protoff,
#ifdef INET
/* IP-in-IP encapsulation */
if (prot == IPPROTO_IPIP) {
+ if (m->m_pkthdr.len - skip < sizeof(struct ip)) {
+ m_freem(m);
+ IPSEC_ISTAT(espstat.esps_hdrops,
+ ahstat.ahs_hdrops,
+ ipcompstat.ipcomps_hdrops);
+ return EINVAL;
+ }
/* ipn will now contain the inner IPv4 header */
m_copydata(m, skip, sizeof(struct ip), (caddr_t) &ipn);
@@ -443,6 +464,13 @@ ipsec_common_input_cb(struct mbuf *m, struct tdb *tdbp, int skip, int protoff,
/* IPv6-in-IP encapsulation */
if (prot == IPPROTO_IPV6) {
+ if (m->m_pkthdr.len - skip < sizeof(struct ip6_hdr)) {
+ m_freem(m);
+ IPSEC_ISTAT(espstat.esps_hdrops,
+ ahstat.ahs_hdrops,
+ ipcompstat.ipcomps_hdrops);
+ return EINVAL;
+ }
/* ip6n will now contain the inner IPv6 header. */
m_copydata(m, skip, sizeof(struct ip6_hdr),
(caddr_t) &ip6n);