Commit 097657c9 authored by David S. Miller's avatar David S. Miller

Merge branch 'stmmac-regression-fix'

Merge branch 'stmmac-regression-fix'

Herve Codina says:

====================
net: stmmac: fix regression on SPEAr3xx SOC

The ethernet driver used on old SPEAr3xx soc was previously supported on old
kernel. Some regressions were introduced during the different updates leading
to a broken driver for this soc.

This series fixes these regressions and brings back ethernet on SPEAr3xx.
Tested on a SPEAr320 board.
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents 612f71d7 6636fec2
...@@ -21,6 +21,7 @@ select: ...@@ -21,6 +21,7 @@ select:
contains: contains:
enum: enum:
- snps,dwmac - snps,dwmac
- snps,dwmac-3.40a
- snps,dwmac-3.50a - snps,dwmac-3.50a
- snps,dwmac-3.610 - snps,dwmac-3.610
- snps,dwmac-3.70a - snps,dwmac-3.70a
...@@ -76,6 +77,7 @@ properties: ...@@ -76,6 +77,7 @@ properties:
- rockchip,rk3399-gmac - rockchip,rk3399-gmac
- rockchip,rv1108-gmac - rockchip,rv1108-gmac
- snps,dwmac - snps,dwmac
- snps,dwmac-3.40a
- snps,dwmac-3.50a - snps,dwmac-3.50a
- snps,dwmac-3.610 - snps,dwmac-3.610
- snps,dwmac-3.70a - snps,dwmac-3.70a
......
...@@ -47,7 +47,7 @@ dma@fc400000 { ...@@ -47,7 +47,7 @@ dma@fc400000 {
}; };
gmac: eth@e0800000 { gmac: eth@e0800000 {
compatible = "st,spear600-gmac"; compatible = "snps,dwmac-3.40a";
reg = <0xe0800000 0x8000>; reg = <0xe0800000 0x8000>;
interrupts = <23 22>; interrupts = <23 22>;
interrupt-names = "macirq", "eth_wake_irq"; interrupt-names = "macirq", "eth_wake_irq";
......
...@@ -71,6 +71,7 @@ static int dwmac_generic_probe(struct platform_device *pdev) ...@@ -71,6 +71,7 @@ static int dwmac_generic_probe(struct platform_device *pdev)
static const struct of_device_id dwmac_generic_match[] = { static const struct of_device_id dwmac_generic_match[] = {
{ .compatible = "st,spear600-gmac"}, { .compatible = "st,spear600-gmac"},
{ .compatible = "snps,dwmac-3.40a"},
{ .compatible = "snps,dwmac-3.50a"}, { .compatible = "snps,dwmac-3.50a"},
{ .compatible = "snps,dwmac-3.610"}, { .compatible = "snps,dwmac-3.610"},
{ .compatible = "snps,dwmac-3.70a"}, { .compatible = "snps,dwmac-3.70a"},
......
...@@ -218,11 +218,18 @@ static void dwmac1000_dump_dma_regs(void __iomem *ioaddr, u32 *reg_space) ...@@ -218,11 +218,18 @@ static void dwmac1000_dump_dma_regs(void __iomem *ioaddr, u32 *reg_space)
readl(ioaddr + DMA_BUS_MODE + i * 4); readl(ioaddr + DMA_BUS_MODE + i * 4);
} }
static void dwmac1000_get_hw_feature(void __iomem *ioaddr, static int dwmac1000_get_hw_feature(void __iomem *ioaddr,
struct dma_features *dma_cap) struct dma_features *dma_cap)
{ {
u32 hw_cap = readl(ioaddr + DMA_HW_FEATURE); u32 hw_cap = readl(ioaddr + DMA_HW_FEATURE);
if (!hw_cap) {
/* 0x00000000 is the value read on old hardware that does not
* implement this register
*/
return -EOPNOTSUPP;
}
dma_cap->mbps_10_100 = (hw_cap & DMA_HW_FEAT_MIISEL); dma_cap->mbps_10_100 = (hw_cap & DMA_HW_FEAT_MIISEL);
dma_cap->mbps_1000 = (hw_cap & DMA_HW_FEAT_GMIISEL) >> 1; dma_cap->mbps_1000 = (hw_cap & DMA_HW_FEAT_GMIISEL) >> 1;
dma_cap->half_duplex = (hw_cap & DMA_HW_FEAT_HDSEL) >> 2; dma_cap->half_duplex = (hw_cap & DMA_HW_FEAT_HDSEL) >> 2;
...@@ -252,6 +259,8 @@ static void dwmac1000_get_hw_feature(void __iomem *ioaddr, ...@@ -252,6 +259,8 @@ static void dwmac1000_get_hw_feature(void __iomem *ioaddr,
dma_cap->number_tx_channel = (hw_cap & DMA_HW_FEAT_TXCHCNT) >> 22; dma_cap->number_tx_channel = (hw_cap & DMA_HW_FEAT_TXCHCNT) >> 22;
/* Alternate (enhanced) DESC mode */ /* Alternate (enhanced) DESC mode */
dma_cap->enh_desc = (hw_cap & DMA_HW_FEAT_ENHDESSEL) >> 24; dma_cap->enh_desc = (hw_cap & DMA_HW_FEAT_ENHDESSEL) >> 24;
return 0;
} }
static void dwmac1000_rx_watchdog(void __iomem *ioaddr, u32 riwt, static void dwmac1000_rx_watchdog(void __iomem *ioaddr, u32 riwt,
......
...@@ -347,8 +347,8 @@ static void dwmac4_dma_tx_chan_op_mode(void __iomem *ioaddr, int mode, ...@@ -347,8 +347,8 @@ static void dwmac4_dma_tx_chan_op_mode(void __iomem *ioaddr, int mode,
writel(mtl_tx_op, ioaddr + MTL_CHAN_TX_OP_MODE(channel)); writel(mtl_tx_op, ioaddr + MTL_CHAN_TX_OP_MODE(channel));
} }
static void dwmac4_get_hw_feature(void __iomem *ioaddr, static int dwmac4_get_hw_feature(void __iomem *ioaddr,
struct dma_features *dma_cap) struct dma_features *dma_cap)
{ {
u32 hw_cap = readl(ioaddr + GMAC_HW_FEATURE0); u32 hw_cap = readl(ioaddr + GMAC_HW_FEATURE0);
...@@ -437,6 +437,8 @@ static void dwmac4_get_hw_feature(void __iomem *ioaddr, ...@@ -437,6 +437,8 @@ static void dwmac4_get_hw_feature(void __iomem *ioaddr,
dma_cap->frpbs = (hw_cap & GMAC_HW_FEAT_FRPBS) >> 11; dma_cap->frpbs = (hw_cap & GMAC_HW_FEAT_FRPBS) >> 11;
dma_cap->frpsel = (hw_cap & GMAC_HW_FEAT_FRPSEL) >> 10; dma_cap->frpsel = (hw_cap & GMAC_HW_FEAT_FRPSEL) >> 10;
dma_cap->dvlan = (hw_cap & GMAC_HW_FEAT_DVLAN) >> 5; dma_cap->dvlan = (hw_cap & GMAC_HW_FEAT_DVLAN) >> 5;
return 0;
} }
/* Enable/disable TSO feature and set MSS */ /* Enable/disable TSO feature and set MSS */
......
...@@ -371,8 +371,8 @@ static int dwxgmac2_dma_interrupt(void __iomem *ioaddr, ...@@ -371,8 +371,8 @@ static int dwxgmac2_dma_interrupt(void __iomem *ioaddr,
return ret; return ret;
} }
static void dwxgmac2_get_hw_feature(void __iomem *ioaddr, static int dwxgmac2_get_hw_feature(void __iomem *ioaddr,
struct dma_features *dma_cap) struct dma_features *dma_cap)
{ {
u32 hw_cap; u32 hw_cap;
...@@ -445,6 +445,8 @@ static void dwxgmac2_get_hw_feature(void __iomem *ioaddr, ...@@ -445,6 +445,8 @@ static void dwxgmac2_get_hw_feature(void __iomem *ioaddr,
dma_cap->frpes = (hw_cap & XGMAC_HWFEAT_FRPES) >> 11; dma_cap->frpes = (hw_cap & XGMAC_HWFEAT_FRPES) >> 11;
dma_cap->frpbs = (hw_cap & XGMAC_HWFEAT_FRPPB) >> 9; dma_cap->frpbs = (hw_cap & XGMAC_HWFEAT_FRPPB) >> 9;
dma_cap->frpsel = (hw_cap & XGMAC_HWFEAT_FRPSEL) >> 3; dma_cap->frpsel = (hw_cap & XGMAC_HWFEAT_FRPSEL) >> 3;
return 0;
} }
static void dwxgmac2_rx_watchdog(void __iomem *ioaddr, u32 riwt, u32 queue) static void dwxgmac2_rx_watchdog(void __iomem *ioaddr, u32 riwt, u32 queue)
......
...@@ -203,8 +203,8 @@ struct stmmac_dma_ops { ...@@ -203,8 +203,8 @@ struct stmmac_dma_ops {
int (*dma_interrupt) (void __iomem *ioaddr, int (*dma_interrupt) (void __iomem *ioaddr,
struct stmmac_extra_stats *x, u32 chan, u32 dir); struct stmmac_extra_stats *x, u32 chan, u32 dir);
/* If supported then get the optional core features */ /* If supported then get the optional core features */
void (*get_hw_feature)(void __iomem *ioaddr, int (*get_hw_feature)(void __iomem *ioaddr,
struct dma_features *dma_cap); struct dma_features *dma_cap);
/* Program the HW RX Watchdog */ /* Program the HW RX Watchdog */
void (*rx_watchdog)(void __iomem *ioaddr, u32 riwt, u32 queue); void (*rx_watchdog)(void __iomem *ioaddr, u32 riwt, u32 queue);
void (*set_tx_ring_len)(void __iomem *ioaddr, u32 len, u32 chan); void (*set_tx_ring_len)(void __iomem *ioaddr, u32 len, u32 chan);
...@@ -255,7 +255,7 @@ struct stmmac_dma_ops { ...@@ -255,7 +255,7 @@ struct stmmac_dma_ops {
#define stmmac_dma_interrupt_status(__priv, __args...) \ #define stmmac_dma_interrupt_status(__priv, __args...) \
stmmac_do_callback(__priv, dma, dma_interrupt, __args) stmmac_do_callback(__priv, dma, dma_interrupt, __args)
#define stmmac_get_hw_feature(__priv, __args...) \ #define stmmac_get_hw_feature(__priv, __args...) \
stmmac_do_void_callback(__priv, dma, get_hw_feature, __args) stmmac_do_callback(__priv, dma, get_hw_feature, __args)
#define stmmac_rx_watchdog(__priv, __args...) \ #define stmmac_rx_watchdog(__priv, __args...) \
stmmac_do_void_callback(__priv, dma, rx_watchdog, __args) stmmac_do_void_callback(__priv, dma, rx_watchdog, __args)
#define stmmac_set_tx_ring_len(__priv, __args...) \ #define stmmac_set_tx_ring_len(__priv, __args...) \
......
...@@ -508,6 +508,14 @@ stmmac_probe_config_dt(struct platform_device *pdev, u8 *mac) ...@@ -508,6 +508,14 @@ stmmac_probe_config_dt(struct platform_device *pdev, u8 *mac)
plat->pmt = 1; plat->pmt = 1;
} }
if (of_device_is_compatible(np, "snps,dwmac-3.40a")) {
plat->has_gmac = 1;
plat->enh_desc = 1;
plat->tx_coe = 1;
plat->bugged_jumbo = 1;
plat->pmt = 1;
}
if (of_device_is_compatible(np, "snps,dwmac-4.00") || if (of_device_is_compatible(np, "snps,dwmac-4.00") ||
of_device_is_compatible(np, "snps,dwmac-4.10a") || of_device_is_compatible(np, "snps,dwmac-4.10a") ||
of_device_is_compatible(np, "snps,dwmac-4.20a") || of_device_is_compatible(np, "snps,dwmac-4.20a") ||
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment