Author: tuexen
Date: Sun Jun 21 23:12:56 2020
New Revision: 362473
URL: https://svnweb.freebsd.org/changeset/base/362473

Log:
  Cleanup the defintion of struct sctp_getaddresses. This stucture
  is used by the IPPROTO_SCTP level socket options SCTP_GET_PEER_ADDRESSES
  and SCTP_GET_LOCAL_ADDRESSES, which are used by libc to implement
  sctp_getladdrs() and sctp_getpaddrs().
  These changes allow an old libc to work on a newer kernel.

Modified:
  head/lib/libc/net/sctp_sys_calls.c
  head/sys/netinet/sctp_uio.h
  head/sys/netinet/sctp_usrreq.c

Modified: head/lib/libc/net/sctp_sys_calls.c
==============================================================================
--- head/lib/libc/net/sctp_sys_calls.c  Sun Jun 21 22:09:30 2020        
(r362472)
+++ head/lib/libc/net/sctp_sys_calls.c  Sun Jun 21 23:12:56 2020        
(r362473)
@@ -406,7 +406,7 @@ sctp_getpaddrs(int sd, sctp_assoc_t id, struct sockadd
                return (-1);
        }
        /* size required is returned in 'asoc' */
-       opt_len = (socklen_t)((size_t)asoc + sizeof(sctp_assoc_t));
+       opt_len = (socklen_t)((size_t)asoc + sizeof(struct sctp_getaddresses));
        addrs = calloc(1, (size_t)opt_len);
        if (addrs == NULL) {
                errno = ENOMEM;
@@ -419,9 +419,9 @@ sctp_getpaddrs(int sd, sctp_assoc_t id, struct sockadd
                free(addrs);
                return (-1);
        }
-       *raddrs = (struct sockaddr *)&addrs->addr[0];
+       *raddrs = &addrs->addr[0].sa;
        cnt = 0;
-       sa = (struct sockaddr *)&addrs->addr[0];
+       sa = &addrs->addr[0].sa;
        lim = (caddr_t)addrs + opt_len;
        while (((caddr_t)sa < lim) && (sa->sa_len > 0)) {
                sa = (struct sockaddr *)((caddr_t)sa + sa->sa_len);
@@ -436,7 +436,7 @@ sctp_freepaddrs(struct sockaddr *addrs)
        void *fr_addr;
 
        /* Take away the hidden association id */
-       fr_addr = (void *)((caddr_t)addrs - sizeof(sctp_assoc_t));
+       fr_addr = (void *)((caddr_t)addrs - offsetof(struct sctp_getaddresses, 
addr));
        /* Now free it */
        free(fr_addr);
 }
@@ -466,7 +466,7 @@ sctp_getladdrs(int sd, sctp_assoc_t id, struct sockadd
                errno = ENOTCONN;
                return (-1);
        }
-       opt_len = (socklen_t)(size_of_addresses + sizeof(sctp_assoc_t));
+       opt_len = (socklen_t)(size_of_addresses + sizeof(struct 
sctp_getaddresses));
        addrs = calloc(1, (size_t)opt_len);
        if (addrs == NULL) {
                errno = ENOMEM;
@@ -480,9 +480,9 @@ sctp_getladdrs(int sd, sctp_assoc_t id, struct sockadd
                errno = ENOMEM;
                return (-1);
        }
-       *raddrs = (struct sockaddr *)&addrs->addr[0];
+       *raddrs = &addrs->addr[0].sa;
        cnt = 0;
-       sa = (struct sockaddr *)&addrs->addr[0];
+       sa = &addrs->addr[0].sa;
        lim = (caddr_t)addrs + opt_len;
        while (((caddr_t)sa < lim) && (sa->sa_len > 0)) {
                sa = (struct sockaddr *)((caddr_t)sa + sa->sa_len);
@@ -497,7 +497,7 @@ sctp_freeladdrs(struct sockaddr *addrs)
        void *fr_addr;
 
        /* Take away the hidden association id */
-       fr_addr = (void *)((caddr_t)addrs - sizeof(sctp_assoc_t));
+       fr_addr = (void *)((caddr_t)addrs - offsetof(struct sctp_getaddresses, 
addr));
        /* Now free it */
        free(fr_addr);
 }

Modified: head/sys/netinet/sctp_uio.h
==============================================================================
--- head/sys/netinet/sctp_uio.h Sun Jun 21 22:09:30 2020        (r362472)
+++ head/sys/netinet/sctp_uio.h Sun Jun 21 23:12:56 2020        (r362473)
@@ -39,7 +39,7 @@ __FBSDID("$FreeBSD$");
 #define _NETINET_SCTP_UIO_H_
 
 
-#if ! defined(_KERNEL)
+#if !defined(_KERNEL)
 #include <stdint.h>
 #endif
 #include <sys/types.h>
@@ -633,10 +633,15 @@ struct sctp_setpeerprim {
        uint8_t sspp_padding[4];
 };
 
+union sctp_sockstore {
+       struct sockaddr_in sin;
+       struct sockaddr_in6 sin6;
+       struct sockaddr sa;
+};
+
 struct sctp_getaddresses {
        sctp_assoc_t sget_assoc_id;
-       /* addr is filled in for N * sockaddr_storage */
-       struct sockaddr addr[1];
+       union sctp_sockstore addr[];
 };
 
 struct sctp_status {
@@ -1142,12 +1147,6 @@ struct sctpstat {
 #define SCTP_STAT_DECR_COUNTER32(_x) SCTP_STAT_DECR(_x)
 #define SCTP_STAT_DECR_COUNTER64(_x) SCTP_STAT_DECR(_x)
 #define SCTP_STAT_DECR_GAUGE32(_x) SCTP_STAT_DECR(_x)
-
-union sctp_sockstore {
-       struct sockaddr_in sin;
-       struct sockaddr_in6 sin6;
-       struct sockaddr sa;
-};
 
 
 /***********************************/

Modified: head/sys/netinet/sctp_usrreq.c
==============================================================================
--- head/sys/netinet/sctp_usrreq.c      Sun Jun 21 22:09:30 2020        
(r362472)
+++ head/sys/netinet/sctp_usrreq.c      Sun Jun 21 23:12:56 2020        
(r362473)
@@ -989,7 +989,7 @@ sctp_shutdown(struct socket *so)
  * returns 0 on success, 1 on error
  */
 static uint32_t
-sctp_fill_user_address(struct sockaddr_storage *ss, struct sockaddr *sa)
+sctp_fill_user_address(union sctp_sockstore *ss, struct sockaddr *sa)
 {
 #ifdef INET6
        struct sockaddr_in6 lsa6;
@@ -1010,7 +1010,7 @@ static size_t
 sctp_fill_up_addresses_vrf(struct sctp_inpcb *inp,
     struct sctp_tcb *stcb,
     size_t limit,
-    struct sockaddr_storage *sas,
+    union sctp_sockstore *addr,
     uint32_t vrf_id)
 {
        struct sctp_ifn *sctp_ifn;
@@ -1125,18 +1125,18 @@ sctp_fill_up_addresses_vrf(struct sctp_inpcb *inp,
                                                        if (actual + 
sizeof(struct sockaddr_in6) > limit) {
                                                                return (actual);
                                                        }
-                                                       
in6_sin_2_v4mapsin6(sin, (struct sockaddr_in6 *)sas);
-                                                       ((struct sockaddr_in6 
*)sas)->sin6_port = inp->sctp_lport;
-                                                       sas = (struct 
sockaddr_storage *)((caddr_t)sas + sizeof(struct sockaddr_in6));
+                                                       
in6_sin_2_v4mapsin6(sin, &addr->sin6);
+                                                       addr->sin6.sin6_port = 
inp->sctp_lport;
+                                                       addr = (union 
sctp_sockstore *)((caddr_t)addr + sizeof(struct sockaddr_in6));
                                                        actual += sizeof(struct 
sockaddr_in6);
                                                } else {
 #endif
                                                        if (actual + 
sizeof(struct sockaddr_in) > limit) {
                                                                return (actual);
                                                        }
-                                                       memcpy(sas, sin, 
sizeof(struct sockaddr_in));
-                                                       ((struct sockaddr_in 
*)sas)->sin_port = inp->sctp_lport;
-                                                       sas = (struct 
sockaddr_storage *)((caddr_t)sas + sizeof(struct sockaddr_in));
+                                                       memcpy(addr, sin, 
sizeof(struct sockaddr_in));
+                                                       addr->sin.sin_port = 
inp->sctp_lport;
+                                                       addr = (union 
sctp_sockstore *)((caddr_t)addr + sizeof(struct sockaddr_in));
                                                        actual += sizeof(struct 
sockaddr_in);
 #ifdef INET6
                                                }
@@ -1188,9 +1188,9 @@ sctp_fill_up_addresses_vrf(struct sctp_inpcb *inp,
                                                if (actual + sizeof(struct 
sockaddr_in6) > limit) {
                                                        return (actual);
                                                }
-                                               memcpy(sas, sin6, sizeof(struct 
sockaddr_in6));
-                                               ((struct sockaddr_in6 
*)sas)->sin6_port = inp->sctp_lport;
-                                               sas = (struct sockaddr_storage 
*)((caddr_t)sas + sizeof(struct sockaddr_in6));
+                                               memcpy(addr, sin6, 
sizeof(struct sockaddr_in6));
+                                               addr->sin6.sin6_port = 
inp->sctp_lport;
+                                               addr = (union sctp_sockstore 
*)((caddr_t)addr + sizeof(struct sockaddr_in6));
                                                actual += sizeof(struct 
sockaddr_in6);
                                        } else {
                                                continue;
@@ -1217,24 +1217,24 @@ sctp_fill_up_addresses_vrf(struct sctp_inpcb *inp,
                        if (actual + sa_len > limit) {
                                return (actual);
                        }
-                       if (sctp_fill_user_address(sas, 
&laddr->ifa->address.sa))
+                       if (sctp_fill_user_address(addr, 
&laddr->ifa->address.sa))
                                continue;
                        switch (laddr->ifa->address.sa.sa_family) {
 #ifdef INET
                        case AF_INET:
-                               ((struct sockaddr_in *)sas)->sin_port = 
inp->sctp_lport;
+                               addr->sin.sin_port = inp->sctp_lport;
                                break;
 #endif
 #ifdef INET6
                        case AF_INET6:
-                               ((struct sockaddr_in6 *)sas)->sin6_port = 
inp->sctp_lport;
+                               addr->sin6.sin6_port = inp->sctp_lport;
                                break;
 #endif
                        default:
                                /* TSNH */
                                break;
                        }
-                       sas = (struct sockaddr_storage *)((caddr_t)sas + 
sa_len);
+                       addr = (union sctp_sockstore *)((caddr_t)addr + sa_len);
                        actual += sa_len;
                }
        }
@@ -1245,13 +1245,13 @@ static size_t
 sctp_fill_up_addresses(struct sctp_inpcb *inp,
     struct sctp_tcb *stcb,
     size_t limit,
-    struct sockaddr_storage *sas)
+    union sctp_sockstore *addr)
 {
        size_t size = 0;
 
        SCTP_IPI_ADDR_RLOCK();
        /* fill up addresses for the endpoint's default vrf */
-       size = sctp_fill_up_addresses_vrf(inp, stcb, limit, sas,
+       size = sctp_fill_up_addresses_vrf(inp, stcb, limit, addr,
            inp->def_vrf_id);
        SCTP_IPI_ADDR_RUNLOCK();
        return (size);
@@ -2226,7 +2226,7 @@ flags_out:
                 */
                {
                        size_t cpsz, left;
-                       struct sockaddr_storage *sas;
+                       union sctp_sockstore *addr;
                        struct sctp_nets *net;
                        struct sctp_getaddresses *saddr;
 
@@ -2234,9 +2234,9 @@ flags_out:
                        SCTP_FIND_STCB(inp, stcb, saddr->sget_assoc_id);
 
                        if (stcb) {
-                               left = (*optsize) - sizeof(sctp_assoc_t);
-                               *optsize = sizeof(sctp_assoc_t);
-                               sas = (struct sockaddr_storage 
*)&saddr->addr[0];
+                               left = *optsize - offsetof(struct 
sctp_getaddresses, addr);
+                               *optsize = offsetof(struct sctp_getaddresses, 
addr);
+                               addr = &saddr->addr[0];
 
                                TAILQ_FOREACH(net, &stcb->asoc.nets, sctp_next) 
{
                                        switch (net->ro._l_addr.sa.sa_family) {
@@ -2274,16 +2274,16 @@ flags_out:
                                            (net->ro._l_addr.sa.sa_family == 
AF_INET)) {
                                                /* Must map the address */
                                                
in6_sin_2_v4mapsin6(&net->ro._l_addr.sin,
-                                                   (struct sockaddr_in6 *)sas);
+                                                   &addr->sin6);
                                        } else {
-                                               memcpy(sas, &net->ro._l_addr, 
cpsz);
+                                               memcpy(addr, &net->ro._l_addr, 
cpsz);
                                        }
 #else
-                                       memcpy(sas, &net->ro._l_addr, cpsz);
+                                       memcpy(addr, &net->ro._l_addr, cpsz);
 #endif
-                                       ((struct sockaddr_in *)sas)->sin_port = 
stcb->rport;
+                                       addr->sin.sin_port = stcb->rport;
 
-                                       sas = (struct sockaddr_storage 
*)((caddr_t)sas + cpsz);
+                                       addr = (union sctp_sockstore 
*)((caddr_t)addr + cpsz);
                                        left -= cpsz;
                                        *optsize += cpsz;
                                }
@@ -2297,19 +2297,17 @@ flags_out:
        case SCTP_GET_LOCAL_ADDRESSES:
                {
                        size_t limit, actual;
-                       struct sockaddr_storage *sas;
                        struct sctp_getaddresses *saddr;
 
                        SCTP_CHECK_AND_CAST(saddr, optval, struct 
sctp_getaddresses, *optsize);
                        SCTP_FIND_STCB(inp, stcb, saddr->sget_assoc_id);
 
-                       sas = (struct sockaddr_storage *)&saddr->addr[0];
-                       limit = *optsize - sizeof(sctp_assoc_t);
-                       actual = sctp_fill_up_addresses(inp, stcb, limit, sas);
+                       limit = *optsize - offsetof(struct sctp_getaddresses, 
addr);
+                       actual = sctp_fill_up_addresses(inp, stcb, limit, 
saddr->addr);
                        if (stcb) {
                                SCTP_TCB_UNLOCK(stcb);
                        }
-                       *optsize = sizeof(sctp_assoc_t) + actual;
+                       *optsize = offsetof(struct sctp_getaddresses, addr) + 
actual;
                        break;
                }
        case SCTP_PEER_ADDR_PARAMS:
_______________________________________________
svn-src-head@freebsd.org mailing list
https://lists.freebsd.org/mailman/listinfo/svn-src-head
To unsubscribe, send any mail to "svn-src-head-unsubscr...@freebsd.org"

Reply via email to