[BACK]Return to ip6_input.c CVS log [TXT][DIR] Up to [cvs.NetBSD.org] / src / sys / netinet6

Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.

Diff for /src/sys/netinet6/ip6_input.c between version 1.149.4.5 and 1.149.4.7

version 1.149.4.5, 2016/04/22 15:44:18 version 1.149.4.7, 2016/07/09 20:25:22
Line 133  __KERNEL_RCSID(0, "$NetBSD$");
Line 133  __KERNEL_RCSID(0, "$NetBSD$");
 extern struct domain inet6domain;  extern struct domain inet6domain;
   
 u_char ip6_protox[IPPROTO_MAX];  u_char ip6_protox[IPPROTO_MAX];
 struct in6_ifaddr *in6_ifaddr;  
 pktqueue_t *ip6_pktq __read_mostly;  pktqueue_t *ip6_pktq __read_mostly;
   
 int ip6_forward_srcrt;                  /* XXX */  int ip6_forward_srcrt;                  /* XXX */
Line 163  ip6_init(void)
Line 162  ip6_init(void)
         const struct ip6protosw *pr;          const struct ip6protosw *pr;
         int i;          int i;
   
           in6_init();
   
         sysctl_net_inet6_ip6_setup(NULL);          sysctl_net_inet6_ip6_setup(NULL);
         pr = (const struct ip6protosw *)pffindproto(PF_INET6, IPPROTO_RAW, SOCK_RAW);          pr = (const struct ip6protosw *)pffindproto(PF_INET6, IPPROTO_RAW, SOCK_RAW);
         if (pr == 0)          if (pr == 0)
Line 217  ip6intr(void *arg __unused)
Line 218  ip6intr(void *arg __unused)
   
         mutex_enter(softnet_lock);          mutex_enter(softnet_lock);
         while ((m = pktq_dequeue(ip6_pktq)) != NULL) {          while ((m = pktq_dequeue(ip6_pktq)) != NULL) {
                 const ifnet_t *ifp = m->m_pkthdr.rcvif;                  struct psref psref;
                   struct ifnet *rcvif = m_get_rcvif_psref(m, &psref);
   
                   if (rcvif == NULL) {
                           m_freem(m);
                           continue;
                   }
                 /*                  /*
                  * Drop the packet if IPv6 is disabled on the interface.                   * Drop the packet if IPv6 is disabled on the interface.
                  */                   */
                 if ((ND_IFINFO(ifp)->flags & ND6_IFF_IFDISABLED)) {                  if ((ND_IFINFO(rcvif)->flags & ND6_IFF_IFDISABLED)) {
                           m_put_rcvif_psref(rcvif, &psref);
                         m_freem(m);                          m_freem(m);
                         continue;                          continue;
                 }                  }
                 ip6_input(m);                  ip6_input(m, rcvif);
                   m_put_rcvif_psref(rcvif, &psref);
         }          }
         mutex_exit(softnet_lock);          mutex_exit(softnet_lock);
 }  }
