Author: bz
Date: Thu Sep  9 06:43:18 2010
New Revision: 212351
URL: http://svn.freebsd.org/changeset/base/212351

Log:
  MFC r212155:
    MFp4 CH=183052 183053 183258:
  
      In protosw we define pr_protocol as short, while on the wire
      it is an uint8_t.  That way we can have "internal" protocols
      like DIVERT, SEND or gaps for modules (PROTO_SPACER).
      Switch ipproto_{un,}register to accept a short protocol number(*)
      and do an upfront check for valid boundries. With this we
      also consistently report EPROTONOSUPPORT for out of bounds
      protocols, as we did for proto == 0.  This allows a caller
      to not error for this case, which is especially important
      if we want to automatically call these from domain handling.
  
      (*) the functions have been without any in-tree consumer
      since the initial introducation, so this is considered save.
  
      Implement ip6proto_{un,}register() similarly to their legacy IP
      counter parts to allow modules to hook up dynamically.
  
    Reviewed by:        philip, will

Modified:
  stable/8/sys/netinet/ip_input.c
  stable/8/sys/netinet/ip_var.h
  stable/8/sys/netinet6/ip6_input.c
  stable/8/sys/netinet6/ip6_var.h
Directory Properties:
  stable/8/sys/   (props changed)
  stable/8/sys/amd64/include/xen/   (props changed)
  stable/8/sys/cddl/contrib/opensolaris/   (props changed)
  stable/8/sys/contrib/dev/acpica/   (props changed)
  stable/8/sys/contrib/pf/   (props changed)
  stable/8/sys/dev/xen/xenpci/   (props changed)

Modified: stable/8/sys/netinet/ip_input.c
==============================================================================
--- stable/8/sys/netinet/ip_input.c     Thu Sep  9 03:33:07 2010        
(r212350)
+++ stable/8/sys/netinet/ip_input.c     Thu Sep  9 06:43:18 2010        
(r212351)
@@ -1293,12 +1293,12 @@ ip_drain(void)
  * in inetsw[], either statically or through pf_proto_register().
  */
 int
-ipproto_register(u_char ipproto)
+ipproto_register(short ipproto)
 {
        struct protosw *pr;
 
        /* Sanity checks. */
-       if (ipproto == 0)
+       if (ipproto <= 0 || ipproto >= IPPROTO_MAX)
                return (EPROTONOSUPPORT);
 
        /*
@@ -1316,24 +1316,20 @@ ipproto_register(u_char ipproto)
             pr < inetdomain.dom_protoswNPROTOSW; pr++) {
                if (pr->pr_domain->dom_family == PF_INET &&
                    pr->pr_protocol && pr->pr_protocol == ipproto) {
-                       /* Be careful to only index valid IP protocols. */
-                       if (pr->pr_protocol < IPPROTO_MAX) {
-                               ip_protox[pr->pr_protocol] = pr - inetsw;
-                               return (0);
-                       } else
-                               return (EINVAL);
+                       ip_protox[pr->pr_protocol] = pr - inetsw;
+                       return (0);
                }
        }
        return (EPROTONOSUPPORT);
 }
 
 int
-ipproto_unregister(u_char ipproto)
+ipproto_unregister(short ipproto)
 {
        struct protosw *pr;
 
        /* Sanity checks. */
-       if (ipproto == 0)
+       if (ipproto <= 0 || ipproto >= IPPROTO_MAX)
                return (EPROTONOSUPPORT);
 
        /* Check if the protocol was indeed registered. */

Modified: stable/8/sys/netinet/ip_var.h
==============================================================================
--- stable/8/sys/netinet/ip_var.h       Thu Sep  9 03:33:07 2010        
(r212350)
+++ stable/8/sys/netinet/ip_var.h       Thu Sep  9 06:43:18 2010        
(r212351)
@@ -220,8 +220,8 @@ extern int
 int    ip_output(struct mbuf *,
            struct mbuf *, struct route *, int, struct ip_moptions *,
            struct inpcb *);
-int    ipproto_register(u_char);
-int    ipproto_unregister(u_char);
+int    ipproto_register(short);
+int    ipproto_unregister(short);
 struct mbuf *
        ip_reass(struct mbuf *);
 struct in_ifaddr *

Modified: stable/8/sys/netinet6/ip6_input.c
==============================================================================
--- stable/8/sys/netinet6/ip6_input.c   Thu Sep  9 03:33:07 2010        
(r212350)
+++ stable/8/sys/netinet6/ip6_input.c   Thu Sep  9 06:43:18 2010        
(r212351)
@@ -202,6 +202,64 @@ ip6_init(void)
        netisr_register(&ip6_nh);
 }
 
