Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit c39904a0 authored by David S. Miller's avatar David S. Miller
Browse files


Jeff Kirsher says:

====================
This series contains updates to e1000e, igb and ixgbe.

There are 2 patches in this series which could be applied to net,
but since Linus is so very close to releasing 3.9, I do not think
it prudent to try and push these into net at this time.  I have CC'd
stable on these patches so that they can queue them up as soon as
3.9 gets released.

The 2 patches are:
  e1000e: fix numeric overflow in phc settime method
  ixgbe: fix EICR write in ixgbe_msix_other

Richard provides a fix for e1000e by using a helper function from time.h
to resolve a unintended overflow in the PTP settime function.

Bruce provides a fix to wait for NAPI to be done with the current context
after disabling interrupts and then disable NAPI when the interface
is going down.  This fixes a possible "unable to handle kernel paging
request" panic in net-next.

Andi Kleen provides a patch for igb to use mdelay instead of udelay
when we needed 100000us.

Jacob provides a fix for ixgbe to simply mask the lower 16bits off so that
ixgbe_msix_other does not write them in the EICR, which causes them to
remain high and be properly handled by the clean_rings interrupt routine
as normal.

Emil cleans up the logic in ixgbe_setup_loopback_test() to only access
registers applicable to the MAC type.  In addition, removes majority
of the AUTOC register reads by using a cached value instead to avoid
writing corrupted values to AUTOC due to bad FW.  Emil also add support
for disabling link during boot time.  Lastly, he provides a patch which
adds the MAC type to the version in ethtool_regs which will make it
easier to check the MAC type when dumping registers with ethtool.

There is a separate ethtool tool patch which is dependent upon Emil's
last patch of the series to add the MAC type to the version in
ethtool_regs, which will be sent separately.
====================

Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents b38a54ea c4a56de8
Loading
Loading
Loading
Loading
+5 −2
Original line number Diff line number Diff line
@@ -4016,6 +4016,8 @@ void e1000e_down(struct e1000_adapter *adapter)

	e1000_irq_disable(adapter);

	napi_synchronize(&adapter->napi);

	del_timer_sync(&adapter->watchdog_timer);
	del_timer_sync(&adapter->phy_info_timer);

@@ -4372,12 +4374,13 @@ static int e1000_close(struct net_device *netdev)

	pm_runtime_get_sync(&pdev->dev);

	napi_disable(&adapter->napi);

	if (!test_bit(__E1000_DOWN, &adapter->state)) {
		e1000e_down(adapter);
		e1000_free_irq(adapter);
	}

	napi_disable(&adapter->napi);

	e1000_power_down_phy(adapter);

	e1000e_free_tx_resources(adapter->tx_ring);
+1 −2
Original line number Diff line number Diff line
@@ -145,8 +145,7 @@ static int e1000e_phc_settime(struct ptp_clock_info *ptp,
	unsigned long flags;
	u64 ns;

	ns = ts->tv_sec * NSEC_PER_SEC;
	ns += ts->tv_nsec;
	ns = timespec_to_ns(ts);

	/* reset the timecounter */
	spin_lock_irqsave(&adapter->systim_lock, flags);
+3 −3
Original line number Diff line number Diff line
@@ -1130,7 +1130,7 @@ s32 igb_phy_force_speed_duplex_igp(struct e1000_hw *hw)
	if (phy->autoneg_wait_to_complete) {
		hw_dbg("Waiting for forced speed/duplex link on IGP phy.\n");

		ret_val = igb_phy_has_link(hw, PHY_FORCE_LIMIT, 100000, &link);
		ret_val = igb_phy_has_link(hw, PHY_FORCE_LIMIT, 10000, &link);
		if (ret_val)
			goto out;

@@ -1138,7 +1138,7 @@ s32 igb_phy_force_speed_duplex_igp(struct e1000_hw *hw)
			hw_dbg("Link taking longer than expected.\n");

		/* Try once more */
		ret_val = igb_phy_has_link(hw, PHY_FORCE_LIMIT, 100000, &link);
		ret_val = igb_phy_has_link(hw, PHY_FORCE_LIMIT, 10000, &link);
		if (ret_val)
			goto out;
	}
@@ -1590,7 +1590,7 @@ s32 igb_phy_has_link(struct e1000_hw *hw, u32 iterations,
		 * it across the board.
		 */
		ret_val = hw->phy.ops.read_reg(hw, PHY_STATUS, &phy_status);
		if (ret_val) {
		if (ret_val && usec_interval > 0) {
			/* If the first read fails, another entity may have
			 * ownership of the resources, wait and try again to
			 * see if they have relinquished the resources yet.
+43 −18
Original line number Diff line number Diff line
@@ -167,9 +167,9 @@ static s32 ixgbe_setup_sfp_modules_82599(struct ixgbe_hw *hw)
		}

		/* Restart DSP and set SFI mode */
		IXGBE_WRITE_REG(hw, IXGBE_AUTOC, (IXGBE_READ_REG(hw,
				IXGBE_AUTOC) | IXGBE_AUTOC_LMS_10G_SERIAL));

		IXGBE_WRITE_REG(hw, IXGBE_AUTOC, ((hw->mac.orig_autoc) |
				IXGBE_AUTOC_LMS_10G_SERIAL));
		hw->mac.cached_autoc = IXGBE_READ_REG(hw, IXGBE_AUTOC);
		ret_val = ixgbe_reset_pipeline_82599(hw);

		if (got_lock) {
@@ -803,12 +803,9 @@ static s32 ixgbe_setup_mac_link_82599(struct ixgbe_hw *hw,
				      bool autoneg_wait_to_complete)
{
	s32 status = 0;
	u32 autoc = IXGBE_READ_REG(hw, IXGBE_AUTOC);
	u32 autoc, pma_pmd_1g, link_mode, start_autoc;
	u32 autoc2 = IXGBE_READ_REG(hw, IXGBE_AUTOC2);
	u32 start_autoc = autoc;
	u32 orig_autoc = 0;
	u32 link_mode = autoc & IXGBE_AUTOC_LMS_MASK;
	u32 pma_pmd_1g = autoc & IXGBE_AUTOC_1G_PMA_PMD_MASK;
	u32 pma_pmd_10g_serial = autoc2 & IXGBE_AUTOC2_10G_SERIAL_PMA_PMD_MASK;
	u32 links_reg;
	u32 i;
@@ -831,9 +828,14 @@ static s32 ixgbe_setup_mac_link_82599(struct ixgbe_hw *hw,

	/* Use stored value (EEPROM defaults) of AUTOC to find KR/KX4 support*/
	if (hw->mac.orig_link_settings_stored)
		orig_autoc = hw->mac.orig_autoc;
		autoc = hw->mac.orig_autoc;
	else
		autoc = IXGBE_READ_REG(hw, IXGBE_AUTOC);

	orig_autoc = autoc;
	start_autoc = hw->mac.cached_autoc;
	link_mode = autoc & IXGBE_AUTOC_LMS_MASK;
	pma_pmd_1g = autoc & IXGBE_AUTOC_1G_PMA_PMD_MASK;

	if (link_mode == IXGBE_AUTOC_LMS_KX4_KX_KR ||
	    link_mode == IXGBE_AUTOC_LMS_KX4_KX_KR_1G_AN ||
@@ -887,6 +889,7 @@ static s32 ixgbe_setup_mac_link_82599(struct ixgbe_hw *hw,

		/* Restart link */
		IXGBE_WRITE_REG(hw, IXGBE_AUTOC, autoc);
		hw->mac.cached_autoc = autoc;
		ixgbe_reset_pipeline_82599(hw);

		if (got_lock)
@@ -958,7 +961,7 @@ static s32 ixgbe_reset_hw_82599(struct ixgbe_hw *hw)
{
	ixgbe_link_speed link_speed;
	s32 status;
	u32 ctrl, i, autoc, autoc2;
	u32 ctrl, i, autoc2;
	u32 curr_lms;
	bool link_up = false;

@@ -991,8 +994,12 @@ static s32 ixgbe_reset_hw_82599(struct ixgbe_hw *hw)
	if (hw->phy.reset_disable == false && hw->phy.ops.reset != NULL)
		hw->phy.ops.reset(hw);

	/* remember AUTOC LMS from before we reset */
	curr_lms = IXGBE_READ_REG(hw, IXGBE_AUTOC) & IXGBE_AUTOC_LMS_MASK;
	/* remember AUTOC from before we reset */
	if (hw->mac.cached_autoc)
		curr_lms = hw->mac.cached_autoc & IXGBE_AUTOC_LMS_MASK;
	else
		curr_lms = IXGBE_READ_REG(hw, IXGBE_AUTOC) &
			   IXGBE_AUTOC_LMS_MASK;

mac_reset_top:
	/*
@@ -1042,10 +1049,18 @@ static s32 ixgbe_reset_hw_82599(struct ixgbe_hw *hw)
	 * stored off yet.  Otherwise restore the stored original
	 * values since the reset operation sets back to defaults.
	 */
	autoc = IXGBE_READ_REG(hw, IXGBE_AUTOC);
	hw->mac.cached_autoc = IXGBE_READ_REG(hw, IXGBE_AUTOC);
	autoc2 = IXGBE_READ_REG(hw, IXGBE_AUTOC2);

	/* Enable link if disabled in NVM */
	if (autoc2 & IXGBE_AUTOC2_LINK_DISABLE_MASK) {
		autoc2 &= ~IXGBE_AUTOC2_LINK_DISABLE_MASK;
		IXGBE_WRITE_REG(hw, IXGBE_AUTOC2, autoc2);
		IXGBE_WRITE_FLUSH(hw);
	}

	if (hw->mac.orig_link_settings_stored == false) {
		hw->mac.orig_autoc = autoc;
		hw->mac.orig_autoc = hw->mac.cached_autoc;
		hw->mac.orig_autoc2 = autoc2;
		hw->mac.orig_link_settings_stored = true;
	} else {
@@ -1062,7 +1077,7 @@ static s32 ixgbe_reset_hw_82599(struct ixgbe_hw *hw)
				(hw->mac.orig_autoc & ~IXGBE_AUTOC_LMS_MASK) |
				curr_lms;

		if (autoc != hw->mac.orig_autoc) {
		if (hw->mac.cached_autoc != hw->mac.orig_autoc) {
			/* Need SW/FW semaphore around AUTOC writes if LESM is
			 * on, likewise reset_pipeline requires us to hold
			 * this lock as it also writes to AUTOC.
@@ -1078,6 +1093,7 @@ static s32 ixgbe_reset_hw_82599(struct ixgbe_hw *hw)
			}

			IXGBE_WRITE_REG(hw, IXGBE_AUTOC, hw->mac.orig_autoc);
			hw->mac.cached_autoc = hw->mac.orig_autoc;
			ixgbe_reset_pipeline_82599(hw);

			if (got_lock)
@@ -2178,10 +2194,19 @@ static s32 ixgbe_read_eeprom_82599(struct ixgbe_hw *hw,
 **/
s32 ixgbe_reset_pipeline_82599(struct ixgbe_hw *hw)
{
	s32 i, autoc_reg, ret_val;
	s32 anlp1_reg = 0;
	s32 ret_val;
	u32 anlp1_reg = 0;
	u32 i, autoc_reg, autoc2_reg;

	/* Enable link if disabled in NVM */
	autoc2_reg = IXGBE_READ_REG(hw, IXGBE_AUTOC2);
	if (autoc2_reg & IXGBE_AUTOC2_LINK_DISABLE_MASK) {
		autoc2_reg &= ~IXGBE_AUTOC2_LINK_DISABLE_MASK;
		IXGBE_WRITE_REG(hw, IXGBE_AUTOC2, autoc2_reg);
		IXGBE_WRITE_FLUSH(hw);
	}

	autoc_reg = IXGBE_READ_REG(hw, IXGBE_AUTOC);
	autoc_reg = hw->mac.cached_autoc;
	autoc_reg |= IXGBE_AUTOC_AN_RESTART;

	/* Write AUTOC register with toggled LMS[2] bit and Restart_AN */
+16 −13
Original line number Diff line number Diff line
@@ -440,7 +440,8 @@ static void ixgbe_get_regs(struct net_device *netdev,

	memset(p, 0, IXGBE_REGS_LEN * sizeof(u32));

	regs->version = (1 << 24) | hw->revision_id << 16 | hw->device_id;
	regs->version = hw->mac.type << 24 | hw->revision_id << 16 |
			hw->device_id;

	/* General Registers */
	regs_buff[0] = IXGBE_READ_REG(hw, IXGBE_CTRL);
@@ -1609,16 +1610,9 @@ static int ixgbe_setup_loopback_test(struct ixgbe_adapter *adapter)
	struct ixgbe_hw *hw = &adapter->hw;
	u32 reg_data;

	/* X540 needs to set the MACC.FLU bit to force link up */
	if (adapter->hw.mac.type == ixgbe_mac_X540) {
		reg_data = IXGBE_READ_REG(hw, IXGBE_MACC);
		reg_data |= IXGBE_MACC_FLU;
		IXGBE_WRITE_REG(hw, IXGBE_MACC, reg_data);
	}

	/* right now we only support MAC loopback in the driver */
	reg_data = IXGBE_READ_REG(hw, IXGBE_HLREG0);
	/* Setup MAC loopback */
	reg_data = IXGBE_READ_REG(hw, IXGBE_HLREG0);
	reg_data |= IXGBE_HLREG0_LPBK;
	IXGBE_WRITE_REG(hw, IXGBE_HLREG0, reg_data);

@@ -1626,10 +1620,19 @@ static int ixgbe_setup_loopback_test(struct ixgbe_adapter *adapter)
	reg_data |= IXGBE_FCTRL_BAM | IXGBE_FCTRL_SBP | IXGBE_FCTRL_MPE;
	IXGBE_WRITE_REG(hw, IXGBE_FCTRL, reg_data);

	reg_data = IXGBE_READ_REG(hw, IXGBE_AUTOC);
	reg_data &= ~IXGBE_AUTOC_LMS_MASK;
	reg_data |= IXGBE_AUTOC_LMS_10G_LINK_NO_AN | IXGBE_AUTOC_FLU;
	/* X540 needs to set the MACC.FLU bit to force link up */
	if (adapter->hw.mac.type == ixgbe_mac_X540) {
		reg_data = IXGBE_READ_REG(hw, IXGBE_MACC);
		reg_data |= IXGBE_MACC_FLU;
		IXGBE_WRITE_REG(hw, IXGBE_MACC, reg_data);
	} else {
		if (hw->mac.orig_autoc) {
			reg_data = hw->mac.orig_autoc | IXGBE_AUTOC_FLU;
			IXGBE_WRITE_REG(hw, IXGBE_AUTOC, reg_data);
		} else {
			return 10;
		}
	}
	IXGBE_WRITE_FLUSH(hw);
	usleep_range(10000, 20000);

Loading