Line 234  ip6intr(void *arg __unused)
Line 242  ip6intr(void *arg __unused)
 extern struct   route ip6_forward_rt;  extern struct   route ip6_forward_rt;
   
 void  void
 ip6_input(struct mbuf *m)  ip6_input(struct mbuf *m, struct ifnet *rcvif)
 {  {
         struct ip6_hdr *ip6;          struct ip6_hdr *ip6;
         int hit, off = sizeof(struct ip6_hdr), nest;          int hit, off = sizeof(struct ip6_hdr), nest;
Line 265  ip6_input(struct mbuf *m)
Line 273  ip6_input(struct mbuf *m)
         } else {          } else {
 #define M2MMAX  32  #define M2MMAX  32
                 if (m->m_next) {                  if (m->m_next) {
                         if (m->m_flags & M_LOOP) {                          if (m->m_flags & M_LOOP)
                         /*XXX*/ IP6_STATINC(IP6_STAT_M2M + lo0ifp->if_index);                          /*XXX*/ IP6_STATINC(IP6_STAT_M2M + lo0ifp->if_index);
                         } else if (m->m_pkthdr.rcvif->if_index < M2MMAX) {                          else if (rcvif->if_index < M2MMAX)
                                 IP6_STATINC(IP6_STAT_M2M +                                  IP6_STATINC(IP6_STAT_M2M + rcvif->if_index);
                                             m->m_pkthdr.rcvif->if_index);                          else
                         } else  
                                 IP6_STATINC(IP6_STAT_M2M);                                  IP6_STATINC(IP6_STAT_M2M);
                 } else                  } else
                         IP6_STATINC(IP6_STAT_M1);                          IP6_STATINC(IP6_STAT_M1);
 #undef M2MMAX  #undef M2MMAX
         }          }
   
         in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_receive);          in6_ifstat_inc(rcvif, ifs6_in_receive);
         IP6_STATINC(IP6_STAT_TOTAL);          IP6_STATINC(IP6_STAT_TOTAL);
   
         /*          /*
Line 287  ip6_input(struct mbuf *m)
Line 294  ip6_input(struct mbuf *m)
          * IPv6 header is in the first mbuf of the chain.           * IPv6 header is in the first mbuf of the chain.
          */           */
         if (IP6_HDR_ALIGNED_P(mtod(m, void *)) == 0) {          if (IP6_HDR_ALIGNED_P(mtod(m, void *)) == 0) {
                 struct ifnet *inifp = m->m_pkthdr.rcvif;  
                 if ((m = m_copyup(m, sizeof(struct ip6_hdr),                  if ((m = m_copyup(m, sizeof(struct ip6_hdr),
                                   (max_linkhdr + 3) & ~3)) == NULL) {                                    (max_linkhdr + 3) & ~3)) == NULL) {
                         /* XXXJRT new stat, please */                          /* XXXJRT new stat, please */
                         IP6_STATINC(IP6_STAT_TOOSMALL);                          IP6_STATINC(IP6_STAT_TOOSMALL);
                         in6_ifstat_inc(inifp, ifs6_in_hdrerr);                          in6_ifstat_inc(rcvif, ifs6_in_hdrerr);
                         return;                          return;
                 }                  }
         } else if (__predict_false(m->m_len < sizeof(struct ip6_hdr))) {          } else if (__predict_false(m->m_len < sizeof(struct ip6_hdr))) {
                 struct ifnet *inifp = m->m_pkthdr.rcvif;  
                 if ((m = m_pullup(m, sizeof(struct ip6_hdr))) == NULL) {                  if ((m = m_pullup(m, sizeof(struct ip6_hdr))) == NULL) {
                         IP6_STATINC(IP6_STAT_TOOSMALL);                          IP6_STATINC(IP6_STAT_TOOSMALL);
                         in6_ifstat_inc(inifp, ifs6_in_hdrerr);                          in6_ifstat_inc(rcvif, ifs6_in_hdrerr);
                         return;                          return;
                 }                  }
         }          }
Line 308  ip6_input(struct mbuf *m)
Line 313  ip6_input(struct mbuf *m)
   
         if ((ip6->ip6_vfc & IPV6_VERSION_MASK) != IPV6_VERSION) {          if ((ip6->ip6_vfc & IPV6_VERSION_MASK) != IPV6_VERSION) {
                 IP6_STATINC(IP6_STAT_BADVERS);                  IP6_STATINC(IP6_STAT_BADVERS);
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_hdrerr);                  in6_ifstat_inc(rcvif, ifs6_in_hdrerr);
                 goto bad;                  goto bad;
         }          }
   
Line 338  ip6_input(struct mbuf *m)
Line 343  ip6_input(struct mbuf *m)
                 struct in6_addr odst;                  struct in6_addr odst;
   
                 odst = ip6->ip6_dst;                  odst = ip6->ip6_dst;
                 if (pfil_run_hooks(inet6_pfil_hook, &m, m->m_pkthdr.rcvif,                  if (pfil_run_hooks(inet6_pfil_hook, &m, rcvif, PFIL_IN) != 0)
                                    PFIL_IN) != 0)  
                         return;                          return;
                 if (m == NULL)                  if (m == NULL)
                         return;                          return;
