On Fri, 4 Nov 2016 12:01:58 +0100
Martin Pieuchot <[email protected]> wrote:

> Rather than trying to keep this old routing table like function alive
> by reimplementing rn_refines(), let's get rid of it.
> 
> ok?
> 
> Index: net/route.c
> ===================================================================
> RCS file: /cvs/src/sys/net/route.c,v
> retrieving revision 1.333
> diff -u -p -r1.333 route.c
> --- net/route.c       6 Oct 2016 19:09:08 -0000       1.333
> +++ net/route.c       4 Nov 2016 10:51:55 -0000
> @@ -550,11 +550,16 @@ rtredirect(struct sockaddr *dst, struct 
>       splsoftassert(IPL_SOFTNET);
>  
>       /* verify the gateway is directly reachable */
> -     if ((ifa = ifa_ifwithnet(gateway, rdomain)) == NULL) {
> +     rt = rtalloc(gateway, 0, rdomain);
> +     if (!rtisvalid(rt) || ISSET(rt->rt_flags, RTF_GATEWAY)) {
> +             rtfree(rt);
>               error = ENETUNREACH;
>               goto out;
>       }
> -     ifidx = ifa->ifa_ifp->if_index;
> +     ifidx = rt->rt_ifidx;
> +     rtfree(rt);
> +     rt = NULL;
> +
>       rt = rtable_lookup(rdomain, dst, NULL, NULL, RTP_ANY);
>       /*
>        * If the redirect isn't from our current router for this
> dst, Index: net/if.c
> ===================================================================
> RCS file: /cvs/src/sys/net/if.c,v
> retrieving revision 1.456
> diff -u -p -r1.456 if.c
> --- net/if.c  19 Oct 2016 02:05:49 -0000      1.456
> +++ net/if.c  4 Nov 2016 10:55:03 -0000
> @@ -1282,47 +1282,6 @@ ifa_ifwithdstaddr(struct sockaddr *addr,
>  }
>  
>  /*
> - * Find an interface on a specific network.  If many, choice
> - * is most specific found.
> - */
> -struct ifaddr *
> -ifa_ifwithnet(struct sockaddr *sa, u_int rtableid)
> -{
> -     struct ifnet *ifp;
> -     struct ifaddr *ifa, *ifa_maybe = NULL;
> -     char *cplim, *addr_data = sa->sa_data;
> -     u_int rdomain;
> -
> -     KERNEL_ASSERT_LOCKED();
> -     rdomain = rtable_l2(rtableid);
> -     TAILQ_FOREACH(ifp, &ifnet, if_list) {
> -             if (ifp->if_rdomain != rdomain)
> -                     continue;
> -             TAILQ_FOREACH(ifa, &ifp->if_addrlist, ifa_list) {
> -                     char *cp, *cp2, *cp3;
> -
> -                     if (ifa->ifa_addr->sa_family !=
> sa->sa_family ||
> -                         ifa->ifa_netmask == 0)
> -                             next: continue;
> -                     cp = addr_data;
> -                     cp2 = ifa->ifa_addr->sa_data;
> -                     cp3 = ifa->ifa_netmask->sa_data;
> -                     cplim = (char *)ifa->ifa_netmask +
> -                             ifa->ifa_netmask->sa_len;
> -                     while (cp3 < cplim)
> -                             if ((*cp++ ^ *cp2++) & *cp3++)
> -                                 /* want to continue for() loop */
> -                                     goto next;
> -                     if (ifa_maybe == 0 ||
> -                         rn_refines((caddr_t)ifa->ifa_netmask,
> -                         (caddr_t)ifa_maybe->ifa_netmask))
> -                             ifa_maybe = ifa;
> -             }
> -     }
> -     return (ifa_maybe);
> -}
> -
> -/*
>   * Find an interface address specific to an interface best matching
>   * a given address.
>   */
> Index: net/if_var.h
> ===================================================================
> RCS file: /cvs/src/sys/net/if_var.h,v
> retrieving revision 1.75
> diff -u -p -r1.75 if_var.h
> --- net/if_var.h      4 Sep 2016 15:46:39 -0000       1.75
> +++ net/if_var.h      4 Nov 2016 10:54:55 -0000
> @@ -304,7 +304,6 @@ void      p2p_rtrequest(struct ifnet *, int, 
>  
>  struct       ifaddr *ifa_ifwithaddr(struct sockaddr *, u_int);
>  struct       ifaddr *ifa_ifwithdstaddr(struct sockaddr *, u_int);
> -struct       ifaddr *ifa_ifwithnet(struct sockaddr *, u_int);
>  struct       ifaddr *ifaof_ifpforaddr(struct sockaddr *, struct
> ifnet *); void        ifafree(struct ifaddr *);
>  

Everything above is ok vgross@

> Index: netinet/ip_input.c
> ===================================================================
> RCS file: /cvs/src/sys/netinet/ip_input.c,v
> retrieving revision 1.282
> diff -u -p -r1.282 ip_input.c
> --- netinet/ip_input.c        22 Sep 2016 10:12:25 -0000      1.282
> +++ netinet/ip_input.c        4 Nov 2016 10:54:49 -0000
> @@ -1117,37 +1117,19 @@ ip_dooptions(struct mbuf *m, struct ifne
>                       ipaddr.sin_len = sizeof(ipaddr);
>                       memcpy(&ipaddr.sin_addr, cp + off,
>                           sizeof(ipaddr.sin_addr));
> -                     if (opt == IPOPT_SSRR) {
> -                             if ((ia = ifatoia(ifa_ifwithdstaddr(
> -                                 sintosa(&ipaddr),
> -                                 m->m_pkthdr.ph_rtableid))) ==
> NULL)
> -                                     ia = ifatoia(ifa_ifwithnet(
> -                                         sintosa(&ipaddr),
> -
> m->m_pkthdr.ph_rtableid));
> -                             if (ia == NULL) {
> -                                     type = ICMP_UNREACH;
> -                                     code = ICMP_UNREACH_SRCFAIL;
> -                                     goto bad;
> -                             }
> -                             memcpy(cp + off,
> &ia->ia_addr.sin_addr,
> -                                 sizeof(struct in_addr));
> -                             cp[IPOPT_OFFSET] += sizeof(struct
> in_addr);
> -                     } else {
> -                             /* keep packet in the virtual
> instance */
> -                             rt = rtalloc(sintosa(&ipaddr),
> RT_RESOLVE,
> -                                 rtableid);
> -                             if (!rtisvalid(rt)) {
> -                                     type = ICMP_UNREACH;
> -                                     code = ICMP_UNREACH_SRCFAIL;
> -                                     rtfree(rt);
> -                                     goto bad;
> -                             }
> -                             ia = ifatoia(rt->rt_ifa);
> -                             memcpy(cp + off,
> &ia->ia_addr.sin_addr,
> -                                 sizeof(struct in_addr));
> +                     /* keep packet in the virtual instance */
> +                     rt = rtalloc(sintosa(&ipaddr), RT_RESOLVE,
> rtableid);
> +                     if (!rtisvalid(rt)) {
> +                             type = ICMP_UNREACH;
> +                             code = ICMP_UNREACH_SRCFAIL;
>                               rtfree(rt);
> -                             cp[IPOPT_OFFSET] += sizeof(struct
> in_addr);
> +                             goto bad;
>                       }
> +                     ia = ifatoia(rt->rt_ifa);
> +                     memcpy(cp + off, &ia->ia_addr.sin_addr,
> +                         sizeof(struct in_addr));
> +                     rtfree(rt);
> +                     cp[IPOPT_OFFSET] += sizeof(struct in_addr);
>                       ip->ip_dst = ipaddr.sin_addr;
>                       /*
>                        * Let ip_intr's mcast routing check handle
> mcast pkts
> 

Why are you killing Strict Source Route Record ? Just as you did with
rtredirect(), you can check whether RTF_GATEWAY is set and send back
an ICMP_UNREACH if so. Or did I miss something ?

Reply via email to