Diff below make the function always iterate on all the interfaces.

After that I'd like to change ifa_ifwithaddr() to only match unicast
addresses and use in_broadcast() in the few places where we also accept
broadcast addresses.
This would prevent people from matching a broadcast address when they
don't want to.

Ok?

Index: netinet/in.c
===================================================================
RCS file: /cvs/src/sys/netinet/in.c,v
retrieving revision 1.109
diff -u -p -r1.109 in.c
--- netinet/in.c        20 Nov 2014 10:06:54 -0000      1.109
+++ netinet/in.c        20 Nov 2014 14:15:30 -0000
@@ -876,36 +876,19 @@ in_scrubprefix(struct in_ifaddr *ia0)
 }
 
 /*
- * Return 1 if the address might be a local broadcast address.
+ * Return 1 if the address is a local broadcast address.
  */
 int
-in_broadcast(struct in_addr in, struct ifnet *ifp, u_int rtableid)
+in_broadcast(struct in_addr in, u_int rtableid)
 {
-       struct ifnet *ifn, *if_first, *if_target;
+       struct ifnet *ifn;
        struct ifaddr *ifa;
        u_int rdomain;
 
        rdomain = rtable_l2(rtableid);
 
-       if (in.s_addr == INADDR_BROADCAST ||
-           in.s_addr == INADDR_ANY)
-               return 1;
-
-       if (ifp == NULL) {
-               if_first = TAILQ_FIRST(&ifnet);
-               if_target = 0;
-       } else {
-               if_first = ifp;
-               if_target = TAILQ_NEXT(ifp, if_list);
-       }
-
 #define ia (ifatoia(ifa))
-       /*
-        * Look through the list of addresses for a match
-        * with a broadcast address.
-        * If ifp is NULL, check against all the interfaces.
-        */
-        for (ifn = if_first; ifn != if_target; ifn = TAILQ_NEXT(ifn, if_list)) 
{
+       TAILQ_FOREACH(ifn, &ifnet, if_list) {
                if (ifn->if_rdomain != rdomain)
                        continue;
                if ((ifn->if_flags & IFF_BROADCAST) == 0)
Index: netinet/in.h
===================================================================
RCS file: /cvs/src/sys/netinet/in.h,v
retrieving revision 1.109
diff -u -p -r1.109 in.h
--- netinet/in.h        12 Jul 2014 16:25:08 -0000      1.109
+++ netinet/in.h        20 Nov 2014 14:15:30 -0000
@@ -782,7 +782,7 @@ extern         int inetctlerrmap[];
 extern    struct ifqueue ipintrq;      /* ip packet input queue */
 extern    struct in_addr zeroin_addr;
 
-int       in_broadcast(struct in_addr, struct ifnet *, u_int);
+int       in_broadcast(struct in_addr, u_int);
 int       in_canforward(struct in_addr);
 int       in_cksum(struct mbuf *, int);
 int       in4_cksum(struct mbuf *, u_int8_t, int, int);
Index: netinet/tcp_usrreq.c
===================================================================
RCS file: /cvs/src/sys/netinet/tcp_usrreq.c,v
retrieving revision 1.121
diff -u -p -r1.121 tcp_usrreq.c
--- netinet/tcp_usrreq.c        18 Nov 2014 02:37:31 -0000      1.121
+++ netinet/tcp_usrreq.c        20 Nov 2014 14:15:31 -0000
@@ -275,9 +275,9 @@ tcp_usrreq(so, req, m, nam, control, p)
 #endif /* INET6 */
                {
                        if ((sin->sin_addr.s_addr == INADDR_ANY) ||
+                           (sin->sin_addr.s_addr == INADDR_BROADCAST) ||
                            IN_MULTICAST(sin->sin_addr.s_addr) ||
-                           in_broadcast(sin->sin_addr, NULL,
-                           inp->inp_rtableid)) {
+                           in_broadcast(sin->sin_addr, inp->inp_rtableid)) {
                                error = EINVAL;
                                break;
                        }

Reply via email to