diff mbox series

[2/6] net: dwc_eth_qos: Correctly wrap around TX descriptor tail pointer

Message ID 20200323014526.3340884-2-marex@denx.de
State Accepted
Commit 83858d87954627af7a576ccc7c93034b055faa7b
Headers show
Series [1/6] net: dwc_eth_qos: Fully rewrite RX descriptor field 3 | expand

Commit Message

Marek Vasut March 23, 2020, 1:45 a.m. UTC
This code programs the next descriptor in the TX descriptor ring into
the hardware as the last valid TX descriptor. The problem is that if
the currenty descriptor is the last one in the array, the code will
not wrap around correctly and use TX descriptor 0 again, but instead
will use TX descriptor at address right past the TX descriptor ring,
which is the first descriptor in the RX ring.

Fix this by adding the necessary wrap-around.

Signed-off-by: Marek Vasut <marex at denx.de>
Cc: Joe Hershberger <joe.hershberger at ni.com>
Cc: Patrice Chotard <patrice.chotard at st.com>
Cc: Patrick Delaunay <patrick.delaunay at st.com>
Cc: Ramon Fried <rfried.dev at gmail.com>
Cc: Stephen Warren <swarren at nvidia.com>
---
 drivers/net/dwc_eth_qos.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

Comments

Ramon Fried March 23, 2020, 7:06 a.m. UTC | #1
On Mon, Mar 23, 2020 at 3:45 AM Marek Vasut <marex at denx.de> wrote:
>
> This code programs the next descriptor in the TX descriptor ring into
> the hardware as the last valid TX descriptor. The problem is that if
> the currenty descriptor is the last one in the array, the code will
> not wrap around correctly and use TX descriptor 0 again, but instead
> will use TX descriptor at address right past the TX descriptor ring,
> which is the first descriptor in the RX ring.
>
> Fix this by adding the necessary wrap-around.
>
> Signed-off-by: Marek Vasut <marex at denx.de>
> Cc: Joe Hershberger <joe.hershberger at ni.com>
> Cc: Patrice Chotard <patrice.chotard at st.com>
> Cc: Patrick Delaunay <patrick.delaunay at st.com>
> Cc: Ramon Fried <rfried.dev at gmail.com>
> Cc: Stephen Warren <swarren at nvidia.com>
> ---
>  drivers/net/dwc_eth_qos.c | 3 ++-
>  1 file changed, 2 insertions(+), 1 deletion(-)
>
> diff --git a/drivers/net/dwc_eth_qos.c b/drivers/net/dwc_eth_qos.c
> index 4bce6d4290..c4f665bda9 100644
> --- a/drivers/net/dwc_eth_qos.c
> +++ b/drivers/net/dwc_eth_qos.c
> @@ -1373,7 +1373,8 @@ static int eqos_send(struct udevice *dev, void *packet, int length)
>         tx_desc->des3 = EQOS_DESC3_OWN | EQOS_DESC3_FD | EQOS_DESC3_LD | length;
>         eqos->config->ops->eqos_flush_desc(tx_desc);
>
> -       writel((ulong)(tx_desc + 1), &eqos->dma_regs->ch0_txdesc_tail_pointer);
> +       writel((ulong)(&(eqos->tx_descs[eqos->tx_desc_idx])),
> +               &eqos->dma_regs->ch0_txdesc_tail_pointer);
>
>         for (i = 0; i < 1000000; i++) {
>                 eqos->config->ops->eqos_inval_desc(tx_desc);
> --
> 2.25.1
>
Reviewed-by: Ramon Fried <rfried.dev at gmail.com>
diff mbox series

Patch

diff --git a/drivers/net/dwc_eth_qos.c b/drivers/net/dwc_eth_qos.c
index 4bce6d4290..c4f665bda9 100644
--- a/drivers/net/dwc_eth_qos.c
+++ b/drivers/net/dwc_eth_qos.c
@@ -1373,7 +1373,8 @@  static int eqos_send(struct udevice *dev, void *packet, int length)
 	tx_desc->des3 = EQOS_DESC3_OWN | EQOS_DESC3_FD | EQOS_DESC3_LD | length;
 	eqos->config->ops->eqos_flush_desc(tx_desc);
 
-	writel((ulong)(tx_desc + 1), &eqos->dma_regs->ch0_txdesc_tail_pointer);
+	writel((ulong)(&(eqos->tx_descs[eqos->tx_desc_idx])),
+		&eqos->dma_regs->ch0_txdesc_tail_pointer);
 
 	for (i = 0; i < 1000000; i++) {
 		eqos->config->ops->eqos_inval_desc(tx_desc);