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);
}
/* empty stream's listen queue */
-static void
+static inline void
empty_lq(struct tle_tcp_stream *s, struct stbl *st)
{
uint32_t i, n;
}
/* empty TX queue */
- empty_mbuf_ring(s->tx.q);
+ empty_tq(s);
/*
* mark the stream as free again.
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) {
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)
* 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);