libtle_l4p: fix at termination tcp stream not always cleanup it's send queue. 95/7095/1
authorKonstantin Ananyev <konstantin.ananyev@intel.com>
Sun, 11 Jun 2017 12:22:41 +0000 (13:22 +0100)
committerKonstantin Ananyev <konstantin.ananyev@intel.com>
Sun, 11 Jun 2017 12:23:51 +0000 (13:23 +0100)
Change-Id: I8ab713c98712fafe2550a6954224ebc741cf9029
Signed-off-by: Konstantin Ananyev <konstantin.ananyev@intel.com>
lib/libtle_l4p/tcp_ctl.h
lib/libtle_l4p/tcp_rxtx.c

index f7e70e3..32faaa2 100644 (file)
@@ -55,8 +55,16 @@ calc_rx_wnd(const struct tle_tcp_stream *s, uint32_t scale)
                return  _rte_ring_get_mask(s->rx.q) << scale;
 }
 
+/* empty stream's send queue */
+static inline void
+empty_tq(struct tle_tcp_stream *s)
+{
+       s->tx.q->cons.head = s->tx.q->cons.tail;
+       empty_mbuf_ring(s->tx.q);
+}
+
 /* empty stream's receive queue */
-static void
+static inline void
 empty_rq(struct tle_tcp_stream *s)
 {
        empty_mbuf_ring(s->rx.q);
@@ -64,7 +72,7 @@ empty_rq(struct tle_tcp_stream *s)
 }
 
 /* empty stream's listen queue */
-static void
+static inline void
 empty_lq(struct tle_tcp_stream *s, struct stbl *st)
 {
        uint32_t i, n;
@@ -117,7 +125,7 @@ tcp_stream_reset(struct tle_ctx *ctx, struct tle_tcp_stream *s)
        }
 
        /* empty TX queue */
-       empty_mbuf_ring(s->tx.q);
+       empty_tq(s);
 
        /*
         * mark the stream as free again.
index 7429bf0..a1c7d09 100644 (file)
@@ -1080,8 +1080,17 @@ rx_fin(struct tle_tcp_stream *s, uint32_t state,
                        return -ENOBUFS;
        }
 
-       /* process ack here */
-       rx_ackdata(s, si->ack);
+       /*
+        * fast-path: all data & FIN was already sent out
+        * and now is acknowledged.
+        */
+       if (s->tcb.snd.fss == s->tcb.snd.nxt &&
+                       si->ack == (uint32_t)s->tcb.snd.nxt) {
+               s->tcb.snd.una = s->tcb.snd.fss;
+               empty_tq(s);
+       /* conventional ACK processiing */
+       } else
+               rx_ackdata(s, si->ack);
 
        /* some fragments still missing */
        if (seq + plen != s->tcb.rcv.nxt) {
@@ -1470,7 +1479,7 @@ rx_ackfin(struct tle_tcp_stream *s)
        uint32_t state;
 
        s->tcb.snd.una = s->tcb.snd.fss;
-       empty_mbuf_ring(s->tx.q);
+       empty_tq(s);
 
        state = s->tcb.state;
        if (state == TCP_ST_LAST_ACK)
@@ -1656,7 +1665,7 @@ rx_stream(struct tle_tcp_stream *s, uint32_t ts,
                 * and now is acknowledged.
                 */
                if (s->tcb.snd.fss == s->tcb.snd.nxt &&
-                               tack.ack == (uint32_t) s->tcb.snd.nxt)
+                               tack.ack == (uint32_t)s->tcb.snd.nxt)
                        rx_ackfin(s);
                else
                        rx_process_ack(s, ts, &tack);