Cleanup the adding and deleting of addresses via sctp_bindx().
There is no need to use the association identifier, so remove it. While there, cleanup the code a bit. MFC after: 1 week
This commit is contained in:
parent
a74534b121
commit
7621bd5ead
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=362448
@ -6032,9 +6032,7 @@ sctp_setopt(struct socket *so, int optname, void *optval, size_t optsize,
|
|||||||
error = EAFNOSUPPORT;
|
error = EAFNOSUPPORT;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
sctp_bindx_add_address(so, inp, addrs->addr,
|
sctp_bindx_add_address(so, inp, addrs->addr, vrf_id, &error, p);
|
||||||
addrs->sget_assoc_id, vrf_id,
|
|
||||||
&error, p);
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case SCTP_BINDX_REM_ADDR:
|
case SCTP_BINDX_REM_ADDR:
|
||||||
@ -6078,9 +6076,7 @@ sctp_setopt(struct socket *so, int optname, void *optval, size_t optsize,
|
|||||||
error = EAFNOSUPPORT;
|
error = EAFNOSUPPORT;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
sctp_bindx_delete_address(inp, addrs->addr,
|
sctp_bindx_delete_address(inp, addrs->addr, vrf_id, &error);
|
||||||
addrs->sget_assoc_id, vrf_id,
|
|
||||||
&error);
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case SCTP_EVENT:
|
case SCTP_EVENT:
|
||||||
|
@ -6694,13 +6694,21 @@ sctp_connectx_helper_find(struct sctp_inpcb *inp, struct sockaddr *addr,
|
|||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
||||||
struct sockaddr *sa, sctp_assoc_t assoc_id,
|
struct sockaddr *sa, uint32_t vrf_id, int *error,
|
||||||
uint32_t vrf_id, int *error, void *p)
|
void *p)
|
||||||
{
|
{
|
||||||
struct sockaddr *addr_touse;
|
|
||||||
#if defined(INET) && defined(INET6)
|
#if defined(INET) && defined(INET6)
|
||||||
struct sockaddr_in sin;
|
struct sockaddr_in sin;
|
||||||
#endif
|
#endif
|
||||||
|
#ifdef INET6
|
||||||
|
struct sockaddr_in6 *sin6;
|
||||||
|
#endif
|
||||||
|
#ifdef INET
|
||||||
|
struct sockaddr_in *sinp;
|
||||||
|
#endif
|
||||||
|
struct sockaddr *addr_to_use;
|
||||||
|
struct sctp_inpcb *lep;
|
||||||
|
uint16_t port;
|
||||||
|
|
||||||
/* see if we're bound all already! */
|
/* see if we're bound all already! */
|
||||||
if (inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) {
|
if (inp->sctp_flags & SCTP_PCB_FLAGS_BOUNDALL) {
|
||||||
@ -6708,13 +6716,9 @@ sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
|||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
addr_touse = sa;
|
switch (sa->sa_family) {
|
||||||
#ifdef INET6
|
#ifdef INET6
|
||||||
if (sa->sa_family == AF_INET6) {
|
case AF_INET6:
|
||||||
#ifdef INET
|
|
||||||
struct sockaddr_in6 *sin6;
|
|
||||||
|
|
||||||
#endif
|
|
||||||
if (sa->sa_len != sizeof(struct sockaddr_in6)) {
|
if (sa->sa_len != sizeof(struct sockaddr_in6)) {
|
||||||
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
@ -6726,8 +6730,9 @@ sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
|||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
sin6 = (struct sockaddr_in6 *)sa;
|
||||||
|
port = sin6->sin6_port;
|
||||||
#ifdef INET
|
#ifdef INET
|
||||||
sin6 = (struct sockaddr_in6 *)addr_touse;
|
|
||||||
if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) {
|
if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) {
|
||||||
if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
|
if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
|
||||||
SCTP_IPV6_V6ONLY(inp)) {
|
SCTP_IPV6_V6ONLY(inp)) {
|
||||||
@ -6737,13 +6742,15 @@ sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
in6_sin6_2_sin(&sin, sin6);
|
in6_sin6_2_sin(&sin, sin6);
|
||||||
addr_touse = (struct sockaddr *)&sin;
|
addr_to_use = (struct sockaddr *)&sin;
|
||||||
|
} else {
|
||||||
|
addr_to_use = sa;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
break;
|
||||||
#endif
|
#endif
|
||||||
#ifdef INET
|
#ifdef INET
|
||||||
if (sa->sa_family == AF_INET) {
|
case AF_INET:
|
||||||
if (sa->sa_len != sizeof(struct sockaddr_in)) {
|
if (sa->sa_len != sizeof(struct sockaddr_in)) {
|
||||||
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
@ -6756,8 +6763,16 @@ sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
|||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
sinp = (struct sockaddr_in *)sa;
|
||||||
|
port = sinp->sin_port;
|
||||||
|
addr_to_use = sa;
|
||||||
|
break;
|
||||||
#endif
|
#endif
|
||||||
|
default:
|
||||||
|
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
||||||
|
*error = EINVAL;
|
||||||
|
return;
|
||||||
|
}
|
||||||
if (inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) {
|
if (inp->sctp_flags & SCTP_PCB_FLAGS_UNBOUND) {
|
||||||
if (p == NULL) {
|
if (p == NULL) {
|
||||||
/* Can't get proc for Net/Open BSD */
|
/* Can't get proc for Net/Open BSD */
|
||||||
@ -6765,55 +6780,25 @@ sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
|||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
*error = sctp_inpcb_bind(so, addr_touse, NULL, p);
|
*error = sctp_inpcb_bind(so, addr_to_use, NULL, p);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
/*
|
/* Validate the incoming port. */
|
||||||
* No locks required here since bind and mgmt_ep_sa all do their own
|
if ((port != 0) && (port != inp->sctp_lport)) {
|
||||||
* locking. If we do something for the FIX: below we may need to
|
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
||||||
* lock in that case.
|
*error = EINVAL;
|
||||||
*/
|
return;
|
||||||
if (assoc_id == 0) {
|
}
|
||||||
|
lep = sctp_pcb_findep(addr_to_use, 1, 0, vrf_id);
|
||||||
|
if (lep == NULL) {
|
||||||
/* add the address */
|
/* add the address */
|
||||||
struct sctp_inpcb *lep;
|
*error = sctp_addr_mgmt_ep_sa(inp, addr_to_use,
|
||||||
struct sockaddr_in *lsin = (struct sockaddr_in *)addr_touse;
|
SCTP_ADD_IP_ADDRESS, vrf_id);
|
||||||
|
} else {
|
||||||
/* validate the incoming port */
|
if (lep != inp) {
|
||||||
if ((lsin->sin_port != 0) &&
|
|
||||||
(lsin->sin_port != inp->sctp_lport)) {
|
|
||||||
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
|
||||||
*error = EINVAL;
|
|
||||||
return;
|
|
||||||
} else {
|
|
||||||
/* user specified 0 port, set it to existing port */
|
|
||||||
lsin->sin_port = inp->sctp_lport;
|
|
||||||
}
|
|
||||||
|
|
||||||
lep = sctp_pcb_findep(addr_touse, 1, 0, vrf_id);
|
|
||||||
if (lep != NULL) {
|
|
||||||
/*
|
|
||||||
* We must decrement the refcount since we have the
|
|
||||||
* ep already and are binding. No remove going on
|
|
||||||
* here.
|
|
||||||
*/
|
|
||||||
SCTP_INP_DECR_REF(lep);
|
|
||||||
}
|
|
||||||
if (lep == inp) {
|
|
||||||
/* already bound to it.. ok */
|
|
||||||
return;
|
|
||||||
} else if (lep == NULL) {
|
|
||||||
((struct sockaddr_in *)addr_touse)->sin_port = 0;
|
|
||||||
*error = sctp_addr_mgmt_ep_sa(inp, addr_touse,
|
|
||||||
SCTP_ADD_IP_ADDRESS, vrf_id);
|
|
||||||
} else {
|
|
||||||
*error = EADDRINUSE;
|
*error = EADDRINUSE;
|
||||||
}
|
}
|
||||||
if (*error)
|
SCTP_INP_DECR_REF(lep);
|
||||||
return;
|
|
||||||
} else {
|
|
||||||
/*
|
|
||||||
* FIX: decide whether we allow assoc based bindx
|
|
||||||
*/
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -6823,11 +6808,11 @@ sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
|||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
sctp_bindx_delete_address(struct sctp_inpcb *inp,
|
sctp_bindx_delete_address(struct sctp_inpcb *inp,
|
||||||
struct sockaddr *sa, sctp_assoc_t assoc_id,
|
struct sockaddr *sa, uint32_t vrf_id, int *error)
|
||||||
uint32_t vrf_id, int *error)
|
|
||||||
{
|
{
|
||||||
struct sockaddr *addr_touse;
|
struct sockaddr *addr_to_use;
|
||||||
#if defined(INET) && defined(INET6)
|
#if defined(INET) && defined(INET6)
|
||||||
|
struct sockaddr_in6 *sin6;
|
||||||
struct sockaddr_in sin;
|
struct sockaddr_in sin;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -6837,13 +6822,9 @@ sctp_bindx_delete_address(struct sctp_inpcb *inp,
|
|||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
addr_touse = sa;
|
switch (sa->sa_family) {
|
||||||
#ifdef INET6
|
#ifdef INET6
|
||||||
if (sa->sa_family == AF_INET6) {
|
case AF_INET6:
|
||||||
#ifdef INET
|
|
||||||
struct sockaddr_in6 *sin6;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if (sa->sa_len != sizeof(struct sockaddr_in6)) {
|
if (sa->sa_len != sizeof(struct sockaddr_in6)) {
|
||||||
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
@ -6856,7 +6837,7 @@ sctp_bindx_delete_address(struct sctp_inpcb *inp,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
#ifdef INET
|
#ifdef INET
|
||||||
sin6 = (struct sockaddr_in6 *)addr_touse;
|
sin6 = (struct sockaddr_in6 *)sa;
|
||||||
if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) {
|
if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) {
|
||||||
if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
|
if ((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) &&
|
||||||
SCTP_IPV6_V6ONLY(inp)) {
|
SCTP_IPV6_V6ONLY(inp)) {
|
||||||
@ -6866,13 +6847,15 @@ sctp_bindx_delete_address(struct sctp_inpcb *inp,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
in6_sin6_2_sin(&sin, sin6);
|
in6_sin6_2_sin(&sin, sin6);
|
||||||
addr_touse = (struct sockaddr *)&sin;
|
addr_to_use = (struct sockaddr *)&sin;
|
||||||
|
} else {
|
||||||
|
addr_to_use = sa;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
break;
|
||||||
#endif
|
#endif
|
||||||
#ifdef INET
|
#ifdef INET
|
||||||
if (sa->sa_family == AF_INET) {
|
case AF_INET:
|
||||||
if (sa->sa_len != sizeof(struct sockaddr_in)) {
|
if (sa->sa_len != sizeof(struct sockaddr_in)) {
|
||||||
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
@ -6885,22 +6868,17 @@ sctp_bindx_delete_address(struct sctp_inpcb *inp,
|
|||||||
*error = EINVAL;
|
*error = EINVAL;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
addr_to_use = sa;
|
||||||
|
break;
|
||||||
#endif
|
#endif
|
||||||
/*
|
default:
|
||||||
* No lock required mgmt_ep_sa does its own locking. If the FIX:
|
SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTPUTIL, EINVAL);
|
||||||
* below is ever changed we may need to lock before calling
|
*error = EINVAL;
|
||||||
* association level binding.
|
return;
|
||||||
*/
|
|
||||||
if (assoc_id == 0) {
|
|
||||||
/* delete the address */
|
|
||||||
*error = sctp_addr_mgmt_ep_sa(inp, addr_touse,
|
|
||||||
SCTP_DEL_IP_ADDRESS, vrf_id);
|
|
||||||
} else {
|
|
||||||
/*
|
|
||||||
* FIX: decide whether we allow assoc based bindx
|
|
||||||
*/
|
|
||||||
}
|
}
|
||||||
|
/* No lock required mgmt_ep_sa does its own locking. */
|
||||||
|
*error = sctp_addr_mgmt_ep_sa(inp, addr_to_use, SCTP_DEL_IP_ADDRESS,
|
||||||
|
vrf_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -229,11 +229,10 @@ struct mbuf *sctp_generate_no_user_data_cause(uint32_t);
|
|||||||
|
|
||||||
void
|
void
|
||||||
sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
sctp_bindx_add_address(struct socket *so, struct sctp_inpcb *inp,
|
||||||
struct sockaddr *sa, sctp_assoc_t assoc_id,
|
struct sockaddr *sa, uint32_t vrf_id, int *error,
|
||||||
uint32_t vrf_id, int *error, void *p);
|
void *p);
|
||||||
void
|
void
|
||||||
sctp_bindx_delete_address(struct sctp_inpcb *inp,
|
sctp_bindx_delete_address(struct sctp_inpcb *inp, struct sockaddr *sa,
|
||||||
struct sockaddr *sa, sctp_assoc_t assoc_id,
|
|
||||||
uint32_t vrf_id, int *error);
|
uint32_t vrf_id, int *error);
|
||||||
|
|
||||||
int sctp_local_addr_count(struct sctp_tcb *stcb);
|
int sctp_local_addr_count(struct sctp_tcb *stcb);
|
||||||
|
Loading…
Reference in New Issue
Block a user