Author: tuexen
Date: Fri Aug 28 20:05:18 2020
New Revision: 364937
URL: https://svnweb.freebsd.org/changeset/base/364937

Log:
  Fix a regression with the explicit EOR mode I introduced in r364268.
  A short MFC time as discussed with the secteam.
  
  Reported by:          Taylor Brandstetter
  MFC after:            1 day

Modified:
  head/sys/netinet/sctp_output.c

Modified: head/sys/netinet/sctp_output.c
==============================================================================
--- head/sys/netinet/sctp_output.c      Fri Aug 28 20:03:54 2020        
(r364936)
+++ head/sys/netinet/sctp_output.c      Fri Aug 28 20:05:18 2020        
(r364937)
@@ -13118,11 +13118,10 @@ skip_preblock:
                        error = EINVAL;
                        goto out;
                }
-               SCTP_TCB_SEND_UNLOCK(stcb);
-
                strm = &stcb->asoc.strmout[srcv->sinfo_stream];
                if (strm->last_msg_incomplete == 0) {
        do_a_copy_in:
+                       SCTP_TCB_SEND_UNLOCK(stcb);
                        sp = sctp_copy_it_in(stcb, asoc, srcv, uio, net, 
max_len, user_marks_eor, &error);
                        if (error) {
                                goto out;
@@ -13151,19 +13150,8 @@ skip_preblock:
                        sp->processing = 1;
                        TAILQ_INSERT_TAIL(&strm->outqueue, sp, next);
                        stcb->asoc.ss_functions.sctp_ss_add_to_stream(stcb, 
asoc, strm, sp, 1);
-                       SCTP_TCB_SEND_UNLOCK(stcb);
                } else {
-                       SCTP_TCB_SEND_LOCK(stcb);
                        sp = TAILQ_LAST(&strm->outqueue, sctp_streamhead);
-                       if (sp->processing) {
-                               SCTP_TCB_SEND_UNLOCK(stcb);
-                               SCTP_LTRACE_ERR_RET(inp, stcb, net, 
SCTP_FROM_SCTP_OUTPUT, EINVAL);
-                               error = EINVAL;
-                               goto out;
-                       } else {
-                               sp->processing = 1;
-                       }
-                       SCTP_TCB_SEND_UNLOCK(stcb);
                        if (sp == NULL) {
                                /* ???? Huh ??? last msg is gone */
 #ifdef INVARIANTS
@@ -13175,7 +13163,16 @@ skip_preblock:
                                goto do_a_copy_in;
 
                        }
+                       if (sp->processing) {
+                               SCTP_TCB_SEND_UNLOCK(stcb);
+                               SCTP_LTRACE_ERR_RET(inp, stcb, net, 
SCTP_FROM_SCTP_OUTPUT, EINVAL);
+                               error = EINVAL;
+                               goto out;
+                       } else {
+                               sp->processing = 1;
+                       }
                }
+               SCTP_TCB_SEND_UNLOCK(stcb);
                while (uio->uio_resid > 0) {
                        /* How much room do we have? */
                        struct mbuf *new_tail, *mm;
@@ -13200,6 +13197,11 @@ skip_preblock:
                                        if (mm) {
                                                sctp_m_freem(mm);
                                        }
+                                       SCTP_TCB_SEND_LOCK(stcb);
+                                       if (sp != NULL) {
+                                               sp->processing = 0;
+                                       }
+                                       SCTP_TCB_SEND_UNLOCK(stcb);
                                        goto out;
                                }
                                /* Update the mbuf and count */
@@ -13215,6 +13217,9 @@ skip_preblock:
                                                SCTP_LTRACE_ERR_RET(NULL, stcb, 
NULL, SCTP_FROM_SCTP_OUTPUT, ECONNRESET);
                                                error = ECONNRESET;
                                        }
+                                       if (sp != NULL) {
+                                               sp->processing = 0;
+                                       }
                                        SCTP_TCB_SEND_UNLOCK(stcb);
                                        goto out;
                                }
@@ -13274,6 +13279,11 @@ skip_preblock:
                        /* wait for space now */
                        if (non_blocking) {
                                /* Non-blocking io in place out */
+                               SCTP_TCB_SEND_LOCK(stcb);
+                               if (sp != NULL) {
+                                       sp->processing = 0;
+                               }
+                               SCTP_TCB_SEND_UNLOCK(stcb);
                                goto skip_out_eof;
                        }
                        /* What about the INIT, send it maybe */
@@ -13401,6 +13411,11 @@ skip_preblock:
                                                }
                                        }
                                        SOCKBUF_UNLOCK(&so->so_snd);
+                                       SCTP_TCB_SEND_LOCK(stcb);
+                                       if (sp != NULL) {
+                                               sp->processing = 0;
+                                       }
+                                       SCTP_TCB_SEND_UNLOCK(stcb);
                                        goto out_unlocked;
                                }
 
@@ -13410,9 +13425,15 @@ skip_preblock:
                                }
                        }
                        SOCKBUF_UNLOCK(&so->so_snd);
+                       SCTP_TCB_SEND_LOCK(stcb);
                        if (stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) {
+                               if (sp != NULL) {
+                                       sp->processing = 0;
+                               }
+                               SCTP_TCB_SEND_UNLOCK(stcb);
                                goto out_unlocked;
                        }
+                       SCTP_TCB_SEND_UNLOCK(stcb);
                }
                SCTP_TCB_SEND_LOCK(stcb);
                if ((stcb->asoc.state & SCTP_STATE_ABOUT_TO_BE_FREED) ||
_______________________________________________
svn-src-all@freebsd.org mailing list
https://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"

Reply via email to