Line 365  ip6_input(struct mbuf *m)
Line 369  ip6_input(struct mbuf *m)
                  * XXX: "badscope" is not very suitable for a multicast source.                   * XXX: "badscope" is not very suitable for a multicast source.
                  */                   */
                 IP6_STATINC(IP6_STAT_BADSCOPE);                  IP6_STATINC(IP6_STAT_BADSCOPE);
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);                  in6_ifstat_inc(rcvif, ifs6_in_addrerr);
                 goto bad;                  goto bad;
         }          }
         /*          /*
Line 383  ip6_input(struct mbuf *m)
Line 387  ip6_input(struct mbuf *m)
         if (IN6_IS_ADDR_V4MAPPED(&ip6->ip6_src) ||          if (IN6_IS_ADDR_V4MAPPED(&ip6->ip6_src) ||
             IN6_IS_ADDR_V4MAPPED(&ip6->ip6_dst)) {              IN6_IS_ADDR_V4MAPPED(&ip6->ip6_dst)) {
                 IP6_STATINC(IP6_STAT_BADSCOPE);                  IP6_STATINC(IP6_STAT_BADSCOPE);
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);                  in6_ifstat_inc(rcvif, ifs6_in_addrerr);
                 goto bad;                  goto bad;
         }          }
 #if 0  #if 0
Line 397  ip6_input(struct mbuf *m)
Line 401  ip6_input(struct mbuf *m)
         if (IN6_IS_ADDR_V4COMPAT(&ip6->ip6_src) ||          if (IN6_IS_ADDR_V4COMPAT(&ip6->ip6_src) ||
             IN6_IS_ADDR_V4COMPAT(&ip6->ip6_dst)) {              IN6_IS_ADDR_V4COMPAT(&ip6->ip6_dst)) {
                 IP6_STATINC(IP6_STAT_BADSCOPE);                  IP6_STATINC(IP6_STAT_BADSCOPE);
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);                  in6_ifstat_inc(rcvif, ifs6_in_addrerr);
                 goto bad;                  goto bad;
         }          }
 #endif  #endif
Line 420  ip6_input(struct mbuf *m)
Line 424  ip6_input(struct mbuf *m)
                 IP6_STATINC(IP6_STAT_BADSCOPE); /* XXX */                  IP6_STATINC(IP6_STAT_BADSCOPE); /* XXX */
                 goto bad;                  goto bad;
         }          }
         if (in6_setscope(&ip6->ip6_src, m->m_pkthdr.rcvif, NULL) ||          if (in6_setscope(&ip6->ip6_src, rcvif, NULL) ||
             in6_setscope(&ip6->ip6_dst, m->m_pkthdr.rcvif, NULL)) {              in6_setscope(&ip6->ip6_dst, rcvif, NULL)) {
                 IP6_STATINC(IP6_STAT_BADSCOPE);                  IP6_STATINC(IP6_STAT_BADSCOPE);
                 goto bad;                  goto bad;
         }          }
Line 432  ip6_input(struct mbuf *m)
Line 436  ip6_input(struct mbuf *m)
         if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst)) {          if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst)) {
                 struct  in6_multi *in6m = 0;                  struct  in6_multi *in6m = 0;
   
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_mcast);                  in6_ifstat_inc(rcvif, ifs6_in_mcast);
                 /*                  /*
                  * See if we belong to the destination multicast group on the                   * See if we belong to the destination multicast group on the
                  * arrival interface.                   * arrival interface.
                  */                   */
                 IN6_LOOKUP_MULTI(ip6->ip6_dst, m->m_pkthdr.rcvif, in6m);                  IN6_LOOKUP_MULTI(ip6->ip6_dst, rcvif, in6m);
                 if (in6m)                  if (in6m)
                         ours = 1;                          ours = 1;
                 else if (!ip6_mrouter) {                  else if (!ip6_mrouter) {
Line 445  ip6_input(struct mbuf *m)
Line 449  ip6_input(struct mbuf *m)
                         ip6s[IP6_STAT_NOTMEMBER]++;                          ip6s[IP6_STAT_NOTMEMBER]++;
                         ip6s[IP6_STAT_CANTFORWARD]++;                          ip6s[IP6_STAT_CANTFORWARD]++;
                         IP6_STAT_PUTREF();                          IP6_STAT_PUTREF();
                         in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);                          in6_ifstat_inc(rcvif, ifs6_in_discard);
                         goto bad;                          goto bad;
                 }                  }
                 deliverifp = m->m_pkthdr.rcvif;                  deliverifp = rcvif;
                 goto hbhcheck;                  goto hbhcheck;
         }          }
   
Line 530  ip6_input(struct mbuf *m)
Line 534  ip6_input(struct mbuf *m)
          * working right.           * working right.
          */           */
         struct ifaddr *ifa;          struct ifaddr *ifa;
         IFADDR_FOREACH(ifa, m->m_pkthdr.rcvif) {          IFADDR_READER_FOREACH(ifa, rcvif) {
                 if (ifa->ifa_addr == NULL)  
                         continue;       /* just for safety */  
                 if (ifa->ifa_addr->sa_family != AF_INET6)                  if (ifa->ifa_addr->sa_family != AF_INET6)
                         continue;                          continue;
                 if (IN6_ARE_ADDR_EQUAL(IFA_IN6(ifa), &ip6->ip6_dst)) {                  if (IN6_ARE_ADDR_EQUAL(IFA_IN6(ifa), &ip6->ip6_dst)) {
Line 550  ip6_input(struct mbuf *m)
Line 552  ip6_input(struct mbuf *m)
          */           */
         if (!ip6_forwarding) {          if (!ip6_forwarding) {
                 IP6_STATINC(IP6_STAT_CANTFORWARD);                  IP6_STATINC(IP6_STAT_CANTFORWARD);
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);                  in6_ifstat_inc(rcvif, ifs6_in_discard);
                 goto bad;                  goto bad;
         }          }
   
Line 585  ip6_input(struct mbuf *m)
Line 587  ip6_input(struct mbuf *m)
   
                 if (ip6_hopopts_input(&plen, &rtalert, &m, &off)) {                  if (ip6_hopopts_input(&plen, &rtalert, &m, &off)) {
 #if 0   /*touches NULL pointer*/  #if 0   /*touches NULL pointer*/
                         in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);                          in6_ifstat_inc(rcvif, ifs6_in_discard);
 #endif  #endif
                         return; /* m have already been freed */                          return; /* m have already been freed */
                 }                  }
Line 605  ip6_input(struct mbuf *m)
Line 607  ip6_input(struct mbuf *m)
                          * (non-zero) payload length to the variable plen.                           * (non-zero) payload length to the variable plen.
                          */                           */
                         IP6_STATINC(IP6_STAT_BADOPTIONS);                          IP6_STATINC(IP6_STAT_BADOPTIONS);
                         in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);                          in6_ifstat_inc(rcvif, ifs6_in_discard);
                         in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_hdrerr);                          in6_ifstat_inc(rcvif, ifs6_in_hdrerr);
                         icmp6_error(m, ICMP6_PARAM_PROB,                          icmp6_error(m, ICMP6_PARAM_PROB,
                                     ICMP6_PARAMPROB_HEADER,                                      ICMP6_PARAMPROB_HEADER,
                                     (char *)&ip6->ip6_plen - (char *)ip6);                                      (char *)&ip6->ip6_plen - (char *)ip6);
