diff options
author | tuexen <tuexen@FreeBSD.org> | 2016-08-30 19:27:27 +0000 |
---|---|---|
committer | tuexen <tuexen@FreeBSD.org> | 2016-08-30 19:27:27 +0000 |
commit | dc4f3749dfb352811f4e04a039c632be3226d66f (patch) | |
tree | c1755bcdde52c1051b468b34ca0d54a758b29ec8 /sys/netinet/sctputil.c | |
parent | 116ab41ae85c36ebec9f7202bedf31ce3a90da2a (diff) | |
download | FreeBSD-src-dc4f3749dfb352811f4e04a039c632be3226d66f.zip FreeBSD-src-dc4f3749dfb352811f4e04a039c632be3226d66f.tar.gz |
MFC r304736:
When aborting an association, send the ABORT before notifying the upper
layer. For the kernel this doesn't matter, for the userland stack, it does.
While there, silence a clang warning when compiling it in userland.
MFC r304837:
Fix a bug, where no SACK is sent when receiving a FORWARD-TSN or
I-FORWARD-TSN chunk before any DATA or I-DATA chunk.
Thanks to Julian Cordes for finding this problem and prividing
packetdrill scripts to reporduce the issue.
Diffstat (limited to 'sys/netinet/sctputil.c')
-rw-r--r-- | sys/netinet/sctputil.c | 16 |
1 files changed, 8 insertions, 8 deletions
diff --git a/sys/netinet/sctputil.c b/sys/netinet/sctputil.c index 4d5d497..6eb9e23 100644 --- a/sys/netinet/sctputil.c +++ b/sys/netinet/sctputil.c @@ -3983,17 +3983,16 @@ sctp_abort_association(struct sctp_inpcb *inp, struct sctp_tcb *stcb, vtag = 0; if (stcb != NULL) { - /* We have a TCB to abort, send notification too */ vtag = stcb->asoc.peer_vtag; - sctp_abort_notification(stcb, 0, 0, NULL, SCTP_SO_NOT_LOCKED); - /* get the assoc vrf id and table id */ vrf_id = stcb->asoc.vrf_id; - stcb->asoc.state |= SCTP_STATE_WAS_ABORTED; } sctp_send_abort(m, iphlen, src, dst, sh, vtag, op_err, mflowtype, mflowid, inp->fibnum, vrf_id, port); if (stcb != NULL) { + /* We have a TCB to abort, send notification too */ + sctp_abort_notification(stcb, 0, 0, NULL, SCTP_SO_NOT_LOCKED); + stcb->asoc.state |= SCTP_STATE_WAS_ABORTED; /* Ok, now lets free it */ #if defined(__APPLE__) || defined(SCTP_SO_LOCK_TESTING) so = SCTP_INP_SO(inp); @@ -4109,10 +4108,6 @@ sctp_abort_an_association(struct sctp_inpcb *inp, struct sctp_tcb *stcb, } else { stcb->asoc.state |= SCTP_STATE_WAS_ABORTED; } - /* notify the ulp */ - if ((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE) == 0) { - sctp_abort_notification(stcb, 0, 0, NULL, so_locked); - } /* notify the peer */ sctp_send_abort_tcb(stcb, op_err, so_locked); SCTP_STAT_INCR_COUNTER32(sctps_aborted); @@ -4120,6 +4115,10 @@ sctp_abort_an_association(struct sctp_inpcb *inp, struct sctp_tcb *stcb, (SCTP_GET_STATE(&stcb->asoc) == SCTP_STATE_SHUTDOWN_RECEIVED)) { SCTP_STAT_DECR_GAUGE32(sctps_currestab); } + /* notify the ulp */ + if ((inp->sctp_flags & SCTP_PCB_FLAGS_SOCKET_GONE) == 0) { + sctp_abort_notification(stcb, 0, 0, NULL, so_locked); + } /* now free the asoc */ #ifdef SCTP_ASOCLOG_OF_TSNS sctp_print_out_track_log(stcb); @@ -6400,6 +6399,7 @@ sctp_connectx_helper_find(struct sctp_inpcb *inp, struct sockaddr *addr, #endif default: *totaddr = i; + incr = 0; /* we are done */ break; } |