+/*
+ * The protocol to be inserted into ip6_protox[] must be already registered
+ * in inet6sw[], either statically or through pf_proto_register().
+ */
+int
+ip6proto_register(short ip6proto)
+{
+       struct ip6protosw *pr;
+
+       /* Sanity checks. */
+       if (ip6proto <= 0 || ip6proto >= IPPROTO_MAX)
+               return (EPROTONOSUPPORT);
+
+       /*
+        * The protocol slot must not be occupied by another protocol
+        * already.  An index pointing to IPPROTO_RAW is unused.
+        */
+       pr = (struct ip6protosw *)pffindproto(PF_INET6, IPPROTO_RAW, SOCK_RAW);
+       if (pr == NULL)
+               return (EPFNOSUPPORT);
+       if (ip6_protox[ip6proto] != pr - inet6sw)       /* IPPROTO_RAW */
+               return (EEXIST);
+
+       /*
+        * Find the protocol position in inet6sw[] and set the index.
+        */
+       for (pr = (struct ip6protosw *)inet6domain.dom_protosw;
+           pr < (struct ip6protosw *)inet6domain.dom_protoswNPROTOSW; pr++) {
+               if (pr->pr_domain->dom_family == PF_INET6 &&
+                   pr->pr_protocol && pr->pr_protocol == ip6proto) {
+                       ip6_protox[pr->pr_protocol] = pr - inet6sw;
+                       return (0);
+               }
+       }
+       return (EPROTONOSUPPORT);
+}
+
+int
+ip6proto_unregister(short ip6proto)
+{
+       struct ip6protosw *pr;
+
+       /* Sanity checks. */
+       if (ip6proto <= 0 || ip6proto >= IPPROTO_MAX)
+               return (EPROTONOSUPPORT);
+
+       /* Check if the protocol was indeed registered. */
+       pr = (struct ip6protosw *)pffindproto(PF_INET6, IPPROTO_RAW, SOCK_RAW);
+       if (pr == NULL)
+               return (EPFNOSUPPORT);
+       if (ip6_protox[ip6proto] == pr - inet6sw)       /* IPPROTO_RAW */
+               return (ENOENT);
+
+       /* Reset the protocol slot to IPPROTO_RAW. */
+       ip6_protox[ip6proto] = pr - inet6sw;
+       return (0);
+}
+
 #ifdef VIMAGE
 void
 ip6_destroy()

Modified: stable/8/sys/netinet6/ip6_var.h
==============================================================================
--- stable/8/sys/netinet6/ip6_var.h     Thu Sep  9 03:33:07 2010        
(r212350)
+++ stable/8/sys/netinet6/ip6_var.h     Thu Sep  9 06:43:18 2010        
(r212351)
@@ -368,6 +368,9 @@ void        ip6_init __P((void));
 #ifdef VIMAGE
 void   ip6_destroy __P((void));
 #endif
+int    ip6proto_register(short);
+int    ip6proto_unregister(short);
+
 void   ip6_input __P((struct mbuf *));
 struct in6_ifaddr *ip6_getdstifaddr __P((struct mbuf *));
 void   ip6_freepcbopts __P((struct ip6_pktopts *));
_______________________________________________
svn-src-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"

Reply via email to