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.
This commit is contained in:
parent
e387af1fa8
commit
c5d9e5c99e
@ -406,7 +406,7 @@ sctp_getpaddrs(int sd, sctp_assoc_t id, struct sockaddr **raddrs)
|
||||
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 sockaddr **raddrs)
|
||||
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 sockaddr **raddrs)
|
||||
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 sockaddr **raddrs)
|
||||
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);
|
||||
}
|
||||
|
@ -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 {
|
||||
@ -1143,12 +1148,6 @@ struct sctpstat {
|
||||
#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;
|
||||
};
|
||||
|
||||
|
||||
/***********************************/
|
||||
/* And something for us old timers */
|
||||
|
@ -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:
|
||||
|
Loading…
x
Reference in New Issue
Block a user