From 950d08794ec02a2cc7aaeb450f5a20b2034b67ce Mon Sep 17 00:00:00 2001 From: Hauke Mehrtens Date: Wed, 6 Feb 2013 14:57:00 +0000 Subject: brcm47xx: bgmac: make it possible to set the devices into promisc mode when it is already up This fixes #12927. git-svn-id: svn://svn.openwrt.org/openwrt/trunk@35507 3c298f89-4303-0410-b956-a3cf2f4a3e73 --- .../brcm47xx/patches-3.6/760-bgmac-fixes.patch | 112 +++++++++++++++++++++ 1 file changed, 112 insertions(+) create mode 100644 target/linux/brcm47xx/patches-3.6/760-bgmac-fixes.patch (limited to 'target/linux/brcm47xx/patches-3.6/760-bgmac-fixes.patch') diff --git a/target/linux/brcm47xx/patches-3.6/760-bgmac-fixes.patch b/target/linux/brcm47xx/patches-3.6/760-bgmac-fixes.patch new file mode 100644 index 0000000000..dfe9ccf7e7 --- /dev/null +++ b/target/linux/brcm47xx/patches-3.6/760-bgmac-fixes.patch @@ -0,0 +1,112 @@ +--- a/drivers/net/ethernet/broadcom/bgmac.c ++++ b/drivers/net/ethernet/broadcom/bgmac.c +@@ -761,6 +761,26 @@ static void bgmac_cmdcfg_maskset(struct + udelay(2); + } + ++static void bgmac_write_mac_address(struct bgmac *bgmac, u8 *addr) ++{ ++ u32 tmp; ++ ++ tmp = (addr[0] << 24) | (addr[1] << 16) | (addr[2] << 8) | addr[3]; ++ bgmac_write(bgmac, BGMAC_MACADDR_HIGH, tmp); ++ tmp = (addr[4] << 8) | addr[5]; ++ bgmac_write(bgmac, BGMAC_MACADDR_LOW, tmp); ++} ++ ++static void bgmac_set_rx_mode(struct net_device *net_dev) ++{ ++ struct bgmac *bgmac = netdev_priv(net_dev); ++ ++ if (net_dev->flags & IFF_PROMISC) ++ bgmac_cmdcfg_maskset(bgmac, ~0, BGMAC_CMDCFG_PROM, false); ++ else ++ bgmac_cmdcfg_maskset(bgmac, ~BGMAC_CMDCFG_PROM, 0, false); ++} ++ + #if 0 /* We don't use that regs yet */ + static void bgmac_chip_stats_update(struct bgmac *bgmac) + { +@@ -889,8 +909,10 @@ static void bgmac_chip_reset(struct bgma + sw_type = et_swtype; + } else if (ci->id == BCMA_CHIP_ID_BCM5357 && ci->pkg == 9) { + sw_type = BGMAC_CHIPCTL_1_SW_TYPE_EPHYRMII; +- } else if (0) { +- /* TODO */ ++ } else if ((ci->id != BCMA_CHIP_ID_BCM53572 && ci->pkg == 10) || ++ (ci->id == BCMA_CHIP_ID_BCM53572 && ci->pkg == 9)) { ++ sw_type = BGMAC_CHIPCTL_1_IF_TYPE_RGMII | ++ BGMAC_CHIPCTL_1_SW_TYPE_RGMII; + } + bcma_chipco_chipctl_maskset(cc, 1, + ~(BGMAC_CHIPCTL_1_IF_TYPE_MASK | +@@ -1004,8 +1026,6 @@ static void bgmac_enable(struct bgmac *b + static void bgmac_chip_init(struct bgmac *bgmac, bool full_init) + { + struct bgmac_dma_ring *ring; +- u8 *mac = bgmac->net_dev->dev_addr; +- u32 tmp; + int i; + + /* 1 interrupt per received frame */ +@@ -1014,16 +1034,9 @@ static void bgmac_chip_init(struct bgmac + /* Enable 802.3x tx flow control (honor received PAUSE frames) */ + bgmac_cmdcfg_maskset(bgmac, ~BGMAC_CMDCFG_RPI, 0, true); + +- if (bgmac->net_dev->flags & IFF_PROMISC) +- bgmac_cmdcfg_maskset(bgmac, ~0, BGMAC_CMDCFG_PROM, false); +- else +- bgmac_cmdcfg_maskset(bgmac, ~BGMAC_CMDCFG_PROM, 0, false); ++ bgmac_set_rx_mode(bgmac->net_dev); + +- /* Set MAC addr */ +- tmp = (mac[0] << 24) | (mac[1] << 16) | (mac[2] << 8) | mac[3]; +- bgmac_write(bgmac, BGMAC_MACADDR_HIGH, tmp); +- tmp = (mac[4] << 8) | mac[5]; +- bgmac_write(bgmac, BGMAC_MACADDR_LOW, tmp); ++ bgmac_write_mac_address(bgmac, bgmac->net_dev->dev_addr); + + if (bgmac->loopback) + bgmac_cmdcfg_maskset(bgmac, ~0, BGMAC_CMDCFG_ML, true); +@@ -1160,6 +1173,19 @@ static netdev_tx_t bgmac_start_xmit(stru + return bgmac_dma_tx_add(bgmac, ring, skb); + } + ++static int bgmac_set_mac_address(struct net_device *net_dev, void *addr) ++{ ++ struct bgmac *bgmac = netdev_priv(net_dev); ++ int ret; ++ ++ ret = eth_prepare_mac_addr_change(net_dev, addr); ++ if (ret < 0) ++ return ret; ++ bgmac_write_mac_address(bgmac, (u8 *)addr); ++ eth_commit_mac_addr_change(net_dev, addr); ++ return 0; ++} ++ + static int bgmac_ioctl(struct net_device *net_dev, struct ifreq *ifr, int cmd) + { + struct bgmac *bgmac = netdev_priv(net_dev); +@@ -1190,7 +1216,9 @@ static const struct net_device_ops bgmac + .ndo_open = bgmac_open, + .ndo_stop = bgmac_stop, + .ndo_start_xmit = bgmac_start_xmit, +- .ndo_set_mac_address = eth_mac_addr, /* generic, sets dev_addr */ ++ .ndo_set_rx_mode = bgmac_set_rx_mode, ++ .ndo_set_mac_address = bgmac_set_mac_address, ++ .ndo_validate_addr = eth_validate_addr, + .ndo_do_ioctl = bgmac_ioctl, + }; + +--- a/drivers/net/ethernet/broadcom/bgmac.h ++++ b/drivers/net/ethernet/broadcom/bgmac.h +@@ -339,7 +339,7 @@ + #define BGMAC_CHIPCTL_1_SW_TYPE_EPHY 0x00000000 + #define BGMAC_CHIPCTL_1_SW_TYPE_EPHYMII 0x00000040 + #define BGMAC_CHIPCTL_1_SW_TYPE_EPHYRMII 0x00000080 +-#define BGMAC_CHIPCTL_1_SW_TYPE_RGMI 0x000000C0 ++#define BGMAC_CHIPCTL_1_SW_TYPE_RGMII 0x000000C0 + #define BGMAC_CHIPCTL_1_RXC_DLL_BYPASS 0x00010000 + + #define BGMAC_SPEED_10 0x0001 -- cgit v1.2.3