Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/netinet6 do not use cached route if the route becomes !R...
details: https://anonhg.NetBSD.org/src/rev/6f6aa2cd2d3f
branches: trunk
changeset: 487831:6f6aa2cd2d3f
user: itojun <itojun%NetBSD.org@localhost>
date: Tue Jun 13 14:43:44 2000 +0000
description:
do not use cached route if the route becomes !RTF_UP.
make the validation for jumbo payload option more strict.
diffstat:
sys/netinet6/ip6_input.c | 158 +++++++++++++++++++++++++++++-----------------
1 files changed, 100 insertions(+), 58 deletions(-)
diffs (223 lines):
diff -r dfafe31a205e -r 6f6aa2cd2d3f sys/netinet6/ip6_input.c
--- a/sys/netinet6/ip6_input.c Tue Jun 13 14:42:55 2000 +0000
+++ b/sys/netinet6/ip6_input.c Tue Jun 13 14:43:44 2000 +0000
@@ -1,5 +1,5 @@
-/* $NetBSD: ip6_input.c,v 1.21 2000/05/19 20:09:27 itojun Exp $ */
-/* $KAME: ip6_input.c,v 1.89 2000/05/19 19:59:05 itojun Exp $ */
+/* $NetBSD: ip6_input.c,v 1.22 2000/06/13 14:43:44 itojun Exp $ */
+/* $KAME: ip6_input.c,v 1.94 2000/06/13 10:06:19 jinmei Exp $ */
/*
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
@@ -261,8 +261,7 @@
if (m->m_next) {
if (m->m_flags & M_LOOP) {
ip6stat.ip6s_m2m[loif[0].if_index]++; /*XXX*/
- }
- else if (m->m_pkthdr.rcvif->if_index <= 31)
+ } else if (m->m_pkthdr.rcvif->if_index <= 31)
ip6stat.ip6s_m2m[m->m_pkthdr.rcvif->if_index]++;
else
ip6stat.ip6s_m2m[0]++;
@@ -443,13 +442,18 @@
/*
* Unicast check
*/
- if (ip6_forward_rt.ro_rt == 0 ||
- !IN6_ARE_ADDR_EQUAL(&ip6->ip6_dst,
- &ip6_forward_rt.ro_dst.sin6_addr)) {
+ if (ip6_forward_rt.ro_rt != NULL &&
+ (ip6_forward_rt.ro_rt->rt_flags & RTF_UP) != 0 &&
+ IN6_ARE_ADDR_EQUAL(&ip6->ip6_dst,
+ &ip6_forward_rt.ro_dst.sin6_addr))
+ ; /* cache hit */
+ else {
if (ip6_forward_rt.ro_rt) {
+ /* route is down or destination is different */
RTFREE(ip6_forward_rt.ro_rt);
ip6_forward_rt.ro_rt = 0;
}
+
bzero(&ip6_forward_rt.ro_dst, sizeof(struct sockaddr_in6));
ip6_forward_rt.ro_dst.sin6_len = sizeof(struct sockaddr_in6);
ip6_forward_rt.ro_dst.sin6_family = AF_INET6;
@@ -562,8 +566,29 @@
#endif
return; /* m have already been freed */
}
+
/* adjust pointer */
ip6 = mtod(m, struct ip6_hdr *);
+
+ /*
+ * if the payload length field is 0 and the next header field
+ * indicates Hop-by-Hop Options header, then a Jumbo Payload
+ * option MUST be included.
+ */
+ if (ip6->ip6_plen == 0 && plen == 0) {
+ /*
+ * Note that if a valid jumbo payload option is
+ * contained, ip6_hoptops_input() must set a valid
+ * (non-zero) payload length to the variable plen.
+ */
+ ip6stat.ip6s_badoptions++;
+ in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);
+ in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_hdrerr);
+ icmp6_error(m, ICMP6_PARAM_PROB,
+ ICMP6_PARAMPROB_HEADER,
+ (caddr_t)&ip6->ip6_plen - (caddr_t)ip6);
+ return;
+ }
#ifndef PULLDOWN_TEST
/* ip6_hopopts_input() ensures that mbuf is contiguous */
hbh = (struct ip6_hbh *)(ip6 + 1);
@@ -626,8 +651,7 @@
m_freem(m);
return;
}
- }
- else if (!ours) {
+ } else if (!ours) {
ip6_forward(m, 0);
return;
}
@@ -638,7 +662,6 @@
#ifdef IFA_STATS
if (IFA_STATS && deliverifp != NULL) {
struct in6_ifaddr *ia6;
- ip6 = mtod(m, struct ip6_hdr *);
ia6 = in6_ifawithifp(deliverifp, &ip6->ip6_dst);
if (ia6)
ia6->ia_ifa.ifa_data.ifad_inbytes += m->m_pkthdr.len;
@@ -740,6 +763,7 @@
int optlen = 0;
u_int8_t *opt = opthead;
u_int16_t rtalert_val;
+ u_int32_t jumboplen;
for (; hbhlen > 0; hbhlen -= optlen, opt += optlen) {
switch(*opt) {
@@ -768,57 +792,75 @@
*rtalertp = ntohs(rtalert_val);
break;
case IP6OPT_JUMBO:
- /* XXX may need check for alignment */
- if (hbhlen < IP6OPT_JUMBO_LEN) {
- ip6stat.ip6s_toosmall++;
- goto bad;
- }
- if (*(opt + 1) != IP6OPT_JUMBO_LEN - 2)
- /* XXX: should we discard the packet? */
- log(LOG_ERR, "length of jumbopayload opt "
- "is inconsistent(%d)",
- *(opt + 1));
- optlen = IP6OPT_JUMBO_LEN;
+ /* XXX may need check for alignment */
+ if (hbhlen < IP6OPT_JUMBO_LEN) {
+ ip6stat.ip6s_toosmall++;
+ goto bad;
+ }
+ if (*(opt + 1) != IP6OPT_JUMBO_LEN - 2)
+ /* XXX: should we discard the packet? */
+ log(LOG_ERR, "length of jumbopayload opt "
+ "is inconsistent(%d)",
+ *(opt + 1));
+ optlen = IP6OPT_JUMBO_LEN;
- /*
- * We can simply cast because of the alignment
- * requirement of the jumbo payload option.
- */
-#if 0
- *plenp = ntohl(*(u_int32_t *)(opt + 2));
-#else
- bcopy(opt + 2, plenp, sizeof(*plenp));
- *plenp = htonl(*plenp);
+ /*
+ * IPv6 packets that have non 0 payload length
+ * must not contain a jumbo paylod option.
+ */
+ ip6 = mtod(m, struct ip6_hdr *);
+ if (ip6->ip6_plen) {
+ ip6stat.ip6s_badoptions++;
+ icmp6_error(m, ICMP6_PARAM_PROB,
+ ICMP6_PARAMPROB_HEADER,
+ sizeof(struct ip6_hdr) +
+ sizeof(struct ip6_hbh) +
+ opt - opthead);
+ return(-1);
+ }
+
+ /*
+ * We may see jumbolen in unaligned location, so
+ * we'd need to perform bcopy().
+ */
+ bcopy(opt + 2, &jumboplen, sizeof(jumboplen));
+ jumboplen = (u_int32_t)htonl(jumboplen);
+
+#if 1
+ /*
+ * if there are multiple jumbo payload options,
+ * *plenp will be non-zero and the packet will be
+ * rejected.
+ * the behavior may need some debate in ipngwg -
+ * multiple options does not make sense, however,
+ * there's no explicit mention in specification.
+ */
+ if (*plenp != 0) {
+ ip6stat.ip6s_badoptions++;
+ icmp6_error(m, ICMP6_PARAM_PROB,
+ ICMP6_PARAMPROB_HEADER,
+ sizeof(struct ip6_hdr) +
+ sizeof(struct ip6_hbh) +
+ opt + 2 - opthead);
+ return(-1);
+ }
#endif
- if (*plenp <= IPV6_MAXPACKET) {
- /*
- * jumbo payload length must be larger
- * than 65535
- */
- ip6stat.ip6s_badoptions++;
- icmp6_error(m, ICMP6_PARAM_PROB,
- ICMP6_PARAMPROB_HEADER,
- sizeof(struct ip6_hdr) +
- sizeof(struct ip6_hbh) +
- opt + 2 - opthead);
- return(-1);
- }
- ip6 = mtod(m, struct ip6_hdr *);
- if (ip6->ip6_plen) {
- /*
- * IPv6 packets that have non 0 payload length
- * must not contain a jumbo paylod option.
- */
- ip6stat.ip6s_badoptions++;
- icmp6_error(m, ICMP6_PARAM_PROB,
- ICMP6_PARAMPROB_HEADER,
- sizeof(struct ip6_hdr) +
- sizeof(struct ip6_hbh) +
- opt - opthead);
- return(-1);
- }
- break;
+ /*
+ * jumbo payload length must be larger than 65535.
+ */
+ if (jumboplen <= IPV6_MAXPACKET) {
+ ip6stat.ip6s_badoptions++;
+ icmp6_error(m, ICMP6_PARAM_PROB,
+ ICMP6_PARAMPROB_HEADER,
+ sizeof(struct ip6_hdr) +
+ sizeof(struct ip6_hbh) +
+ opt + 2 - opthead);
+ return(-1);
+ }
+ *plenp = jumboplen;
+
+ break;
default: /* unknown option */
if (hbhlen < IP6OPT_MINLEN) {
ip6stat.ip6s_toosmall++;
Home |
Main Index |
Thread Index |
Old Index