skge: set mac address bonding fix

When bonding does fail over it calls set_mac_address. When this happens
as the result of another port going down, the phy_mutex that is common to
both ports is held, so it deadlocks. Setting the address doesn't need to do
anything that needs the phy_mutex, it already has the RTNL to protect against
other admin actions.

This change just disables the receiver to avoid any hardware confusion
while address is changing.

Signed-off-by: Stephen Hemminger <shemminger@linux-foundation.org>
Signed-off-by: Jeff Garzik <jeff@garzik.org>

authored by Stephen Hemminger and committed by Jeff Garzik 2eb3e621 8ce5e3e4

+17 -11
+17 -11
drivers/net/skge.c
··· 3275 struct skge_hw *hw = skge->hw; 3276 unsigned port = skge->port; 3277 const struct sockaddr *addr = p; 3278 3279 if (!is_valid_ether_addr(addr->sa_data)) 3280 return -EADDRNOTAVAIL; 3281 3282 - mutex_lock(&hw->phy_mutex); 3283 memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN); 3284 - memcpy_toio(hw->regs + B2_MAC_1 + port*8, 3285 - dev->dev_addr, ETH_ALEN); 3286 - memcpy_toio(hw->regs + B2_MAC_2 + port*8, 3287 - dev->dev_addr, ETH_ALEN); 3288 3289 - if (hw->chip_id == CHIP_ID_GENESIS) 3290 - xm_outaddr(hw, port, XM_SA, dev->dev_addr); 3291 - else { 3292 - gma_set_addr(hw, port, GM_SRC_ADDR_1L, dev->dev_addr); 3293 - gma_set_addr(hw, port, GM_SRC_ADDR_2L, dev->dev_addr); 3294 } 3295 - mutex_unlock(&hw->phy_mutex); 3296 3297 return 0; 3298 }
··· 3275 struct skge_hw *hw = skge->hw; 3276 unsigned port = skge->port; 3277 const struct sockaddr *addr = p; 3278 + u16 ctrl; 3279 3280 if (!is_valid_ether_addr(addr->sa_data)) 3281 return -EADDRNOTAVAIL; 3282 3283 memcpy(dev->dev_addr, addr->sa_data, ETH_ALEN); 3284 3285 + /* disable Rx */ 3286 + ctrl = gma_read16(hw, port, GM_GP_CTRL); 3287 + gma_write16(hw, port, GM_GP_CTRL, ctrl & ~GM_GPCR_RX_ENA); 3288 + 3289 + memcpy_toio(hw->regs + B2_MAC_1 + port*8, dev->dev_addr, ETH_ALEN); 3290 + memcpy_toio(hw->regs + B2_MAC_2 + port*8, dev->dev_addr, ETH_ALEN); 3291 + 3292 + if (netif_running(dev)) { 3293 + if (hw->chip_id == CHIP_ID_GENESIS) 3294 + xm_outaddr(hw, port, XM_SA, dev->dev_addr); 3295 + else { 3296 + gma_set_addr(hw, port, GM_SRC_ADDR_1L, dev->dev_addr); 3297 + gma_set_addr(hw, port, GM_SRC_ADDR_2L, dev->dev_addr); 3298 + } 3299 } 3300 + 3301 + gma_write16(hw, port, GM_GP_CTRL, ctrl); 3302 3303 return 0; 3304 }