75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi/*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * This file is provided under a CDDLv1 license. When using or
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * redistributing this file, you may do so under this license.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * In redistributing this file this license must be included
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * and no other modification of this header file is permitted.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * CDDL LICENSE SUMMARY
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Copyright(c) 1999 - 2009 Intel Corporation. All rights reserved.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * The contents of this file are subject to the terms of Version
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * 1.0 of the Common Development and Distribution License (the "License").
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * You should have received a copy of the License with this software.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * You can obtain a copy of the License at
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * http://www.opensolaris.org/os/licensing.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * See the License for the specific language governing permissions
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * and limitations under the License.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi/*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Use is subject to license terms of the CDDLv1.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi#include "e1000_api.h"
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define E1000_FIFO_MULTIPLIER 0x80
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define E1000_FIFO_HDR_SIZE 0x10
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define E1000_FIFO_GRANULARITY 0x10
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define E1000_FIFO_PAD_82547 0x3E0
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define E1000_ERR_FIFO_WRAP 8
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define DSP_RESET_ENABLE 0x0
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define DSP_RESET_DISABLE 0x2
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define E1000_MAX_DSP_RESETS 10
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi#define E1000_ROUNDUP(size, unit) (((size) + (unit) - 1) & ~((unit) - 1))
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi
49b7860084dbba18bc00b29413d6182197f9fe93Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi/*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * e1000_ttl_workaround_enabled_82541 - Returns current TTL workaround status
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @hw: pointer to the HW structure
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Returns the current status of the TTL workaround, as to whether the
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * workaround is enabled or disabled.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchibool
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchie1000_ttl_workaround_enabled_82541(struct e1000_hw *hw)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi{
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi struct e1000_dev_spec_82541 *dev_spec = &hw->dev_spec._82541;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi bool state = false;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi DEBUGFUNC("e1000_ttl_workaround_enabled_82541");
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if ((hw->mac.type != e1000_82541) && (hw->mac.type != e1000_82547))
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi state = dev_spec->ttl_workaround;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchiout:
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi return (state);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi}
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi/*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * e1000_fifo_workaround_82547 - Workaround for Tx fifo failure
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @hw: pointer to the HW structure
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @length: length of next outgoing frame
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Returns: E1000_ERR_FIFO_WRAP if the next packet cannot be transmitted yet
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * E1000_SUCCESS if the next packet can be transmitted
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Workaround for the 82547 Tx fifo failure.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchis32
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchie1000_fifo_workaround_82547(struct e1000_hw *hw, u16 length)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi{
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi struct e1000_dev_spec_82541 *dev_spec = &hw->dev_spec._82541;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi u32 tctl;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi s32 ret_val = E1000_SUCCESS;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi u16 fifo_pkt_len;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi DEBUGFUNC("e1000_fifo_workaround_82547");
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (hw->mac.type != e1000_82547)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Get the length as seen by the FIFO of the next real
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * packet to be transmitted.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi fifo_pkt_len = E1000_ROUNDUP(length + E1000_FIFO_HDR_SIZE,
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_FIFO_GRANULARITY);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (fifo_pkt_len <= (E1000_FIFO_PAD_82547 + E1000_FIFO_HDR_SIZE))
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if ((dev_spec->tx_fifo_head + fifo_pkt_len) <
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi (dev_spec->tx_fifo_size + E1000_FIFO_PAD_82547))
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (E1000_READ_REG(hw, E1000_TDT(0)) !=
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_READ_REG(hw, E1000_TDH(0))) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val = -E1000_ERR_FIFO_WRAP;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (E1000_READ_REG(hw, E1000_TDFT) != E1000_READ_REG(hw, E1000_TDFH)) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val = -E1000_ERR_FIFO_WRAP;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (E1000_READ_REG(hw, E1000_TDFTS) !=
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_READ_REG(hw, E1000_TDFHS)) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val = -E1000_ERR_FIFO_WRAP;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /* Disable the tx unit to avoid further pointer movement */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi tctl = E1000_READ_REG(hw, E1000_TCTL);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_WRITE_REG(hw, E1000_TCTL, tctl & ~E1000_TCTL_EN);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /* Reset the fifo pointers. */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_WRITE_REG(hw, E1000_TDFT, dev_spec->tx_fifo_start);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_WRITE_REG(hw, E1000_TDFH, dev_spec->tx_fifo_start);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_WRITE_REG(hw, E1000_TDFTS, dev_spec->tx_fifo_start);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_WRITE_REG(hw, E1000_TDFHS, dev_spec->tx_fifo_start);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /* Re-enabling tx unit */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_WRITE_REG(hw, E1000_TCTL, tctl);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_WRITE_FLUSH(hw);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->tx_fifo_head = 0;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchiout:
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi return (ret_val);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi}
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi/*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * e1000_update_tx_fifo_head - Update Tx fifo head pointer
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @hw: pointer to the HW structure
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @length: length of next outgoing frame
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Updates the SW calculated Tx FIFO head pointer.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchivoid
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchie1000_update_tx_fifo_head_82547(struct e1000_hw *hw, u32 length)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi{
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi struct e1000_dev_spec_82541 *dev_spec = &hw->dev_spec._82541;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi DEBUGFUNC("e1000_update_tx_fifo_head_82547");
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (hw->mac.type != e1000_82547)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi return;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->tx_fifo_head += E1000_ROUNDUP(length + E1000_FIFO_HDR_SIZE,
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi E1000_FIFO_GRANULARITY);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (dev_spec->tx_fifo_head > dev_spec->tx_fifo_size)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->tx_fifo_head -= dev_spec->tx_fifo_size;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi}
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi/*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * e1000_set_ttl_workaround_state_82541 - Enable/Disables TTL workaround
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @hw: pointer to the HW structure
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @state: boolean to enable/disable TTL workaround
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * For 82541 or 82547 only silicon, allows the driver to enable/disable the
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * TTL workaround.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchivoid
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchie1000_set_ttl_workaround_state_82541(struct e1000_hw *hw, bool state)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi{
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi struct e1000_dev_spec_82541 *dev_spec = &hw->dev_spec._82541;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi DEBUGFUNC("e1000_set_ttl_workaround_state_82541");
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if ((hw->mac.type != e1000_82541) && (hw->mac.type != e1000_82547))
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi return;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->ttl_workaround = state;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi}
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi/*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * e1000_igp_ttl_workaround_82547 - Workaround for long TTL on 100HD hubs
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * @hw: pointer to the HW structure
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Returns: E1000_ERR_PHY if fail to read/write the PHY
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * E1000_SUCCESS in any other case
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi *
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * This function, specific to 82547 hardware only, needs to be called every
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * second. It checks if a parallel detect fault has occurred. If a fault
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * occurred, disable/enable the DSP reset mechanism up to 5 times (once per
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * second). If link is established, stop the workaround and ensure the DSP
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * reset is enabled.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchis32
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchie1000_igp_ttl_workaround_82547(struct e1000_hw *hw)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi{
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi struct e1000_dev_spec_82541 *dev_spec = &hw->dev_spec._82541;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi s32 ret_val = E1000_SUCCESS;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi u16 phy_data = 0;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi u16 dsp_value = DSP_RESET_ENABLE;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi bool link;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi DEBUGFUNC("e1000_igp_ttl_workaround_82547");
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /* The workaround needed only for B-0 silicon HW */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if ((hw->mac.type != e1000_82541) && (hw->mac.type != e1000_82547))
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (!(e1000_ttl_workaround_enabled_82541(hw)))
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /* Check for link first */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val = e1000_phy_has_link_generic(hw, 1, 0, &link);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (ret_val)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (link) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * If link is established during the workaround,
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * the DSP mechanism must be enabled.
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (dev_spec->dsp_reset_counter) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->dsp_reset_counter = 0;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dsp_value = DSP_RESET_ENABLE;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi } else {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val = E1000_SUCCESS;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi } else {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (dev_spec->dsp_reset_counter == 0) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Workaround not activated,
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * check if it needs activation
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val = hw->phy.ops.read_reg(hw,
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi PHY_AUTONEG_EXP,
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi &phy_data);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (ret_val)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /*
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * Activate the workaround if there was a
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi * parallel detect fault
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (phy_data & NWAY_ER_PAR_DETECT_FAULT) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->dsp_reset_counter++;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi } else {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val = E1000_SUCCESS;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi goto out;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi /* After 5 times, stop the workaround */
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (dev_spec->dsp_reset_counter > E1000_MAX_DSP_RESETS) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->dsp_reset_counter = 0;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dsp_value = DSP_RESET_ENABLE;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi } else {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi if (dev_spec->dsp_reset_counter) {
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dsp_value = (dev_spec->dsp_reset_counter & 1)
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ? DSP_RESET_DISABLE
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi : DSP_RESET_ENABLE;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi dev_spec->dsp_reset_counter++;
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi }
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi ret_val =
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi hw->phy.ops.write_reg(hw, IGP01E1000_PHY_DSP_RESET, dsp_value);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchiout:
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi return (ret_val);
75eba5b6d79ed4d2ce3daf7b2806306b6b69a938Robert Mustacchi}