Commit f87af0de authored by Dheeraj Reddy Jonnalagadda's avatar Dheeraj Reddy Jonnalagadda Committed by Wentao Guan
Browse files

net: fec: implement TSO descriptor cleanup

stable inclusion
from stable-v6.6.76
commit d063bec046a04c26bcabf90f36289c77ae51413f
category: bugfix
bugzilla: https://gitee.com/openeuler/kernel/issues/IBW08Q

Reference: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/commit/?id=d063bec046a04c26bcabf90f36289c77ae51413f



--------------------------------

[ Upstream commit 61dc1fd9205bc9d9918aa933a847b08e80b4dc20 ]

Implement cleanup of descriptors in the TSO error path of
fec_enet_txq_submit_tso(). The cleanup

- Unmaps DMA buffers for data descriptors skipping TSO header
- Clears all buffer descriptors
- Handles extended descriptors by clearing cbd_esc when enabled

Fixes: 79f33912 ("net: fec: Add software TSO support")
Signed-off-by: default avatarDheeraj Reddy Jonnalagadda <dheeraj.linuxdev@gmail.com>
Reviewed-by: default avatarWei Fang <wei.fang@nxp.com>
Link: https://patch.msgid.link/20250120085430.99318-1-dheeraj.linuxdev@gmail.com


Signed-off-by: default avatarPaolo Abeni <pabeni@redhat.com>
Signed-off-by: default avatarSasha Levin <sashal@kernel.org>
(cherry picked from commit d063bec046a04c26bcabf90f36289c77ae51413f)
Signed-off-by: default avatarWentao Guan <guanwentao@uniontech.com>
parent 5cff6eec
Loading
Loading
Loading
Loading
+30 −1
Original line number Diff line number Diff line
@@ -821,6 +821,8 @@ static int fec_enet_txq_submit_tso(struct fec_enet_priv_tx_q *txq,
	struct fec_enet_private *fep = netdev_priv(ndev);
	int hdr_len, total_len, data_left;
	struct bufdesc *bdp = txq->bd.cur;
	struct bufdesc *tmp_bdp;
	struct bufdesc_ex *ebdp;
	struct tso_t tso;
	unsigned int index = 0;
	int ret;
@@ -894,7 +896,34 @@ static int fec_enet_txq_submit_tso(struct fec_enet_priv_tx_q *txq,
	return 0;

err_release:
	/* TODO: Release all used data descriptors for TSO */
	/* Release all used data descriptors for TSO */
	tmp_bdp = txq->bd.cur;

	while (tmp_bdp != bdp) {
		/* Unmap data buffers */
		if (tmp_bdp->cbd_bufaddr &&
		    !IS_TSO_HEADER(txq, fec32_to_cpu(tmp_bdp->cbd_bufaddr)))
			dma_unmap_single(&fep->pdev->dev,
					 fec32_to_cpu(tmp_bdp->cbd_bufaddr),
					 fec16_to_cpu(tmp_bdp->cbd_datlen),
					 DMA_TO_DEVICE);

		/* Clear standard buffer descriptor fields */
		tmp_bdp->cbd_sc = 0;
		tmp_bdp->cbd_datlen = 0;
		tmp_bdp->cbd_bufaddr = 0;

		/* Handle extended descriptor if enabled */
		if (fep->bufdesc_ex) {
			ebdp = (struct bufdesc_ex *)tmp_bdp;
			ebdp->cbd_esc = 0;
		}

		tmp_bdp = fec_enet_get_nextdesc(tmp_bdp, &txq->bd);
	}

	dev_kfree_skb_any(skb);

	return ret;
}