summaryrefslogtreecommitdiffstats
path: root/sys/netinet/sctp_usrreq.c
diff options
context:
space:
mode:
authorrrs <rrs@FreeBSD.org>2007-05-08 00:21:05 +0000
committerrrs <rrs@FreeBSD.org>2007-05-08 00:21:05 +0000
commit532412f6c49a9077f90f5cd40b66c87a16efe085 (patch)
tree4db56edaf6063ffdff843e7c1228529525ec2e80 /sys/netinet/sctp_usrreq.c
parentcaa15fdaeb248ba5c8dd136083da6989cacd1979 (diff)
downloadFreeBSD-src-532412f6c49a9077f90f5cd40b66c87a16efe085.zip
FreeBSD-src-532412f6c49a9077f90f5cd40b66c87a16efe085.tar.gz
- More macros for OS compatabilty
- PR-SCTP would ignore FWD-TSN's above a rwnd's worth of TSN's (1 byte msgs).. this left the peer hopelessly out of sync.. or an attacker. So now we abort the assoc. - New IFN hash, also rename hashes to match addr/ifn now that the vrf has multiple. - Do not enable SCTP_PCB_FLAGS_RECVDATAIOEVNT per default as defined in the Socket API ID. - Export MTU information via sysctl. - Vrf's need table id's. This is default for BSD, but may be other things later when BSD fully supports VRFs. - Additional stream reset bug (caught by cisco dev-test). - Additional validations for the address in sending a message (socket api). -------- and ----- - Fix association notifications not to give the active open side false notifications. - Fix so sendfile and SENDALL will work properly (missing flag to say socket sender is done). - Fix Bug that prevented COOKIES from being retransmitted. - Break out connectx into helper sub-models so that iox routines can reuse the helpers. - When an address is added during system init (non-dynamic mode) make sure that the "defer use" flag is not set. ** its compiling on XR now :-D ** Reviewed by: gnn
Diffstat (limited to 'sys/netinet/sctp_usrreq.c')
-rw-r--r--sys/netinet/sctp_usrreq.c92
1 files changed, 28 insertions, 64 deletions
diff --git a/sys/netinet/sctp_usrreq.c b/sys/netinet/sctp_usrreq.c
index c187933..a37da5c 100644
--- a/sys/netinet/sctp_usrreq.c
+++ b/sys/netinet/sctp_usrreq.c
@@ -110,7 +110,10 @@ sctp_pathmtu_adjustment(struct sctp_inpcb *inp,
/* Adjust that too */
stcb->asoc.smallest_mtu = nxtsz;
/* now off to subtract IP_DF flag if needed */
-
+#ifdef SCTP_PRINT_FOR_B_AND_M
+ printf("sctp_pathmtu_adjust called inp:%p stcb:%p net:%p nxtsz:%d\n",
+ inp, stcb, net, nxtsz);
+#endif
TAILQ_FOREACH(chk, &stcb->asoc.send_queue, sctp_next) {
if ((chk->send_size + IP_HDR_SIZE) > nxtsz) {
chk->flags |= CHUNK_FLAGS_FRAGMENT_OK;
@@ -201,6 +204,10 @@ sctp_notify_mbuf(struct sctp_inpcb *inp,
}
/* now what about the ep? */
if (stcb->asoc.smallest_mtu > nxtsz) {
+#ifdef SCTP_PRINT_FOR_B_AND_M
+ printf("notify_mbuf (ICMP) calls sctp_pathmtu_adjust mtu:%d\n",
+ nxtsz);
+#endif
sctp_pathmtu_adjustment(inp, stcb, net, nxtsz);
}
if (tmr_stopped)
@@ -513,10 +520,10 @@ sctp_attach(struct socket *so, int proto, struct thread *p)
#ifdef SCTP_LOG_CLOSING
sctp_log_closing(inp, NULL, 15);
#endif
- SCTP_INP_WUNLOCK(inp);
+ SCTP_INP_WUNLOCK(inp);
sctp_inpcb_free(inp, 1, 0);
} else {
- SCTP_INP_WUNLOCK(inp);
+ SCTP_INP_WUNLOCK(inp);
}
return error;
}
@@ -1234,7 +1241,6 @@ sctp_count_max_addresses(struct sctp_inpcb *inp)
return (cnt);
}
-
static int
sctp_do_connect_x(struct socket *so, struct sctp_inpcb *inp, void *optval,
size_t optsize, void *p, int delay)
@@ -1243,8 +1249,8 @@ sctp_do_connect_x(struct socket *so, struct sctp_inpcb *inp, void *optval,
int creat_lock_on = 0;
struct sctp_tcb *stcb = NULL;
struct sockaddr *sa;
- int num_v6 = 0, num_v4 = 0, *totaddrp, totaddr, i;
- size_t incr, at;
+ int num_v6 = 0, num_v4 = 0, *totaddrp, totaddr;
+ int added = 0;
uint32_t vrf_id;
sctp_assoc_t *a_id;
@@ -1281,43 +1287,15 @@ sctp_do_connect_x(struct socket *so, struct sctp_inpcb *inp, void *optval,
totaddrp = (int *)optval;
totaddr = *totaddrp;
sa = (struct sockaddr *)(totaddrp + 1);
- at = incr = 0;
- /* account and validate addresses */
- for (i = 0; i < totaddr; i++) {
- if (sa->sa_family == AF_INET) {
- num_v4++;
- incr = sizeof(struct sockaddr_in);
- } else if (sa->sa_family == AF_INET6) {
- struct sockaddr_in6 *sin6;
-
- sin6 = (struct sockaddr_in6 *)sa;
- if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) {
- /* Must be non-mapped for connectx */
- error = EINVAL;
- goto out_now;
- }
- num_v6++;
- incr = sizeof(struct sockaddr_in6);
- } else {
- totaddr = i;
- break;
- }
- stcb = sctp_findassociation_ep_addr(&inp, sa, NULL, NULL, NULL);
- if (stcb != NULL) {
- /* Already have or am bring up an association */
- SCTP_ASOC_CREATE_UNLOCK(inp);
- creat_lock_on = 0;
- SCTP_TCB_UNLOCK(stcb);
- error = EALREADY;
- goto out_now;
- }
- if ((at + incr) > optsize) {
- totaddr = i;
- break;
- }
- sa = (struct sockaddr *)((caddr_t)sa + incr);
+ stcb = sctp_connectx_helper_find(inp, sa, &totaddr, &num_v4, &num_v6, &error, (optsize - sizeof(int)));
+ if (stcb != NULL) {
+ /* Already have or am bring up an association */
+ SCTP_ASOC_CREATE_UNLOCK(inp);
+ creat_lock_on = 0;
+ SCTP_TCB_UNLOCK(stcb);
+ error = EALREADY;
+ goto out_now;
}
- sa = (struct sockaddr *)(totaddrp + 1);
#ifdef INET6
if (((inp->sctp_flags & SCTP_PCB_FLAGS_BOUND_V6) == 0) &&
(num_v6 > 0)) {
@@ -1356,33 +1334,14 @@ sctp_do_connect_x(struct socket *so, struct sctp_inpcb *inp, void *optval,
/* Gak! no memory */
goto out_now;
}
+ stcb->asoc.state = SCTP_STATE_COOKIE_WAIT;
/* move to second address */
if (sa->sa_family == AF_INET)
sa = (struct sockaddr *)((caddr_t)sa + sizeof(struct sockaddr_in));
else
sa = (struct sockaddr *)((caddr_t)sa + sizeof(struct sockaddr_in6));
- for (i = 1; i < totaddr; i++) {
- if (sa->sa_family == AF_INET) {
- incr = sizeof(struct sockaddr_in);
- if (sctp_add_remote_addr(stcb, sa, SCTP_DONOT_SETSCOPE, SCTP_ADDR_IS_CONFIRMED)) {
- /* assoc gone no un-lock */
- sctp_free_assoc(inp, stcb, SCTP_NORMAL_PROC, SCTP_FROM_SCTP_USRREQ + SCTP_LOC_7);
- error = ENOBUFS;
- goto out_now;
- }
- } else if (sa->sa_family == AF_INET6) {
- incr = sizeof(struct sockaddr_in6);
- if (sctp_add_remote_addr(stcb, sa, SCTP_DONOT_SETSCOPE, SCTP_ADDR_IS_CONFIRMED)) {
- /* assoc gone no un-lock */
- sctp_free_assoc(inp, stcb, SCTP_NORMAL_PROC, SCTP_FROM_SCTP_USRREQ + SCTP_LOC_8);
- error = ENOBUFS;
- goto out_now;
- }
- }
- sa = (struct sockaddr *)((caddr_t)sa + incr);
- }
- stcb->asoc.state = SCTP_STATE_COOKIE_WAIT;
+ added = sctp_connectx_helper_add(stcb, sa, (totaddr - 1), &error);
/* Fill in the return id */
a_id = (sctp_assoc_t *) optval;
*a_id = sctp_get_associd(stcb);
@@ -3087,8 +3046,13 @@ sctp_setopt(struct socket *so, int optname, void *optval, size_t optsize,
}
if (paddrp->spp_pathmtu > SCTP_DEFAULT_MINSEGMENT) {
net->mtu = paddrp->spp_pathmtu;
- if (net->mtu < stcb->asoc.smallest_mtu)
+ if (net->mtu < stcb->asoc.smallest_mtu) {
+#ifdef SCTP_PRINT_FOR_B_AND_M
+ printf("SCTP_PMTU_DISABLE calls sctp_pathmtu_adjustment:%d\n",
+ net->mtu);
+#endif
sctp_pathmtu_adjustment(inp, stcb, net, net->mtu);
+ }
}
}
if (paddrp->spp_flags & SPP_PMTUD_ENABLE) {
OpenPOWER on IntegriCloud