Skip to content

Commit

Permalink
net: stmmac: fix wrongly set buffer2 valid when sph unsupport
Browse files Browse the repository at this point in the history
commit 396e13e upstream.

In current driver, buffer2 available only when hardware supports split
header. Wrongly set buffer2 valid in stmmac_rx_refill when refill buffer
address. You can see that desc3 is 0x81000000 after initialization, but
turn out to be 0x83000000 after refill.

Fixes: 67afd6d ("net: stmmac: Add Split Header support and enable it in XGMAC cores")
Signed-off-by: Joakim Zhang <qiangqing.zhang@nxp.com>
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
  • Loading branch information
Joakim Zhang authored and gregkh committed Mar 17, 2021
1 parent 6baecb9 commit 25048ef
Show file tree
Hide file tree
Showing 4 changed files with 15 additions and 6 deletions.
9 changes: 7 additions & 2 deletions drivers/net/ethernet/stmicro/stmmac/dwmac4_descs.c
Expand Up @@ -499,10 +499,15 @@ static void dwmac4_get_rx_header_len(struct dma_desc *p, unsigned int *len)
*len = le32_to_cpu(p->des2) & RDES2_HL;
}

static void dwmac4_set_sec_addr(struct dma_desc *p, dma_addr_t addr)
static void dwmac4_set_sec_addr(struct dma_desc *p, dma_addr_t addr, bool buf2_valid)
{
p->des2 = cpu_to_le32(lower_32_bits(addr));
p->des3 = cpu_to_le32(upper_32_bits(addr) | RDES3_BUFFER2_VALID_ADDR);
p->des3 = cpu_to_le32(upper_32_bits(addr));

if (buf2_valid)
p->des3 |= cpu_to_le32(RDES3_BUFFER2_VALID_ADDR);
else
p->des3 &= cpu_to_le32(~RDES3_BUFFER2_VALID_ADDR);
}

static void dwmac4_set_tbs(struct dma_edesc *p, u32 sec, u32 nsec)
Expand Down
2 changes: 1 addition & 1 deletion drivers/net/ethernet/stmicro/stmmac/dwxgmac2_descs.c
Expand Up @@ -292,7 +292,7 @@ static void dwxgmac2_get_rx_header_len(struct dma_desc *p, unsigned int *len)
*len = le32_to_cpu(p->des2) & XGMAC_RDES2_HL;
}

static void dwxgmac2_set_sec_addr(struct dma_desc *p, dma_addr_t addr)
static void dwxgmac2_set_sec_addr(struct dma_desc *p, dma_addr_t addr, bool is_valid)
{
p->des2 = cpu_to_le32(lower_32_bits(addr));
p->des3 = cpu_to_le32(upper_32_bits(addr));
Expand Down
2 changes: 1 addition & 1 deletion drivers/net/ethernet/stmicro/stmmac/hwif.h
Expand Up @@ -91,7 +91,7 @@ struct stmmac_desc_ops {
int (*get_rx_hash)(struct dma_desc *p, u32 *hash,
enum pkt_hash_types *type);
void (*get_rx_header_len)(struct dma_desc *p, unsigned int *len);
void (*set_sec_addr)(struct dma_desc *p, dma_addr_t addr);
void (*set_sec_addr)(struct dma_desc *p, dma_addr_t addr, bool buf2_valid);
void (*set_sarc)(struct dma_desc *p, u32 sarc_type);
void (*set_vlan_tag)(struct dma_desc *p, u16 tag, u16 inner_tag,
u32 inner_type);
Expand Down
8 changes: 6 additions & 2 deletions drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
Expand Up @@ -1303,9 +1303,10 @@ static int stmmac_init_rx_buffers(struct stmmac_priv *priv, struct dma_desc *p,
return -ENOMEM;

buf->sec_addr = page_pool_get_dma_addr(buf->sec_page);
stmmac_set_desc_sec_addr(priv, p, buf->sec_addr);
stmmac_set_desc_sec_addr(priv, p, buf->sec_addr, true);
} else {
buf->sec_page = NULL;
stmmac_set_desc_sec_addr(priv, p, buf->sec_addr, false);
}

buf->addr = page_pool_get_dma_addr(buf->page);
Expand Down Expand Up @@ -3648,7 +3649,10 @@ static inline void stmmac_rx_refill(struct stmmac_priv *priv, u32 queue)
DMA_FROM_DEVICE);

stmmac_set_desc_addr(priv, p, buf->addr);
stmmac_set_desc_sec_addr(priv, p, buf->sec_addr);
if (priv->sph)
stmmac_set_desc_sec_addr(priv, p, buf->sec_addr, true);
else
stmmac_set_desc_sec_addr(priv, p, buf->sec_addr, false);
stmmac_refill_desc3(priv, rx_q, p);

rx_q->rx_count_frames++;
Expand Down

0 comments on commit 25048ef

Please sign in to comment.