Date: Sat, 20 Feb 2010 20:30:40 +0000 (UTC) From: Michael Tuexen <tuexen@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r204141 - head/sys/netinet Message-ID: <201002202030.o1KKUekS010349@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: tuexen Date: Sat Feb 20 20:30:40 2010 New Revision: 204141 URL: http://svn.freebsd.org/changeset/base/204141 Log: Fix handling of SHUTDOWN-ACK chunk in COOKIE_WAIT and COOKIE_ECHOED. MFC after: 1 week Modified: head/sys/netinet/sctp_input.c head/sys/netinet/sctp_output.c head/sys/netinet/sctp_output.h Modified: head/sys/netinet/sctp_input.c ============================================================================== --- head/sys/netinet/sctp_input.c Sat Feb 20 19:59:52 2010 (r204140) +++ head/sys/netinet/sctp_input.c Sat Feb 20 20:30:40 2010 (r204141) @@ -918,7 +918,8 @@ sctp_handle_shutdown(struct sctp_shutdow static void sctp_handle_shutdown_ack(struct sctp_shutdown_ack_chunk *cp, - struct sctp_tcb *stcb, struct sctp_nets *net) + struct sctp_tcb *stcb, + struct sctp_nets *net) { struct sctp_association *asoc; @@ -934,6 +935,13 @@ sctp_handle_shutdown_ack(struct sctp_shu asoc = &stcb->asoc; /* process according to association state */ + if ((SCTP_GET_STATE(asoc) == SCTP_STATE_COOKIE_WAIT) || + (SCTP_GET_STATE(asoc) == SCTP_STATE_COOKIE_ECHOED)) { + /* unexpected SHUTDOWN-ACK... do OOTB handling... */ + sctp_send_shutdown_complete(stcb, net, 1); + SCTP_TCB_UNLOCK(stcb); + return; + } if ((SCTP_GET_STATE(asoc) != SCTP_STATE_SHUTDOWN_SENT) && (SCTP_GET_STATE(asoc) != SCTP_STATE_SHUTDOWN_ACK_SENT)) { /* unexpected SHUTDOWN-ACK... so ignore... */ @@ -975,7 +983,7 @@ sctp_handle_shutdown_ack(struct sctp_shu /* stop the timer */ sctp_timer_stop(SCTP_TIMER_TYPE_SHUTDOWN, stcb->sctp_ep, stcb, net, SCTP_FROM_SCTP_INPUT + SCTP_LOC_9); /* send SHUTDOWN-COMPLETE */ - sctp_send_shutdown_complete(stcb, net); + sctp_send_shutdown_complete(stcb, net, 0); /* notify upper layer protocol */ if (stcb->sctp_socket) { sctp_ulp_notify(SCTP_NOTIFY_ASSOC_DOWN, stcb, 0, NULL, SCTP_SO_NOT_LOCKED); Modified: head/sys/netinet/sctp_output.c ============================================================================== --- head/sys/netinet/sctp_output.c Sat Feb 20 19:59:52 2010 (r204140) +++ head/sys/netinet/sctp_output.c Sat Feb 20 20:30:40 2010 (r204141) @@ -10622,27 +10622,37 @@ sctp_send_abort_tcb(struct sctp_tcb *stc void sctp_send_shutdown_complete(struct sctp_tcb *stcb, - struct sctp_nets *net) + struct sctp_nets *net, + int reflect_vtag) { /* formulate and SEND a SHUTDOWN-COMPLETE */ struct mbuf *m_shutdown_comp; struct sctp_shutdown_complete_chunk *shutdown_complete; + uint32_t vtag; + uint8_t flags; m_shutdown_comp = sctp_get_mbuf_for_msg(sizeof(struct sctp_chunkhdr), 0, M_DONTWAIT, 1, MT_HEADER); if (m_shutdown_comp == NULL) { /* no mbuf's */ return; } + if (reflect_vtag) { + flags = SCTP_HAD_NO_TCB; + vtag = stcb->asoc.my_vtag; + } else { + flags = 0; + vtag = stcb->asoc.peer_vtag; + } shutdown_complete = mtod(m_shutdown_comp, struct sctp_shutdown_complete_chunk *); shutdown_complete->ch.chunk_type = SCTP_SHUTDOWN_COMPLETE; - shutdown_complete->ch.chunk_flags = 0; + shutdown_complete->ch.chunk_flags = flags; shutdown_complete->ch.chunk_length = htons(sizeof(struct sctp_shutdown_complete_chunk)); SCTP_BUF_LEN(m_shutdown_comp) = sizeof(struct sctp_shutdown_complete_chunk); (void)sctp_lowlevel_chunk_output(stcb->sctp_ep, stcb, net, (struct sockaddr *)&net->ro._l_addr, m_shutdown_comp, 0, NULL, 0, 1, 0, NULL, 0, stcb->sctp_ep->sctp_lport, stcb->rport, - htonl(stcb->asoc.peer_vtag), + htonl(vtag), net->port, SCTP_SO_NOT_LOCKED, NULL); SCTP_STAT_INCR_COUNTER64(sctps_outcontrolchunks); return; Modified: head/sys/netinet/sctp_output.h ============================================================================== --- head/sys/netinet/sctp_output.h Sat Feb 20 19:59:52 2010 (r204140) +++ head/sys/netinet/sctp_output.h Sat Feb 20 20:30:40 2010 (r204141) @@ -111,7 +111,7 @@ void sctp_send_shutdown(struct sctp_tcb void sctp_send_shutdown_ack(struct sctp_tcb *, struct sctp_nets *); -void sctp_send_shutdown_complete(struct sctp_tcb *, struct sctp_nets *); +void sctp_send_shutdown_complete(struct sctp_tcb *, struct sctp_nets *, int); void sctp_send_shutdown_complete2(struct mbuf *, int, struct sctphdr *,
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201002202030.o1KKUekS010349>