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

Commit 1299653a authored by Sergei Shtylyov's avatar Sergei Shtylyov Committed by David S. Miller
Browse files

sh_eth: fix descriptor access endianness



The driver never  calls cpu_to_edmac() when writing the descriptor address
and edmac_to_cpu() when reading it, although it should -- fix this.

Note that the frame/buffer length descriptor field accesses also need fixing
but since they are both 16-bit we can't  use {cpu|edmac}_to_{edmac|cpu}()...

Signed-off-by: default avatarSergei Shtylyov <sergei.shtylyov@cogentembedded.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 3e230993
Loading
Loading
Loading
Loading
+14 −10
Original line number Diff line number Diff line
@@ -1196,7 +1196,7 @@ static void sh_eth_ring_format(struct net_device *ndev)
			break;
		}
		mdp->rx_skbuff[i] = skb;
		rxdesc->addr = dma_addr;
		rxdesc->addr = cpu_to_edmac(mdp, dma_addr);
		rxdesc->status = cpu_to_edmac(mdp, RD_RACT | RD_RFP);

		/* Rx descriptor address set */
@@ -1427,7 +1427,8 @@ static int sh_eth_txfree(struct net_device *ndev)
			   entry, edmac_to_cpu(mdp, txdesc->status));
		/* Free the original skb. */
		if (mdp->tx_skbuff[entry]) {
			dma_unmap_single(&ndev->dev, txdesc->addr,
			dma_unmap_single(&ndev->dev,
					 edmac_to_cpu(mdp, txdesc->addr),
					 txdesc->buffer_length, DMA_TO_DEVICE);
			dev_kfree_skb_irq(mdp->tx_skbuff[entry]);
			mdp->tx_skbuff[entry] = NULL;
@@ -1503,14 +1504,15 @@ static int sh_eth_rx(struct net_device *ndev, u32 intr_status, int *quota)
			if (desc_status & RD_RFS10)
				ndev->stats.rx_over_errors++;
		} else	if (skb) {
			dma_addr = edmac_to_cpu(mdp, rxdesc->addr);
			if (!mdp->cd->hw_swap)
				sh_eth_soft_swap(
					phys_to_virt(ALIGN(rxdesc->addr, 4)),
					phys_to_virt(ALIGN(dma_addr, 4)),
					pkt_len + 2);
			mdp->rx_skbuff[entry] = NULL;
			if (mdp->cd->rpadir)
				skb_reserve(skb, NET_IP_ALIGN);
			dma_unmap_single(&ndev->dev, rxdesc->addr,
			dma_unmap_single(&ndev->dev, dma_addr,
					 ALIGN(mdp->rx_buf_sz, 32),
					 DMA_FROM_DEVICE);
			skb_put(skb, pkt_len);
@@ -1547,7 +1549,7 @@ static int sh_eth_rx(struct net_device *ndev, u32 intr_status, int *quota)
			mdp->rx_skbuff[entry] = skb;

			skb_checksum_none_assert(skb);
			rxdesc->addr = dma_addr;
			rxdesc->addr = cpu_to_edmac(mdp, dma_addr);
		}
		dma_wmb(); /* RACT bit must be set after all the above writes */
		if (entry >= mdp->num_rx_ring - 1)
@@ -2355,8 +2357,8 @@ static void sh_eth_tx_timeout(struct net_device *ndev)
	/* Free all the skbuffs in the Rx queue. */
	for (i = 0; i < mdp->num_rx_ring; i++) {
		rxdesc = &mdp->rx_ring[i];
		rxdesc->status = 0;
		rxdesc->addr = 0xBADF00D0;
		rxdesc->status = cpu_to_edmac(mdp, 0);
		rxdesc->addr = cpu_to_edmac(mdp, 0xBADF00D0);
		dev_kfree_skb(mdp->rx_skbuff[i]);
		mdp->rx_skbuff[i] = NULL;
	}
@@ -2374,6 +2376,7 @@ static int sh_eth_start_xmit(struct sk_buff *skb, struct net_device *ndev)
{
	struct sh_eth_private *mdp = netdev_priv(ndev);
	struct sh_eth_txdesc *txdesc;
	dma_addr_t dma_addr;
	u32 entry;
	unsigned long flags;

@@ -2397,12 +2400,13 @@ static int sh_eth_start_xmit(struct sk_buff *skb, struct net_device *ndev)
	/* soft swap. */
	if (!mdp->cd->hw_swap)
		sh_eth_soft_swap(PTR_ALIGN(skb->data, 4), skb->len + 2);
	txdesc->addr = dma_map_single(&ndev->dev, skb->data, skb->len,
	dma_addr = dma_map_single(&ndev->dev, skb->data, skb->len,
				  DMA_TO_DEVICE);
	if (dma_mapping_error(&ndev->dev, txdesc->addr)) {
	if (dma_mapping_error(&ndev->dev, dma_addr)) {
		kfree_skb(skb);
		return NETDEV_TX_OK;
	}
	txdesc->addr = cpu_to_edmac(mdp, dma_addr);
	txdesc->buffer_length = skb->len;

	dma_wmb(); /* TACT bit must be set after all the above writes */