From 03662e41c7cff64a776bfb1b3816de4be43de881 Mon Sep 17 00:00:00 2001 From: Tony Zelenoff Date: Wed, 11 Apr 2012 06:15:03 +0000 Subject: atl1: fix kernel panic in case of DMA errors Problem: There was two separate work_struct structures which share one handler. Unfortunately getting atl1_adapter structure from work_struct in case of DMA error was done from incorrect offset which cause kernel panics. Solution: The useless work_struct for DMA error removed and handler name changed to more generic one. Signed-off-by: Tony Zelenoff Signed-off-by: David S. Miller --- drivers/net/ethernet/atheros/atlx/atl1.c | 12 +++++------- drivers/net/ethernet/atheros/atlx/atl1.h | 3 +-- drivers/net/ethernet/atheros/atlx/atlx.c | 2 +- 3 files changed, 7 insertions(+), 10 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/atheros/atlx/atl1.c b/drivers/net/ethernet/atheros/atlx/atl1.c index 40ac4143654..c926857e820 100644 --- a/drivers/net/ethernet/atheros/atlx/atl1.c +++ b/drivers/net/ethernet/atheros/atlx/atl1.c @@ -2476,7 +2476,7 @@ static irqreturn_t atl1_intr(int irq, void *data) "pcie phy link down %x\n", status); if (netif_running(adapter->netdev)) { /* reset MAC */ iowrite32(0, adapter->hw.hw_addr + REG_IMR); - schedule_work(&adapter->pcie_dma_to_rst_task); + schedule_work(&adapter->reset_dev_task); return IRQ_HANDLED; } } @@ -2488,7 +2488,7 @@ static irqreturn_t atl1_intr(int irq, void *data) "pcie DMA r/w error (status = 0x%x)\n", status); iowrite32(0, adapter->hw.hw_addr + REG_IMR); - schedule_work(&adapter->pcie_dma_to_rst_task); + schedule_work(&adapter->reset_dev_task); return IRQ_HANDLED; } @@ -2633,10 +2633,10 @@ static void atl1_down(struct atl1_adapter *adapter) atl1_clean_rx_ring(adapter); } -static void atl1_tx_timeout_task(struct work_struct *work) +static void atl1_reset_dev_task(struct work_struct *work) { struct atl1_adapter *adapter = - container_of(work, struct atl1_adapter, tx_timeout_task); + container_of(work, struct atl1_adapter, reset_dev_task); struct net_device *netdev = adapter->netdev; netif_device_detach(netdev); @@ -3038,12 +3038,10 @@ static int __devinit atl1_probe(struct pci_dev *pdev, (unsigned long)adapter); adapter->phy_timer_pending = false; - INIT_WORK(&adapter->tx_timeout_task, atl1_tx_timeout_task); + INIT_WORK(&adapter->reset_dev_task, atl1_reset_dev_task); INIT_WORK(&adapter->link_chg_task, atlx_link_chg_task); - INIT_WORK(&adapter->pcie_dma_to_rst_task, atl1_tx_timeout_task); - err = register_netdev(netdev); if (err) goto err_common; diff --git a/drivers/net/ethernet/atheros/atlx/atl1.h b/drivers/net/ethernet/atheros/atlx/atl1.h index 109d6da8be9..e04bf4d71e4 100644 --- a/drivers/net/ethernet/atheros/atlx/atl1.h +++ b/drivers/net/ethernet/atheros/atlx/atl1.h @@ -758,9 +758,8 @@ struct atl1_adapter { u16 link_speed; u16 link_duplex; spinlock_t lock; - struct work_struct tx_timeout_task; + struct work_struct reset_dev_task; struct work_struct link_chg_task; - struct work_struct pcie_dma_to_rst_task; struct timer_list phy_config_timer; bool phy_timer_pending; diff --git a/drivers/net/ethernet/atheros/atlx/atlx.c b/drivers/net/ethernet/atheros/atlx/atlx.c index 3cd8837236d..c9e9dc57986 100644 --- a/drivers/net/ethernet/atheros/atlx/atlx.c +++ b/drivers/net/ethernet/atheros/atlx/atlx.c @@ -194,7 +194,7 @@ static void atlx_tx_timeout(struct net_device *netdev) { struct atlx_adapter *adapter = netdev_priv(netdev); /* Do the reset outside of interrupt context */ - schedule_work(&adapter->tx_timeout_task); + schedule_work(&adapter->reset_dev_task); } /* -- cgit v1.2.3-70-g09d2 From a8c9cb106fe79c28d6b7f1397652cadd228715ff Mon Sep 17 00:00:00 2001 From: Jason Wang Date: Wed, 11 Apr 2012 22:10:54 +0000 Subject: 8139cp: set intr mask after its handler is registered We set intr mask before its handler is registered, this does not work well when 8139cp is sharing irq line with other devices. As the irq could be enabled by the device before 8139cp's hander is registered which may lead unhandled irq. Fix this by introducing an helper cp_irq_enable() and call it after request_irq(). Signed-off-by: Jason Wang Reviewed-by: Flavio Leitner Signed-off-by: David S. Miller --- drivers/net/ethernet/realtek/8139cp.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/realtek/8139cp.c b/drivers/net/ethernet/realtek/8139cp.c index abc79076f86..b3287c0fe27 100644 --- a/drivers/net/ethernet/realtek/8139cp.c +++ b/drivers/net/ethernet/realtek/8139cp.c @@ -958,6 +958,11 @@ static inline void cp_start_hw (struct cp_private *cp) cpw8(Cmd, RxOn | TxOn); } +static void cp_enable_irq(struct cp_private *cp) +{ + cpw16_f(IntrMask, cp_intr_mask); +} + static void cp_init_hw (struct cp_private *cp) { struct net_device *dev = cp->dev; @@ -997,8 +1002,6 @@ static void cp_init_hw (struct cp_private *cp) cpw16(MultiIntr, 0); - cpw16_f(IntrMask, cp_intr_mask); - cpw8_f(Cfg9346, Cfg9346_Lock); } @@ -1130,6 +1133,8 @@ static int cp_open (struct net_device *dev) if (rc) goto err_out_hw; + cp_enable_irq(cp); + netif_carrier_off(dev); mii_check_media(&cp->mii_if, netif_msg_link(cp), true); netif_start_queue(dev); @@ -2031,6 +2036,7 @@ static int cp_resume (struct pci_dev *pdev) /* FIXME: sh*t may happen if the Rx ring buffer is depleted */ cp_init_rings_index (cp); cp_init_hw (cp); + cp_enable_irq(cp); netif_start_queue (dev); spin_lock_irqsave (&cp->lock, flags); -- cgit v1.2.3-70-g09d2 From 59a54f3082b9847c1240e24879750e3a03f96754 Mon Sep 17 00:00:00 2001 From: Michal Simek Date: Thu, 12 Apr 2012 01:11:12 +0000 Subject: drivers/net/ethernet/xilinx/axi ethernet: Correct Copyright Also fix MAINTAINERS file to reflect autorship. Daniel and Ariane changed coding style but not any functional changes in the driver itself. Signed-off-by: Michal Simek Signed-off-by: David S. Miller --- MAINTAINERS | 4 ++-- drivers/net/ethernet/xilinx/xilinx_axienet.h | 4 +--- drivers/net/ethernet/xilinx/xilinx_axienet_main.c | 6 +++--- drivers/net/ethernet/xilinx/xilinx_axienet_mdio.c | 6 +++--- 4 files changed, 9 insertions(+), 11 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/MAINTAINERS b/MAINTAINERS index 32671e00800..7cef7be8f84 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -7577,8 +7577,8 @@ F: Documentation/filesystems/xfs.txt F: fs/xfs/ XILINX AXI ETHERNET DRIVER -M: Ariane Keller -M: Daniel Borkmann +M: Anirudha Sarangi +M: John Linn S: Maintained F: drivers/net/ethernet/xilinx/xilinx_axienet* diff --git a/drivers/net/ethernet/xilinx/xilinx_axienet.h b/drivers/net/ethernet/xilinx/xilinx_axienet.h index cc83af083fd..44b8d2bad8c 100644 --- a/drivers/net/ethernet/xilinx/xilinx_axienet.h +++ b/drivers/net/ethernet/xilinx/xilinx_axienet.h @@ -2,9 +2,7 @@ * Definitions for Xilinx Axi Ethernet device driver. * * Copyright (c) 2009 Secret Lab Technologies, Ltd. - * Copyright (c) 2010 Xilinx, Inc. All rights reserved. - * Copyright (c) 2012 Daniel Borkmann, - * Copyright (c) 2012 Ariane Keller, + * Copyright (c) 2010 - 2012 Xilinx, Inc. All rights reserved. */ #ifndef XILINX_AXIENET_H diff --git a/drivers/net/ethernet/xilinx/xilinx_axienet_main.c b/drivers/net/ethernet/xilinx/xilinx_axienet_main.c index 2fcbeba6814..9c365e192a3 100644 --- a/drivers/net/ethernet/xilinx/xilinx_axienet_main.c +++ b/drivers/net/ethernet/xilinx/xilinx_axienet_main.c @@ -4,9 +4,9 @@ * Copyright (c) 2008 Nissin Systems Co., Ltd., Yoshio Kashiwagi * Copyright (c) 2005-2008 DLA Systems, David H. Lynch Jr. * Copyright (c) 2008-2009 Secret Lab Technologies Ltd. - * Copyright (c) 2010 Xilinx, Inc. All rights reserved. - * Copyright (c) 2012 Daniel Borkmann, - * Copyright (c) 2012 Ariane Keller, + * Copyright (c) 2010 - 2011 Michal Simek + * Copyright (c) 2010 - 2011 PetaLogix + * Copyright (c) 2010 - 2012 Xilinx, Inc. All rights reserved. * * This is a driver for the Xilinx Axi Ethernet which is used in the Virtex6 * and Spartan6. diff --git a/drivers/net/ethernet/xilinx/xilinx_axienet_mdio.c b/drivers/net/ethernet/xilinx/xilinx_axienet_mdio.c index d70b6e79f6c..e90e1f46121 100644 --- a/drivers/net/ethernet/xilinx/xilinx_axienet_mdio.c +++ b/drivers/net/ethernet/xilinx/xilinx_axienet_mdio.c @@ -2,9 +2,9 @@ * MDIO bus driver for the Xilinx Axi Ethernet device * * Copyright (c) 2009 Secret Lab Technologies, Ltd. - * Copyright (c) 2010 Xilinx, Inc. All rights reserved. - * Copyright (c) 2012 Daniel Borkmann, - * Copyright (c) 2012 Ariane Keller, + * Copyright (c) 2010 - 2011 Michal Simek + * Copyright (c) 2010 - 2011 PetaLogix + * Copyright (c) 2010 - 2012 Xilinx, Inc. All rights reserved. */ #include -- cgit v1.2.3-70-g09d2 From 51c61a2838c33dab7b6659b9a3e008bb1b40bc9b Mon Sep 17 00:00:00 2001 From: Matt Renzelmann Date: Fri, 13 Apr 2012 07:59:40 +0000 Subject: ks8851: Fix missing mutex_lock/unlock Move the ks8851_rdreg16 call above the call to request_irq and cache the result for subsequent repeated use. A spurious interrupt may otherwise cause a crash. Thanks to Stephen Boyd, Flavio Leitner, and Ben Hutchings for feedback. Signed-off-by: Matt Renzelmann Signed-off-by: David S. Miller --- drivers/net/ethernet/micrel/ks8851.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/micrel/ks8851.c b/drivers/net/ethernet/micrel/ks8851.c index c722aa607d0..e5dc0757f07 100644 --- a/drivers/net/ethernet/micrel/ks8851.c +++ b/drivers/net/ethernet/micrel/ks8851.c @@ -1418,6 +1418,7 @@ static int __devinit ks8851_probe(struct spi_device *spi) struct net_device *ndev; struct ks8851_net *ks; int ret; + unsigned cider; ndev = alloc_etherdev(sizeof(struct ks8851_net)); if (!ndev) @@ -1484,8 +1485,8 @@ static int __devinit ks8851_probe(struct spi_device *spi) ks8851_soft_reset(ks, GRR_GSR); /* simple check for a valid chip being connected to the bus */ - - if ((ks8851_rdreg16(ks, KS_CIDER) & ~CIDER_REV_MASK) != CIDER_ID) { + cider = ks8851_rdreg16(ks, KS_CIDER); + if ((cider & ~CIDER_REV_MASK) != CIDER_ID) { dev_err(&spi->dev, "failed to read device ID\n"); ret = -ENODEV; goto err_id; @@ -1516,8 +1517,7 @@ static int __devinit ks8851_probe(struct spi_device *spi) } netdev_info(ndev, "revision %d, MAC %pM, IRQ %d, %s EEPROM\n", - CIDER_REV_GET(ks8851_rdreg16(ks, KS_CIDER)), - ndev->dev_addr, ndev->irq, + CIDER_REV_GET(cider), ndev->dev_addr, ndev->irq, ks->rc_ccr & CCR_EEPROM ? "has" : "no"); return 0; -- cgit v1.2.3-70-g09d2 From 3c5e979bd037888dd7d722da22da4b43659af485 Mon Sep 17 00:00:00 2001 From: Will Deacon Date: Thu, 12 Apr 2012 05:54:09 +0000 Subject: net: smsc911x: fix skb handling in receive path The SMSC911x driver resets the ->head, ->data and ->tail pointers in the skb on the reset path in order to avoid buffer overflow due to packet padding performed by the hardware. This patch fixes the receive path so that the skb pointers are fixed up after the data has been read from the device, The error path is also fixed to use number of words consistently and prevent erroneous FIFO fastforwarding when skipping over bad data. Signed-off-by: Will Deacon Signed-off-by: Eric Dumazet Signed-off-by: David S. Miller --- drivers/net/ethernet/smsc/smsc911x.c | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/smsc/smsc911x.c b/drivers/net/ethernet/smsc/smsc911x.c index 4a697102707..5aa2dbe2bfb 100644 --- a/drivers/net/ethernet/smsc/smsc911x.c +++ b/drivers/net/ethernet/smsc/smsc911x.c @@ -1166,10 +1166,8 @@ smsc911x_rx_counterrors(struct net_device *dev, unsigned int rxstat) /* Quickly dumps bad packets */ static void -smsc911x_rx_fastforward(struct smsc911x_data *pdata, unsigned int pktbytes) +smsc911x_rx_fastforward(struct smsc911x_data *pdata, unsigned int pktwords) { - unsigned int pktwords = (pktbytes + NET_IP_ALIGN + 3) >> 2; - if (likely(pktwords >= 4)) { unsigned int timeout = 500; unsigned int val; @@ -1233,7 +1231,7 @@ static int smsc911x_poll(struct napi_struct *napi, int budget) continue; } - skb = netdev_alloc_skb(dev, pktlength + NET_IP_ALIGN); + skb = netdev_alloc_skb(dev, pktwords << 2); if (unlikely(!skb)) { SMSC_WARN(pdata, rx_err, "Unable to allocate skb for rx packet"); @@ -1243,14 +1241,12 @@ static int smsc911x_poll(struct napi_struct *napi, int budget) break; } - skb->data = skb->head; - skb_reset_tail_pointer(skb); + pdata->ops->rx_readfifo(pdata, + (unsigned int *)skb->data, pktwords); /* Align IP on 16B boundary */ skb_reserve(skb, NET_IP_ALIGN); skb_put(skb, pktlength - 4); - pdata->ops->rx_readfifo(pdata, - (unsigned int *)skb->head, pktwords); skb->protocol = eth_type_trans(skb, dev); skb_checksum_none_assert(skb); netif_receive_skb(skb); @@ -1565,7 +1561,7 @@ static int smsc911x_open(struct net_device *dev) smsc911x_reg_write(pdata, FIFO_INT, temp); /* set RX Data offset to 2 bytes for alignment */ - smsc911x_reg_write(pdata, RX_CFG, (2 << 8)); + smsc911x_reg_write(pdata, RX_CFG, (NET_IP_ALIGN << 8)); /* enable NAPI polling before enabling RX interrupts */ napi_enable(&pdata->napi); -- cgit v1.2.3-70-g09d2 From 92fe173391b3e0d0a7212fa8b9d72c8d61f31c26 Mon Sep 17 00:00:00 2001 From: Bruce Allan Date: Thu, 12 Apr 2012 06:27:03 +0000 Subject: e1000e: issues in Sx on 82577/8/9 A workaround was previously put in the driver to reset the device when transitioning to Sx in order to activate the changed settings of the PHY OEM bits (Low Power Link Up, or LPLU, and GbE disable configuration) for 82577/8/9 devices. After further review, it was found such a reset can cause the 82579 to confuse which version of 82579 it actually is and broke LPLU on all 82577/8/9 devices. The workaround during an S0->Sx transition on 82579 (instead of resetting the PHY) is to restart auto-negotiation after the OEM bits are configured; the restart of auto-negotiation activates the new OEM bits as does the reset. With 82577/8, the reset is changed to a generic reset which fixes the LPLU bits getting set wrong. Signed-off-by: Bruce Allan Tested-by: Aaron Brown Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/e1000e/ich8lan.c | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/intel/e1000e/ich8lan.c b/drivers/net/ethernet/intel/e1000e/ich8lan.c index 64c76443a7a..b461c24945e 100644 --- a/drivers/net/ethernet/intel/e1000e/ich8lan.c +++ b/drivers/net/ethernet/intel/e1000e/ich8lan.c @@ -1310,10 +1310,6 @@ static s32 e1000_oem_bits_config_ich8lan(struct e1000_hw *hw, bool d0_state) if (mac_reg & E1000_PHY_CTRL_D0A_LPLU) oem_reg |= HV_OEM_BITS_LPLU; - - /* Set Restart auto-neg to activate the bits */ - if (!hw->phy.ops.check_reset_block(hw)) - oem_reg |= HV_OEM_BITS_RESTART_AN; } else { if (mac_reg & (E1000_PHY_CTRL_GBE_DISABLE | E1000_PHY_CTRL_NOND0A_GBE_DISABLE)) @@ -1324,6 +1320,11 @@ static s32 e1000_oem_bits_config_ich8lan(struct e1000_hw *hw, bool d0_state) oem_reg |= HV_OEM_BITS_LPLU; } + /* Set Restart auto-neg to activate the bits */ + if ((d0_state || (hw->mac.type != e1000_pchlan)) && + !hw->phy.ops.check_reset_block(hw)) + oem_reg |= HV_OEM_BITS_RESTART_AN; + ret_val = hw->phy.ops.write_reg_locked(hw, HV_OEM_BITS, oem_reg); release: @@ -3682,7 +3683,11 @@ void e1000_suspend_workarounds_ich8lan(struct e1000_hw *hw) if (hw->mac.type >= e1000_pchlan) { e1000_oem_bits_config_ich8lan(hw, false); - e1000_phy_hw_reset_ich8lan(hw); + + /* Reset PHY to activate OEM bits on 82577/8 */ + if (hw->mac.type == e1000_pchlan) + e1000e_phy_hw_reset_generic(hw); + ret_val = hw->phy.ops.acquire(hw); if (ret_val) return; -- cgit v1.2.3-70-g09d2 From c509e754af96882eb46130e215cc4aa8f763d4ac Mon Sep 17 00:00:00 2001 From: Don Skidmore Date: Thu, 5 Apr 2012 08:12:05 +0000 Subject: ixgbe: fix WoL issue with fiber There are times we turn of the laser before shutdown. This is a bad thing if we want to wake on lan to work so now we make sure the laser is on before shutdown if we support WoL. Signed-off-by: Don Skidmore Tested-by: Stephen Ko Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/ixgbe/ixgbe_main.c | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c index 3e26b1f9ac7..dac7c01f833 100644 --- a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c +++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c @@ -4893,6 +4893,16 @@ static int __ixgbe_shutdown(struct pci_dev *pdev, bool *enable_wake) if (wufc) { ixgbe_set_rx_mode(netdev); + /* + * enable the optics for both mult-speed fiber and + * 82599 SFP+ fiber as we can WoL. + */ + if (hw->mac.ops.enable_tx_laser && + (hw->phy.multispeed_fiber || + (hw->mac.ops.get_media_type(hw) == ixgbe_media_type_fiber && + hw->mac.type == ixgbe_mac_82599EB))) + hw->mac.ops.enable_tx_laser(hw); + /* turn on all-multi mode if wake on multicast is enabled */ if (wufc & IXGBE_WUFC_MC) { fctrl = IXGBE_READ_REG(hw, IXGBE_FCTRL); -- cgit v1.2.3-70-g09d2 From 8a9a0ea6032186e3030419262678d652b88bf6a8 Mon Sep 17 00:00:00 2001 From: Davide Ciminaghi Date: Fri, 13 Apr 2012 04:48:25 +0000 Subject: net/ethernet: ks8851_mll fix rx frame buffer overflow At the beginning of ks_rcv(), a for loop retrieves the header information relevant to all the frames stored in the mac's internal buffers. The number of pending frames is stored as an 8 bits field in KS_RXFCTR. If interrupts are disabled long enough to allow for more than 32 frames to accumulate in the MAC's internal buffers, a buffer overflow occurs. This patch fixes the problem by making the driver's frame_head_info buffer big enough. Well actually, since the chip appears to have 12K of internal rx buffers and the shortest ethernet frame should be 64 bytes long, maybe the limit could be set to 12*1024/64 = 192 frames, but 255 should be safer. Signed-off-by: Davide Ciminaghi Signed-off-by: Raffaele Recalcati Signed-off-by: David S. Miller --- drivers/net/ethernet/micrel/ks8851_mll.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/micrel/ks8851_mll.c b/drivers/net/ethernet/micrel/ks8851_mll.c index b8104d9f408..5ffde23ac8f 100644 --- a/drivers/net/ethernet/micrel/ks8851_mll.c +++ b/drivers/net/ethernet/micrel/ks8851_mll.c @@ -40,7 +40,7 @@ #define DRV_NAME "ks8851_mll" static u8 KS_DEFAULT_MAC_ADDRESS[] = { 0x00, 0x10, 0xA1, 0x86, 0x95, 0x11 }; -#define MAX_RECV_FRAMES 32 +#define MAX_RECV_FRAMES 255 #define MAX_BUF_SIZE 2048 #define TX_BUF_SIZE 2000 #define RX_BUF_SIZE 2000 -- cgit v1.2.3-70-g09d2 From 34948a947d1a576c10afee6d14792fd237549577 Mon Sep 17 00:00:00 2001 From: Benjamin Poirier Date: Fri, 6 Apr 2012 07:20:21 +0000 Subject: ixgbe: add missing rtnl_lock in PM resume path Upon resume from standby, ixgbe may trigger the ASSERT_RTNL() in netif_set_real_num_tx_queues(). The call stack is: netif_set_real_num_tx_queues ixgbe_set_num_queues ixgbe_init_interrupt_scheme ixgbe_resume Signed-off-by: Benjamin Poirier Tested-by: Stephen Ko Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/ixgbe/ixgbe_main.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c index dac7c01f833..9e2be8c45c2 100644 --- a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c +++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c @@ -4836,7 +4836,9 @@ static int ixgbe_resume(struct pci_dev *pdev) pci_wake_from_d3(pdev, false); + rtnl_lock(); err = ixgbe_init_interrupt_scheme(adapter); + rtnl_unlock(); if (err) { e_dev_err("Cannot initialize interrupts for device\n"); return err; -- cgit v1.2.3-70-g09d2 From b2db497eb25510052fc2d3152384f964b3312004 Mon Sep 17 00:00:00 2001 From: Alexander Duyck Date: Sat, 7 Apr 2012 04:57:29 +0000 Subject: ixgbe: Identify FCoE rings earlier to resolve memory corruption w/ FCoE This patch makes it so that we identify FCoE rings earlier than ixgbe_set_rx_buffer_len. Instead we identify the Rx FCoE rings at allocation time in ixgbe_alloc_q_vector. The motivation behind this change is to avoid memory corruption when FCoE is enabled. Without this change we were initializing the rings at 0, and 2K on systems with 4K pages, then when we bumped the buffer size to 4K with order 1 pages we were accessing offsets 2K and 6K instead of 0 and 4K. This was resulting in memory corruptions. Signed-off-by: Alexander Duyck Acked-by: Yi Zou Tested-by: Ross Brattain Signed-off-by: Jeff Kirsher --- drivers/net/ethernet/intel/ixgbe/ixgbe_lib.c | 10 ++++++++++ drivers/net/ethernet/intel/ixgbe/ixgbe_main.c | 8 -------- 2 files changed, 10 insertions(+), 8 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/intel/ixgbe/ixgbe_lib.c b/drivers/net/ethernet/intel/ixgbe/ixgbe_lib.c index 027d7a75be3..ed1b47dc083 100644 --- a/drivers/net/ethernet/intel/ixgbe/ixgbe_lib.c +++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_lib.c @@ -622,6 +622,16 @@ static int ixgbe_alloc_q_vector(struct ixgbe_adapter *adapter, int v_idx, if (adapter->hw.mac.type == ixgbe_mac_82599EB) set_bit(__IXGBE_RX_CSUM_UDP_ZERO_ERR, &ring->state); +#ifdef IXGBE_FCOE + if (adapter->netdev->features & NETIF_F_FCOE_MTU) { + struct ixgbe_ring_feature *f; + f = &adapter->ring_feature[RING_F_FCOE]; + if ((rxr_idx >= f->mask) && + (rxr_idx < f->mask + f->indices)) + set_bit(__IXGBE_RX_FCOE_BUFSZ, &ring->state); + } + +#endif /* IXGBE_FCOE */ /* apply Rx specific ring traits */ ring->count = adapter->rx_ring_count; ring->queue_index = rxr_idx; diff --git a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c index 9e2be8c45c2..a7f3cd872ca 100644 --- a/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c +++ b/drivers/net/ethernet/intel/ixgbe/ixgbe_main.c @@ -3154,14 +3154,6 @@ static void ixgbe_set_rx_buffer_len(struct ixgbe_adapter *adapter) set_ring_rsc_enabled(rx_ring); else clear_ring_rsc_enabled(rx_ring); -#ifdef IXGBE_FCOE - if (netdev->features & NETIF_F_FCOE_MTU) { - struct ixgbe_ring_feature *f; - f = &adapter->ring_feature[RING_F_FCOE]; - if ((i >= f->mask) && (i < f->mask + f->indices)) - set_bit(__IXGBE_RX_FCOE_BUFSZ, &rx_ring->state); - } -#endif /* IXGBE_FCOE */ } } -- cgit v1.2.3-70-g09d2 From 5b76d0600b2b08eef77f8e9226938b7b6bde3099 Mon Sep 17 00:00:00 2001 From: Christian Riesch Date: Mon, 16 Apr 2012 04:35:25 +0000 Subject: davinci_mdio: Fix MDIO timeout check Under heavy load (flood ping) it is possible for the MDIO timeout to expire before the loop checks the GO bit again. This patch adds an additional check whether the operation was done before actually returning -ETIMEDOUT. To reproduce this bug, flood ping the device, e.g., ping -f -l 1000 After some time, a "timed out waiting for user access" warning may appear. And even worse, link may go down since the PHY reported a timeout. Signed-off-by: Christian Riesch Cc: Cc: Cyril Chemparathy Signed-off-by: David S. Miller --- drivers/net/ethernet/ti/davinci_mdio.c | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/ti/davinci_mdio.c b/drivers/net/ethernet/ti/davinci_mdio.c index 2757c7d6e63..e4e47088e26 100644 --- a/drivers/net/ethernet/ti/davinci_mdio.c +++ b/drivers/net/ethernet/ti/davinci_mdio.c @@ -181,6 +181,11 @@ static inline int wait_for_user_access(struct davinci_mdio_data *data) __davinci_mdio_reset(data); return -EAGAIN; } + + reg = __raw_readl(®s->user[0].access); + if ((reg & USERACCESS_GO) == 0) + return 0; + dev_err(data->dev, "timed out waiting for user access\n"); return -ETIMEDOUT; } -- cgit v1.2.3-70-g09d2 From 716af4abd6e6370226f567af50bfaca274515980 Mon Sep 17 00:00:00 2001 From: Dan Carpenter Date: Thu, 19 Apr 2012 10:00:19 +0300 Subject: ksz884x: don't copy too much in netdev_set_mac_address() MAX_ADDR_LEN is 32. ETH_ALEN is 6. mac->sa_data is a 14 byte array, so the memcpy() is doing a read past the end of the array. I asked about this on netdev and Ben Hutchings told me it's supposed to be copying ETH_ALEN bytes (thanks Ben). Signed-off-by: Dan Carpenter Signed-off-by: David S. Miller --- drivers/net/ethernet/micrel/ksz884x.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/micrel/ksz884x.c b/drivers/net/ethernet/micrel/ksz884x.c index ef723b185d8..eaf9ff0262a 100644 --- a/drivers/net/ethernet/micrel/ksz884x.c +++ b/drivers/net/ethernet/micrel/ksz884x.c @@ -5675,7 +5675,7 @@ static int netdev_set_mac_address(struct net_device *dev, void *addr) memcpy(hw->override_addr, mac->sa_data, ETH_ALEN); } - memcpy(dev->dev_addr, mac->sa_data, MAX_ADDR_LEN); + memcpy(dev->dev_addr, mac->sa_data, ETH_ALEN); interrupt = hw_block_intr(hw); -- cgit v1.2.3-70-g09d2 From 7e5998aa74065d3ab31d17e667f40ffebf4b8425 Mon Sep 17 00:00:00 2001 From: Dan Carpenter Date: Tue, 17 Apr 2012 20:53:42 +0000 Subject: bnx2x: off by one in bnx2x_ets_e3b0_sp_pri_to_cos_set() The sp_pri_to_cos[] array size depends on the config but lets say it is BX_E3B0_MAX_NUM_COS_PORT0 and max_num_of_cos is also DCBX_E3B0_MAX_NUM_COS_PORT0. In the original code "pri == max_num_of_cos" was accepted but it is one past the end of the array. Also we used "pri" before capping it. It's a harmless read past the end of the array, but it would affect which error message gets printed. Signed-off-by: Dan Carpenter Acked-by: Eilon Greenstein Signed-off-by: David S. Miller --- drivers/net/ethernet/broadcom/bnx2x/bnx2x_link.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_link.c b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_link.c index ad95324dc04..64392ec410a 100644 --- a/drivers/net/ethernet/broadcom/bnx2x/bnx2x_link.c +++ b/drivers/net/ethernet/broadcom/bnx2x/bnx2x_link.c @@ -942,6 +942,12 @@ static int bnx2x_ets_e3b0_sp_pri_to_cos_set(const struct link_params *params, const u8 max_num_of_cos = (port) ? DCBX_E3B0_MAX_NUM_COS_PORT1 : DCBX_E3B0_MAX_NUM_COS_PORT0; + if (pri >= max_num_of_cos) { + DP(NETIF_MSG_LINK, "bnx2x_ets_e3b0_sp_pri_to_cos_set invalid " + "parameter Illegal strict priority\n"); + return -EINVAL; + } + if (sp_pri_to_cos[pri] != DCBX_INVALID_COS) { DP(NETIF_MSG_LINK, "bnx2x_ets_e3b0_sp_pri_to_cos_set invalid " "parameter There can't be two COS's with " @@ -949,12 +955,6 @@ static int bnx2x_ets_e3b0_sp_pri_to_cos_set(const struct link_params *params, return -EINVAL; } - if (pri > max_num_of_cos) { - DP(NETIF_MSG_LINK, "bnx2x_ets_e3b0_sp_pri_to_cos_set invalid " - "parameter Illegal strict priority\n"); - return -EINVAL; - } - sp_pri_to_cos[pri] = cos_entry; return 0; -- cgit v1.2.3-70-g09d2 From c5a99937a9cf74a623384023201a7d98b51e7e3b Mon Sep 17 00:00:00 2001 From: Stephen Boyd Date: Wed, 18 Apr 2012 17:25:58 +0000 Subject: ks8851: Fix mutex deadlock in ks8851_net_stop() There is a potential deadlock scenario when the ks8851 driver is removed. The interrupt handler schedules a workqueue which acquires a mutex that ks8851_net_stop() also acquires before flushing the workqueue. Previously lockdep wouldn't be able to find this problem but now that it has the support we can trigger this lockdep warning by rmmoding the driver after an ifconfig up. Fix the possible deadlock by disabling the interrupts in the chip and then release the lock across the workqueue flushing. The mutex is only there to proect the registers anyway so this should be ok. ======================================================= [ INFO: possible circular locking dependency detected ] 3.0.21-00021-g8b33780-dirty #2911 ------------------------------------------------------- rmmod/125 is trying to acquire lock: ((&ks->irq_work)){+.+...}, at: [] flush_work+0x0/0xac but task is already holding lock: (&ks->lock){+.+...}, at: [] ks8851_net_stop+0x64/0x138 [ks8851] which lock already depends on the new lock. the existing dependency chain (in reverse order) is: -> #1 (&ks->lock){+.+...}: [] __lock_acquire+0x940/0x9f8 [] lock_acquire+0x10c/0x130 [] mutex_lock_nested+0x68/0x3dc [] ks8851_irq_work+0x24/0x46c [ks8851] [] process_one_work+0x2d8/0x518 [] worker_thread+0x220/0x3a0 [] kthread+0x88/0x94 [] kernel_thread_exit+0x0/0x8 -> #0 ((&ks->irq_work)){+.+...}: [] validate_chain+0x914/0x1018 [] __lock_acquire+0x940/0x9f8 [] lock_acquire+0x10c/0x130 [] flush_work+0x4c/0xac [] ks8851_net_stop+0x6c/0x138 [ks8851] [] __dev_close_many+0x98/0xcc [] dev_close_many+0x68/0xd0 [] rollback_registered_many+0xcc/0x2b8 [] rollback_registered+0x28/0x34 [] unregister_netdevice_queue+0x58/0x7c [] unregister_netdev+0x18/0x20 [] ks8851_remove+0x64/0xb4 [ks8851] [] spi_drv_remove+0x18/0x1c [] __device_release_driver+0x7c/0xbc [] driver_detach+0x8c/0xb4 [] bus_remove_driver+0xb8/0xe8 [] sys_delete_module+0x1e8/0x27c [] ret_fast_syscall+0x0/0x3c other info that might help us debug this: Possible unsafe locking scenario: CPU0 CPU1 ---- ---- lock(&ks->lock); lock((&ks->irq_work)); lock(&ks->lock); lock((&ks->irq_work)); *** DEADLOCK *** 4 locks held by rmmod/125: #0: (&__lockdep_no_validate__){+.+.+.}, at: [] driver_detach+0x6c/0xb4 #1: (&__lockdep_no_validate__){+.+.+.}, at: [] driver_detach+0x78/0xb4 #2: (rtnl_mutex){+.+.+.}, at: [] unregister_netdev+0xc/0x20 #3: (&ks->lock){+.+...}, at: [] ks8851_net_stop+0x64/0x138 [ks8851] Cc: Ben Dooks Signed-off-by: Stephen Boyd Signed-off-by: David S. Miller --- drivers/net/ethernet/micrel/ks8851.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/micrel/ks8851.c b/drivers/net/ethernet/micrel/ks8851.c index e5dc0757f07..ad10759e345 100644 --- a/drivers/net/ethernet/micrel/ks8851.c +++ b/drivers/net/ethernet/micrel/ks8851.c @@ -889,16 +889,17 @@ static int ks8851_net_stop(struct net_device *dev) netif_stop_queue(dev); mutex_lock(&ks->lock); + /* turn off the IRQs and ack any outstanding */ + ks8851_wrreg16(ks, KS_IER, 0x0000); + ks8851_wrreg16(ks, KS_ISR, 0xffff); + mutex_unlock(&ks->lock); /* stop any outstanding work */ flush_work(&ks->irq_work); flush_work(&ks->tx_work); flush_work(&ks->rxctrl_work); - /* turn off the IRQs and ack any outstanding */ - ks8851_wrreg16(ks, KS_IER, 0x0000); - ks8851_wrreg16(ks, KS_ISR, 0xffff); - + mutex_lock(&ks->lock); /* shutdown RX process */ ks8851_wrreg16(ks, KS_RXCR1, 0x0000); @@ -907,6 +908,7 @@ static int ks8851_net_stop(struct net_device *dev) /* set powermode to soft power down to save power */ ks8851_set_powermode(ks, PMECR_PM_SOFTDOWN); + mutex_unlock(&ks->lock); /* ensure any queued tx buffers are dumped */ while (!skb_queue_empty(&ks->txq)) { @@ -918,7 +920,6 @@ static int ks8851_net_stop(struct net_device *dev) dev_kfree_skb(txb); } - mutex_unlock(&ks->lock); return 0; } -- cgit v1.2.3-70-g09d2 From e8195b24feb208f6e944e7542779f4397776794d Mon Sep 17 00:00:00 2001 From: Matt Renzelmann Date: Thu, 19 Apr 2012 07:17:17 +0000 Subject: ks8851: Fix request_irq/free_irq mismatch The dev_id parameter passed to free_irq needs to match the one passed to the corresponding request_irq. Signed-off-by: Matt Renzelmann Acked-by: Stephen Boyd Signed-off-by: David S. Miller --- drivers/net/ethernet/micrel/ks8851.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/micrel/ks8851.c b/drivers/net/ethernet/micrel/ks8851.c index ad10759e345..f8dda009d3c 100644 --- a/drivers/net/ethernet/micrel/ks8851.c +++ b/drivers/net/ethernet/micrel/ks8851.c @@ -1525,7 +1525,7 @@ static int __devinit ks8851_probe(struct spi_device *spi) err_netdev: - free_irq(ndev->irq, ndev); + free_irq(ndev->irq, ks); err_id: err_irq: -- cgit v1.2.3-70-g09d2 From 163faf31778e536ac6125bc8b14f4667adc910e9 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 19 Apr 2012 10:36:33 +0000 Subject: drivers/net: Do not free an IRQ if its request failed Refrain from attempting to free an interrupt line if the request fails and hence, there is no IRQ to free. CC: netdev@vger.kernel.org Signed-off-by: Lee Jones Signed-off-by: David S. Miller --- drivers/net/ethernet/smsc/smsc911x.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'drivers/net/ethernet') diff --git a/drivers/net/ethernet/smsc/smsc911x.c b/drivers/net/ethernet/smsc/smsc911x.c index 5aa2dbe2bfb..cd3defb11ff 100644 --- a/drivers/net/ethernet/smsc/smsc911x.c +++ b/drivers/net/ethernet/smsc/smsc911x.c @@ -2378,7 +2378,6 @@ static int __devinit smsc911x_drv_probe(struct platform_device *pdev) SET_NETDEV_DEV(dev, &pdev->dev); pdata = netdev_priv(dev); - dev->irq = irq_res->start; irq_flags = irq_res->flags & IRQF_TRIGGER_MASK; pdata->ioaddr = ioremap_nocache(res->start, res_size); @@ -2442,7 +2441,7 @@ static int __devinit smsc911x_drv_probe(struct platform_device *pdev) if (retval) { SMSC_WARN(pdata, probe, "Unable to claim requested irq: %d", dev->irq); - goto out_free_irq; + goto out_disable_resources; } retval = register_netdev(dev); -- cgit v1.2.3-70-g09d2