Skip to content

Commit

Permalink
net/faraday: Separate rx page storage from rxdesc
Browse files Browse the repository at this point in the history
The ftgmac100 hardware revision in e.g. the Aspeed AST2500 no longer
reserves all bits in RXDES#2 but instead uses the bottom 16 bits to
store MAC frame metadata. Avoid corruption by shifting struct page
pointers out to their own member in struct ftgmac100.

Signed-off-by: Andrew Jeffery <andrew@aj.id.au>
Signed-off-by: Joel Stanley <joel@jms.id.au>
Signed-off-by: David S. Miller <davem@davemloft.net>
  • Loading branch information
Andrew Jeffery authored and David S. Miller committed Sep 22, 2016
1 parent 524605e commit ada66b5
Showing 1 changed file with 18 additions and 7 deletions.
25 changes: 18 additions & 7 deletions drivers/net/ethernet/faraday/ftgmac100.c
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,8 @@ struct ftgmac100 {
struct ftgmac100_descs *descs;
dma_addr_t descs_dma_addr;

struct page *rx_pages[RX_QUEUE_ENTRIES];

unsigned int rx_pointer;
unsigned int tx_clean_pointer;
unsigned int tx_pointer;
Expand Down Expand Up @@ -341,18 +343,27 @@ static bool ftgmac100_rxdes_ipcs_err(struct ftgmac100_rxdes *rxdes)
return rxdes->rxdes1 & cpu_to_le32(FTGMAC100_RXDES1_IP_CHKSUM_ERR);
}

static inline struct page **ftgmac100_rxdes_page_slot(struct ftgmac100 *priv,
struct ftgmac100_rxdes *rxdes)
{
return &priv->rx_pages[rxdes - priv->descs->rxdes];
}

/*
* rxdes2 is not used by hardware. We use it to keep track of page.
* Since hardware does not touch it, we can skip cpu_to_le32()/le32_to_cpu().
*/
static void ftgmac100_rxdes_set_page(struct ftgmac100_rxdes *rxdes, struct page *page)
static void ftgmac100_rxdes_set_page(struct ftgmac100 *priv,
struct ftgmac100_rxdes *rxdes,
struct page *page)
{
rxdes->rxdes2 = (unsigned int)page;
*ftgmac100_rxdes_page_slot(priv, rxdes) = page;
}

static struct page *ftgmac100_rxdes_get_page(struct ftgmac100_rxdes *rxdes)
static struct page *ftgmac100_rxdes_get_page(struct ftgmac100 *priv,
struct ftgmac100_rxdes *rxdes)
{
return (struct page *)rxdes->rxdes2;
return *ftgmac100_rxdes_page_slot(priv, rxdes);
}

/******************************************************************************
Expand Down Expand Up @@ -501,7 +512,7 @@ static bool ftgmac100_rx_packet(struct ftgmac100 *priv, int *processed)

do {
dma_addr_t map = ftgmac100_rxdes_get_dma_addr(rxdes);
struct page *page = ftgmac100_rxdes_get_page(rxdes);
struct page *page = ftgmac100_rxdes_get_page(priv, rxdes);
unsigned int size;

dma_unmap_page(priv->dev, map, RX_BUF_SIZE, DMA_FROM_DEVICE);
Expand Down Expand Up @@ -779,7 +790,7 @@ static int ftgmac100_alloc_rx_page(struct ftgmac100 *priv,
return -ENOMEM;
}

ftgmac100_rxdes_set_page(rxdes, page);
ftgmac100_rxdes_set_page(priv, rxdes, page);
ftgmac100_rxdes_set_dma_addr(rxdes, map);
ftgmac100_rxdes_set_dma_own(rxdes);
return 0;
Expand All @@ -791,7 +802,7 @@ static void ftgmac100_free_buffers(struct ftgmac100 *priv)

for (i = 0; i < RX_QUEUE_ENTRIES; i++) {
struct ftgmac100_rxdes *rxdes = &priv->descs->rxdes[i];
struct page *page = ftgmac100_rxdes_get_page(rxdes);
struct page *page = ftgmac100_rxdes_get_page(priv, rxdes);
dma_addr_t map = ftgmac100_rxdes_get_dma_addr(rxdes);

if (!page)
Expand Down

0 comments on commit ada66b5

Please sign in to comment.