Line 638  ip6_input(struct mbuf *m)
Line 640  ip6_input(struct mbuf *m)
          */           */
         if (m->m_pkthdr.len - sizeof(struct ip6_hdr) < plen) {          if (m->m_pkthdr.len - sizeof(struct ip6_hdr) < plen) {
                 IP6_STATINC(IP6_STAT_TOOSHORT);                  IP6_STATINC(IP6_STAT_TOOSHORT);
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_truncated);                  in6_ifstat_inc(rcvif, ifs6_in_truncated);
                 goto bad;                  goto bad;
         }          }
         if (m->m_pkthdr.len > sizeof(struct ip6_hdr) + plen) {          if (m->m_pkthdr.len > sizeof(struct ip6_hdr) + plen) {
Line 661  ip6_input(struct mbuf *m)
Line 663  ip6_input(struct mbuf *m)
                  * ip6_mforward() returns a non-zero value, the packet                   * ip6_mforward() returns a non-zero value, the packet
                  * must be discarded, else it may be accepted below.                   * must be discarded, else it may be accepted below.
                  */                   */
                 if (ip6_mrouter && ip6_mforward(ip6, m->m_pkthdr.rcvif, m)) {                  if (ip6_mrouter && ip6_mforward(ip6, rcvif, m)) {
                         IP6_STATINC(IP6_STAT_CANTFORWARD);                          IP6_STATINC(IP6_STAT_CANTFORWARD);
                         m_freem(m);                          m_freem(m);
                         return;                          return;
Line 689  ip6_input(struct mbuf *m)
Line 691  ip6_input(struct mbuf *m)
         if (IN6_IS_ADDR_V4MAPPED(&ip6->ip6_src) ||          if (IN6_IS_ADDR_V4MAPPED(&ip6->ip6_src) ||
             IN6_IS_ADDR_V4MAPPED(&ip6->ip6_dst)) {              IN6_IS_ADDR_V4MAPPED(&ip6->ip6_dst)) {
                 IP6_STATINC(IP6_STAT_BADSCOPE);                  IP6_STATINC(IP6_STAT_BADSCOPE);
                 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);                  in6_ifstat_inc(rcvif, ifs6_in_addrerr);
                 goto bad;                  goto bad;
         }          }
   
Line 712  ip6_input(struct mbuf *m)
Line 714  ip6_input(struct mbuf *m)
         while (nxt != IPPROTO_DONE) {          while (nxt != IPPROTO_DONE) {
                 if (ip6_hdrnestlimit && (++nest > ip6_hdrnestlimit)) {                  if (ip6_hdrnestlimit && (++nest > ip6_hdrnestlimit)) {
                         IP6_STATINC(IP6_STAT_TOOMANYHDR);                          IP6_STATINC(IP6_STAT_TOOMANYHDR);
                         in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_hdrerr);                          in6_ifstat_inc(rcvif, ifs6_in_hdrerr);
                         goto bad;                          goto bad;
                 }                  }
   
Line 722  ip6_input(struct mbuf *m)
Line 724  ip6_input(struct mbuf *m)
                  */                   */
                 if (m->m_pkthdr.len < off) {                  if (m->m_pkthdr.len < off) {
                         IP6_STATINC(IP6_STAT_TOOSHORT);                          IP6_STATINC(IP6_STAT_TOOSHORT);
                         in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_truncated);                          in6_ifstat_inc(rcvif, ifs6_in_truncated);
                         goto bad;                          goto bad;
                 }                  }
   
                 if (nxt == IPPROTO_ROUTING) {                  if (nxt == IPPROTO_ROUTING) {
                         if (rh_present++) {                          if (rh_present++) {
                                 in6_ifstat_inc(m->m_pkthdr.rcvif,                                  in6_ifstat_inc(rcvif, ifs6_in_hdrerr);
                                     ifs6_in_hdrerr);  
                                 IP6_STATINC(IP6_STAT_BADOPTIONS);                                  IP6_STATINC(IP6_STAT_BADOPTIONS);
                                 goto bad;                                  goto bad;
                         }                          }
Line 1062  ip6_savecontrol(struct in6pcb *in6p, str
Line 1063  ip6_savecontrol(struct in6pcb *in6p, str
   
                 memcpy(&pi6.ipi6_addr, &ip6->ip6_dst, sizeof(struct in6_addr));                  memcpy(&pi6.ipi6_addr, &ip6->ip6_dst, sizeof(struct in6_addr));
                 in6_clearscope(&pi6.ipi6_addr); /* XXX */                  in6_clearscope(&pi6.ipi6_addr); /* XXX */
                 pi6.ipi6_ifindex = m->m_pkthdr.rcvif ?                  pi6.ipi6_ifindex = m->m_pkthdr.rcvif_index;
                     m->m_pkthdr.rcvif->if_index : 0;  
                 *mp = sbcreatecontrol((void *) &pi6,                  *mp = sbcreatecontrol((void *) &pi6,
                     sizeof(struct in6_pktinfo),                      sizeof(struct in6_pktinfo),
                     IS2292(IPV6_2292PKTINFO, IPV6_PKTINFO), IPPROTO_IPV6);                      IS2292(IPV6_2292PKTINFO, IPV6_PKTINFO), IPPROTO_IPV6);

Legend:
Removed from v.1.149.4.5  
changed lines
  Added in v.1.149.4.7

CVSweb <webmaster@jp.NetBSD.org>