qcacmn: Do not LRO aggregate if peer is not connected
We have race condition between lro flush of hif_napi_poll and MC thread
lro flush while flushing the ol_txrx_cached_bufq packets for peer. Avoid
the situation by simply marking the all the Rx packets as LRO ineligible
while enqueuing packets to ol_rx_cached_buf.
Change-Id: Ief0d7dd6c25cf45912820f0e237fd1179a57a5c7
CRs-Fixed: 2032674
diff --git a/qdf/linux/src/i_qdf_nbuf.h b/qdf/linux/src/i_qdf_nbuf.h
index 8f8c9d7..e432ead 100644
--- a/qdf/linux/src/i_qdf_nbuf.h
+++ b/qdf/linux/src/i_qdf_nbuf.h
@@ -137,6 +137,7 @@
/* Note: MAX: 40 bytes */
struct {
uint32_t lro_eligible:1,
+ no_peer_lro_ineligible:1,
tcp_proto:1,
tcp_pure_ack:1,
ipv6_proto:1,
@@ -251,6 +252,8 @@
#define QDF_NBUF_CB_RX_LRO_ELIGIBLE(skb) \
(((struct qdf_nbuf_cb *)((skb)->cb))->u.rx.lro_eligible)
+#define QDF_NBUF_CB_RX_LRO_INELIGIBLE(skb) \
+ (((struct qdf_nbuf_cb *)((skb)->cb))->u.rx.no_peer_lro_ineligible)
#define QDF_NBUF_CB_RX_LRO_DESC(skb) \
(((struct qdf_nbuf_cb *)((skb)->cb))->u.rx.lro_desc)
#define QDF_NBUF_CB_RX_LRO_CTX(skb) \
diff --git a/qdf/linux/src/qdf_lro.c b/qdf/linux/src/qdf_lro.c
index a3ab6ab..5437c89 100644
--- a/qdf/linux/src/qdf_lro.c
+++ b/qdf/linux/src/qdf_lro.c
@@ -328,6 +328,7 @@
int hw_lro_eligible =
QDF_NBUF_CB_RX_LRO_ELIGIBLE(nbuf) &&
(!QDF_NBUF_CB_RX_TCP_PURE_ACK(nbuf));
+ int rx_data_before_peer_rx = QDF_NBUF_CB_RX_LRO_INELIGIBLE(nbuf);
if (unlikely(!lro_ctx)) {
QDF_TRACE(QDF_MODULE_ID_QDF, QDF_TRACE_LEVEL_ERROR,
@@ -335,7 +336,7 @@
return false;
}
- if (!hw_lro_eligible)
+ if (!hw_lro_eligible || rx_data_before_peer_rx)
return false;
iph = (struct iphdr *)info->iph;