When a client uses UDP encapsulation and lists IP addresses in the INIT
chunk, enable UDP encapsulation for all those addresses. This helps clients using a userland stack to support multihoming if they are not behind a NAT. MFC after: 1 week
This commit is contained in:
parent
71a53e69d6
commit
ec70917ffa
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=298902
@ -465,7 +465,7 @@ sctp_process_init_ack(struct mbuf *m, int iphlen, int offset,
|
||||
/* load all addresses */
|
||||
if ((retval = sctp_load_addresses_from_init(stcb, m,
|
||||
(offset + sizeof(struct sctp_init_chunk)), initack_limit,
|
||||
src, dst, NULL))) {
|
||||
src, dst, NULL, stcb->asoc.port))) {
|
||||
op_err = sctp_generate_cause(SCTP_BASE_SYSCTL(sctp_diag_info_code),
|
||||
"Problem with address parameters");
|
||||
SCTPDBG(SCTP_DEBUG_INPUT1,
|
||||
@ -1672,7 +1672,7 @@ sctp_process_cookie_existing(struct mbuf *m, int iphlen, int offset,
|
||||
*/
|
||||
if (sctp_load_addresses_from_init(stcb, m,
|
||||
init_offset + sizeof(struct sctp_init_chunk),
|
||||
initack_offset, src, dst, init_src)) {
|
||||
initack_offset, src, dst, init_src, stcb->asoc.port)) {
|
||||
if (how_indx < sizeof(asoc->cookie_how))
|
||||
asoc->cookie_how[how_indx] = 4;
|
||||
return (NULL);
|
||||
@ -1799,7 +1799,7 @@ sctp_process_cookie_existing(struct mbuf *m, int iphlen, int offset,
|
||||
}
|
||||
if (sctp_load_addresses_from_init(stcb, m,
|
||||
init_offset + sizeof(struct sctp_init_chunk),
|
||||
initack_offset, src, dst, init_src)) {
|
||||
initack_offset, src, dst, init_src, stcb->asoc.port)) {
|
||||
if (how_indx < sizeof(asoc->cookie_how))
|
||||
asoc->cookie_how[how_indx] = 10;
|
||||
return (NULL);
|
||||
@ -2011,7 +2011,7 @@ sctp_process_cookie_existing(struct mbuf *m, int iphlen, int offset,
|
||||
|
||||
if (sctp_load_addresses_from_init(stcb, m,
|
||||
init_offset + sizeof(struct sctp_init_chunk),
|
||||
initack_offset, src, dst, init_src)) {
|
||||
initack_offset, src, dst, init_src, stcb->asoc.port)) {
|
||||
if (how_indx < sizeof(asoc->cookie_how))
|
||||
asoc->cookie_how[how_indx] = 14;
|
||||
|
||||
@ -2123,6 +2123,7 @@ sctp_process_cookie_new(struct mbuf *m, int iphlen, int offset,
|
||||
stcb = sctp_aloc_assoc(inp, init_src, &error,
|
||||
ntohl(initack_cp->init.initiate_tag), vrf_id,
|
||||
ntohs(initack_cp->init.num_outbound_streams),
|
||||
port,
|
||||
(struct thread *)NULL
|
||||
);
|
||||
if (stcb == NULL) {
|
||||
@ -2212,7 +2213,7 @@ sctp_process_cookie_new(struct mbuf *m, int iphlen, int offset,
|
||||
/* load all addresses */
|
||||
if (sctp_load_addresses_from_init(stcb, m,
|
||||
init_offset + sizeof(struct sctp_init_chunk), initack_offset,
|
||||
src, dst, init_src)) {
|
||||
src, dst, init_src, port)) {
|
||||
atomic_add_int(&stcb->asoc.refcnt, 1);
|
||||
#if defined(__APPLE__) || defined(SCTP_SO_LOCK_TESTING)
|
||||
SCTP_TCB_UNLOCK(stcb);
|
||||
@ -2371,12 +2372,6 @@ sctp_process_cookie_new(struct mbuf *m, int iphlen, int offset,
|
||||
(*netp)->RTO = sctp_calculate_rto(stcb, asoc, *netp,
|
||||
&cookie->time_entered, sctp_align_unsafe_makecopy,
|
||||
SCTP_RTT_FROM_NON_DATA);
|
||||
#if defined(INET) || defined(INET6)
|
||||
if (((*netp)->port == 0) && (port != 0)) {
|
||||
sctp_pathmtu_adjustment(stcb, (uint16_t) ((*netp)->mtu - sizeof(struct udphdr)));
|
||||
}
|
||||
(*netp)->port = port;
|
||||
#endif
|
||||
}
|
||||
/* respond with a COOKIE-ACK */
|
||||
sctp_send_cookie_ack(stcb);
|
||||
@ -2718,7 +2713,7 @@ sctp_handle_cookie_echo(struct mbuf *m, int iphlen, int offset,
|
||||
*/
|
||||
if (netl == NULL) {
|
||||
/* TSNH! Huh, why do I need to add this address here? */
|
||||
if (sctp_add_remote_addr(*stcb, to, NULL, (*stcb)->asoc.port,
|
||||
if (sctp_add_remote_addr(*stcb, to, NULL, port,
|
||||
SCTP_DONOT_SETSCOPE, SCTP_IN_COOKIE_PROC)) {
|
||||
return (NULL);
|
||||
}
|
||||
|
@ -12765,8 +12765,8 @@ sctp_lower_sosend(struct socket *so,
|
||||
#endif
|
||||
stcb = sctp_aloc_assoc(inp, addr, &error, 0, vrf_id,
|
||||
inp->sctp_ep.pre_open_stream_count,
|
||||
p
|
||||
);
|
||||
inp->sctp_ep.port,
|
||||
p);
|
||||
if (stcb == NULL) {
|
||||
/* Error is setup for us in the call */
|
||||
goto out_unlocked;
|
||||
|
@ -4045,7 +4045,7 @@ sctp_add_remote_addr(struct sctp_tcb *stcb, struct sockaddr *newaddr,
|
||||
stcb->asoc.smallest_mtu = net->mtu;
|
||||
}
|
||||
if (stcb->asoc.smallest_mtu > net->mtu) {
|
||||
stcb->asoc.smallest_mtu = net->mtu;
|
||||
sctp_pathmtu_adjustment(stcb, net->mtu);
|
||||
}
|
||||
#ifdef INET6
|
||||
if (newaddr->sa_family == AF_INET6) {
|
||||
@ -4191,7 +4191,7 @@ sctp_aloc_a_assoc_id(struct sctp_inpcb *inp, struct sctp_tcb *stcb)
|
||||
struct sctp_tcb *
|
||||
sctp_aloc_assoc(struct sctp_inpcb *inp, struct sockaddr *firstaddr,
|
||||
int *error, uint32_t override_tag, uint32_t vrf_id,
|
||||
uint16_t o_streams,
|
||||
uint16_t o_streams, uint16_t port,
|
||||
struct thread *p
|
||||
)
|
||||
{
|
||||
@ -4384,7 +4384,7 @@ sctp_aloc_assoc(struct sctp_inpcb *inp, struct sockaddr *firstaddr,
|
||||
LIST_INSERT_HEAD(head, stcb, sctp_asocs);
|
||||
SCTP_INP_INFO_WUNLOCK();
|
||||
|
||||
if ((err = sctp_add_remote_addr(stcb, firstaddr, NULL, asoc->port, SCTP_DO_SETSCOPE, SCTP_ALLOC_ASOC))) {
|
||||
if ((err = sctp_add_remote_addr(stcb, firstaddr, NULL, port, SCTP_DO_SETSCOPE, SCTP_ALLOC_ASOC))) {
|
||||
/* failure.. memory error? */
|
||||
if (asoc->strmout) {
|
||||
SCTP_FREE(asoc->strmout, SCTP_M_STRMO);
|
||||
@ -6068,7 +6068,7 @@ int
|
||||
sctp_load_addresses_from_init(struct sctp_tcb *stcb, struct mbuf *m,
|
||||
int offset, int limit,
|
||||
struct sockaddr *src, struct sockaddr *dst,
|
||||
struct sockaddr *altsa)
|
||||
struct sockaddr *altsa, uint16_t port)
|
||||
{
|
||||
/*
|
||||
* grub through the INIT pulling addresses and loading them to the
|
||||
@ -6159,7 +6159,7 @@ sctp_load_addresses_from_init(struct sctp_tcb *stcb, struct mbuf *m,
|
||||
#ifdef INET
|
||||
case AF_INET:
|
||||
if (stcb->asoc.scope.ipv4_addr_legal) {
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, stcb->asoc.port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_2)) {
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_2)) {
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
@ -6168,7 +6168,7 @@ sctp_load_addresses_from_init(struct sctp_tcb *stcb, struct mbuf *m,
|
||||
#ifdef INET6
|
||||
case AF_INET6:
|
||||
if (stcb->asoc.scope.ipv6_addr_legal) {
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, stcb->asoc.port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_3)) {
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_3)) {
|
||||
return (-2);
|
||||
}
|
||||
}
|
||||
@ -6253,7 +6253,7 @@ sctp_load_addresses_from_init(struct sctp_tcb *stcb, struct mbuf *m,
|
||||
/* the assoc was freed? */
|
||||
return (-7);
|
||||
}
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, stcb->asoc.port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_4)) {
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_4)) {
|
||||
return (-8);
|
||||
}
|
||||
} else if (stcb_tmp == stcb) {
|
||||
@ -6348,7 +6348,7 @@ sctp_load_addresses_from_init(struct sctp_tcb *stcb, struct mbuf *m,
|
||||
* we must add the address, no scope
|
||||
* set
|
||||
*/
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, stcb->asoc.port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_5)) {
|
||||
if (sctp_add_remote_addr(stcb, sa, NULL, port, SCTP_DONOT_SETSCOPE, SCTP_LOAD_ADDR_5)) {
|
||||
return (-17);
|
||||
}
|
||||
} else if (stcb_tmp == stcb) {
|
||||
|
@ -585,7 +585,7 @@ void sctp_inpcb_free(struct sctp_inpcb *, int, int);
|
||||
|
||||
struct sctp_tcb *
|
||||
sctp_aloc_assoc(struct sctp_inpcb *, struct sockaddr *,
|
||||
int *, uint32_t, uint32_t, uint16_t, struct thread *);
|
||||
int *, uint32_t, uint32_t, uint16_t, uint16_t, struct thread *);
|
||||
|
||||
int sctp_free_assoc(struct sctp_inpcb *, struct sctp_tcb *, int, int);
|
||||
|
||||
@ -616,7 +616,7 @@ void sctp_del_local_addr_restricted(struct sctp_tcb *, struct sctp_ifa *);
|
||||
|
||||
int
|
||||
sctp_load_addresses_from_init(struct sctp_tcb *, struct mbuf *, int, int,
|
||||
struct sockaddr *, struct sockaddr *, struct sockaddr *);
|
||||
struct sockaddr *, struct sockaddr *, struct sockaddr *, uint16_t);
|
||||
|
||||
int
|
||||
sctp_set_primary_addr(struct sctp_tcb *, struct sockaddr *,
|
||||
|
@ -1474,6 +1474,7 @@ sctp_do_connect_x(struct socket *so, struct sctp_inpcb *inp, void *optval,
|
||||
/* We are GOOD to go */
|
||||
stcb = sctp_aloc_assoc(inp, sa, &error, 0, vrf_id,
|
||||
inp->sctp_ep.pre_open_stream_count,
|
||||
inp->sctp_ep.port,
|
||||
(struct thread *)p
|
||||
);
|
||||
if (stcb == NULL) {
|
||||
@ -6999,7 +7000,9 @@ sctp_connect(struct socket *so, struct sockaddr *addr, struct thread *p)
|
||||
}
|
||||
vrf_id = inp->def_vrf_id;
|
||||
/* We are GOOD to go */
|
||||
stcb = sctp_aloc_assoc(inp, addr, &error, 0, vrf_id, inp->sctp_ep.pre_open_stream_count, p);
|
||||
stcb = sctp_aloc_assoc(inp, addr, &error, 0, vrf_id,
|
||||
inp->sctp_ep.pre_open_stream_count,
|
||||
inp->sctp_ep.port, p);
|
||||
if (stcb == NULL) {
|
||||
/* Gak! no memory */
|
||||
goto out_now;
|
||||
|
@ -919,7 +919,9 @@ sctp6_connect(struct socket *so, struct sockaddr *addr, struct thread *p)
|
||||
return (EALREADY);
|
||||
}
|
||||
/* We are GOOD to go */
|
||||
stcb = sctp_aloc_assoc(inp, addr, &error, 0, vrf_id, inp->sctp_ep.pre_open_stream_count, p);
|
||||
stcb = sctp_aloc_assoc(inp, addr, &error, 0, vrf_id,
|
||||
inp->sctp_ep.pre_open_stream_count,
|
||||
inp->sctp_ep.port, p);
|
||||
SCTP_ASOC_CREATE_UNLOCK(inp);
|
||||
if (stcb == NULL) {
|
||||
/* Gak! no memory */
|
||||
|
Loading…
Reference in New Issue
Block a user