Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 1332c54b authored by Skylar Chang's avatar Skylar Chang
Browse files

msm: ipa3: fix packet handling for multiple buffers



Enable EOB event notification from GSI in order to receive completion
events on partial packets, which are split to multiple buffers.
This change is fixing few bugs in the handling of such a scenario.

CRs-Fixed: 1043511
Change-Id: I830dba8f4e47e3383b09639416fc704caa94cdf2
Acked-by: default avatarAdy Abraham <adya@qti.qualcomm.com>
Signed-off-by: default avatarSkylar Chang <chiaweic@codeaurora.org>
parent 323ea2db
Loading
Loading
Loading
Loading
+8 −5
Original line number Diff line number Diff line
@@ -1886,6 +1886,7 @@ static void ipa3_replenish_wlan_rx_cache(struct ipa3_sys_context *sys)
				gsi_xfer_elem_one.addr = rx_pkt->data.dma_addr;
				gsi_xfer_elem_one.len = IPA_WLAN_RX_BUFF_SZ;
				gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOT;
				gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOB;
				gsi_xfer_elem_one.type = GSI_XFER_ELEM_DATA;
				gsi_xfer_elem_one.xfer_user_data = rx_pkt;

@@ -2073,6 +2074,7 @@ static void ipa3_replenish_rx_cache(struct ipa3_sys_context *sys)
			gsi_xfer_elem_one.addr = rx_pkt->data.dma_addr;
			gsi_xfer_elem_one.len = sys->rx_buff_sz;
			gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOT;
			gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOB;
			gsi_xfer_elem_one.type = GSI_XFER_ELEM_DATA;
			gsi_xfer_elem_one.xfer_user_data = rx_pkt;

@@ -2179,6 +2181,7 @@ static void ipa3_replenish_rx_cache_recycle(struct ipa3_sys_context *sys)
			gsi_xfer_elem_one.addr = rx_pkt->data.dma_addr;
			gsi_xfer_elem_one.len = sys->rx_buff_sz;
			gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOT;
			gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOB;
			gsi_xfer_elem_one.type = GSI_XFER_ELEM_DATA;
			gsi_xfer_elem_one.xfer_user_data = rx_pkt;

@@ -2244,6 +2247,7 @@ static void ipa3_fast_replenish_rx_cache(struct ipa3_sys_context *sys)
			gsi_xfer_elem_one.addr = rx_pkt->data.dma_addr;
			gsi_xfer_elem_one.len = sys->rx_buff_sz;
			gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOT;
			gsi_xfer_elem_one.flags |= GSI_XFER_FLAG_EOB;
			gsi_xfer_elem_one.type = GSI_XFER_ELEM_DATA;
			gsi_xfer_elem_one.xfer_user_data = rx_pkt;

@@ -2379,7 +2383,6 @@ static int ipa3_lan_rx_pyld_hdlr(struct sk_buff *skb,

	if (skb->len == 0) {
		IPAERR("ZLT\n");
		sys->free_skb(skb);
		return rc;
	}

@@ -2439,7 +2442,6 @@ static int ipa3_lan_rx_pyld_hdlr(struct sk_buff *skb,
				sys->prev_skb = skb2;
			}
			sys->len_rem -= skb->len;
			sys->free_skb(skb);
			return rc;
		}
	}
@@ -2453,7 +2455,7 @@ begin:
		if (skb->len < pkt_status_sz) {
			WARN_ON(sys->prev_skb != NULL);
			IPADBG_LOW("status straddles buffer\n");
			sys->prev_skb = skb;
			sys->prev_skb = skb_copy(skb, GFP_KERNEL);
			sys->len_partial = skb->len;
			return rc;
		}
@@ -2545,7 +2547,7 @@ begin:
				IPAHAL_PKT_STATUS_EXCEPTION_NONE) {
				WARN_ON(sys->prev_skb != NULL);
				IPADBG_LOW("Ins header in next buffer\n");
				sys->prev_skb = skb;
				sys->prev_skb = skb_copy(skb, GFP_KERNEL);
				sys->len_partial = skb->len;
				return rc;
			}
@@ -2566,7 +2568,7 @@ begin:
			}

			skb2 = ipa3_skb_copy_for_client(skb,
				status.pkt_len + pkt_status_sz);
				min(status.pkt_len + pkt_status_sz, skb->len));
			if (likely(skb2)) {
				if (skb->len < len + pkt_status_sz) {
					IPADBG_LOW("SPL skb len %d len %d\n",
@@ -3699,6 +3701,7 @@ static void ipa_gsi_irq_rx_notify_cb(struct gsi_chan_xfer_notify *notify)

	switch (notify->evt_id) {
	case GSI_CHAN_EVT_EOT:
	case GSI_CHAN_EVT_EOB:
		atomic_set(&ipa3_ctx->transport_pm.eot_activity, 1);
		if (!atomic_read(&sys->curr_polling_state)) {
			/* put the gsi channel into polling mode */