devices/e1000e/netdev-2.6.32-ethercat.c
author Patrick Bruenn <p.bruenn@beckhoff.com>
Tue, 12 Apr 2016 11:17:36 +0200
branchstable-1.5
changeset 2654 b3f6b3e5ef29
parent 2582 87e502828b3f
permissions -rw-r--r--
devices/ccat: revert "limit rx processing to one frame per poll"

revert "limit rx processing to one frame per poll", which caused etherlab
frame timeouts in setups with more than one frame per cycle.
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     1
/*******************************************************************************
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     2
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     3
  Intel PRO/1000 Linux driver
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     4
  Copyright(c) 1999 - 2008 Intel Corporation.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     5
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     6
  This program is free software; you can redistribute it and/or modify it
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     7
  under the terms and conditions of the GNU General Public License,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     8
  version 2, as published by the Free Software Foundation.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     9
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    10
  This program is distributed in the hope it will be useful, but WITHOUT
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    11
  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    12
  FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    13
  more details.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    14
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    15
  You should have received a copy of the GNU General Public License along with
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    16
  this program; if not, write to the Free Software Foundation, Inc.,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    17
  51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    18
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    19
  The full GNU General Public License is included in this distribution in
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    20
  the file called "COPYING".
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    21
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    22
  Contact Information:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    23
  Linux NICS <linux.nics@intel.com>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    24
  e1000-devel Mailing List <e1000-devel@lists.sourceforge.net>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    25
  Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    26
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    27
*******************************************************************************/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    28
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    29
#include <linux/module.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    30
#include <linux/types.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    31
#include <linux/init.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    32
#include <linux/pci.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    33
#include <linux/vmalloc.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    34
#include <linux/pagemap.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    35
#include <linux/delay.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    36
#include <linux/netdevice.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    37
#include <linux/tcp.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    38
#include <linux/ipv6.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    39
#include <net/checksum.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    40
#include <net/ip6_checksum.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    41
#include <linux/mii.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    42
#include <linux/ethtool.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    43
#include <linux/if_vlan.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    44
#include <linux/cpu.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    45
#include <linux/smp.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    46
#include <linux/pm_qos_params.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    47
#include <linux/aer.h>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    48
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    49
#include "e1000-2.6.32-ethercat.h"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    50
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    51
#define DRV_VERSION "1.0.2-k2(ethercat)"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    52
char e1000e_driver_name[] = "ec_e1000e";
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    53
const char e1000e_driver_version[] = DRV_VERSION;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    54
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    55
static const struct e1000_info *e1000_info_tbl[] = {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    56
	[board_82571]		= &e1000_82571_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    57
	[board_82572]		= &e1000_82572_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    58
	[board_82573]		= &e1000_82573_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    59
	[board_82574]		= &e1000_82574_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    60
	[board_82583]		= &e1000_82583_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    61
	[board_80003es2lan]	= &e1000_es2_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    62
	[board_ich8lan]		= &e1000_ich8_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    63
	[board_ich9lan]		= &e1000_ich9_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    64
	[board_ich10lan]	= &e1000_ich10_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    65
	[board_pchlan]		= &e1000_pch_info,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    66
};
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    67
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    68
#ifdef DEBUG
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    69
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    70
 * e1000_get_hw_dev_name - return device name string
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    71
 * used by hardware layer to print debugging information
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    72
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    73
char *e1000e_get_hw_dev_name(struct e1000_hw *hw)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    74
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    75
	return hw->adapter->netdev->name;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    76
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    77
#endif
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    78
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    79
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    80
 * e1000_desc_unused - calculate if we have unused descriptors
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    81
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    82
static int e1000_desc_unused(struct e1000_ring *ring)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    83
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    84
	if (ring->next_to_clean > ring->next_to_use)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    85
		return ring->next_to_clean - ring->next_to_use - 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    86
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    87
	return ring->count + ring->next_to_clean - ring->next_to_use - 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    88
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    89
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    90
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    91
 * e1000_receive_skb - helper function to handle Rx indications
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    92
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    93
 * @status: descriptor status field as written by hardware
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    94
 * @vlan: descriptor vlan field as written by hardware (no le/be conversion)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    95
 * @skb: pointer to sk_buff to be indicated to stack
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    96
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    97
static void e1000_receive_skb(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    98
			      struct net_device *netdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    99
			      struct sk_buff *skb,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   100
			      u8 status, __le16 vlan)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   101
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   102
	skb->protocol = eth_type_trans(skb, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   103
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   104
	if (adapter->vlgrp && (status & E1000_RXD_STAT_VP))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   105
		vlan_gro_receive(&adapter->napi, adapter->vlgrp,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   106
				 le16_to_cpu(vlan), skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   107
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   108
		napi_gro_receive(&adapter->napi, skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   109
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   110
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   111
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   112
 * e1000_rx_checksum - Receive Checksum Offload for 82543
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   113
 * @adapter:     board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   114
 * @status_err:  receive descriptor status and error fields
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   115
 * @csum:	receive descriptor csum field
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   116
 * @sk_buff:     socket buffer with received data
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   117
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   118
static void e1000_rx_checksum(struct e1000_adapter *adapter, u32 status_err,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   119
			      u32 csum, struct sk_buff *skb)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   120
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   121
	u16 status = (u16)status_err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   122
	u8 errors = (u8)(status_err >> 24);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   123
	skb->ip_summed = CHECKSUM_NONE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   124
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   125
	/* Ignore Checksum bit is set */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   126
	if (status & E1000_RXD_STAT_IXSM)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   127
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   128
	/* TCP/UDP checksum error bit is set */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   129
	if (errors & E1000_RXD_ERR_TCPE) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   130
		/* let the stack verify checksum errors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   131
		adapter->hw_csum_err++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   132
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   133
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   134
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   135
	/* TCP/UDP Checksum has not been calculated */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   136
	if (!(status & (E1000_RXD_STAT_TCPCS | E1000_RXD_STAT_UDPCS)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   137
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   138
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   139
	/* It must be a TCP or UDP packet with a valid checksum */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   140
	if (status & E1000_RXD_STAT_TCPCS) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   141
		/* TCP checksum is good */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   142
		skb->ip_summed = CHECKSUM_UNNECESSARY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   143
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   144
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   145
		 * IP fragment with UDP payload
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   146
		 * Hardware complements the payload checksum, so we undo it
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   147
		 * and then put the value in host order for further stack use.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   148
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   149
		__sum16 sum = (__force __sum16)htons(csum);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   150
		skb->csum = csum_unfold(~sum);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   151
		skb->ip_summed = CHECKSUM_COMPLETE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   152
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   153
	adapter->hw_csum_good++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   154
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   155
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   156
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   157
 * e1000_alloc_rx_buffers - Replace used receive buffers; legacy & extended
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   158
 * @adapter: address of board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   159
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   160
static void e1000_alloc_rx_buffers(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   161
				   int cleaned_count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   162
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   163
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   164
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   165
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   166
	struct e1000_rx_desc *rx_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   167
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   168
	struct sk_buff *skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   169
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   170
	unsigned int bufsz = adapter->rx_buffer_len + NET_IP_ALIGN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   171
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   172
	i = rx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   173
	buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   174
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   175
	while (cleaned_count--) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   176
		skb = buffer_info->skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   177
		if (skb) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   178
			skb_trim(skb, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   179
			goto map_skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   180
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   181
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   182
		skb = netdev_alloc_skb(netdev, bufsz);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   183
		if (!skb) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   184
			/* Better luck next round */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   185
			adapter->alloc_rx_buff_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   186
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   187
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   188
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   189
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   190
		 * Make buffer alignment 2 beyond a 16 byte boundary
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   191
		 * this will result in a 16 byte aligned IP header after
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   192
		 * the 14 byte MAC header is removed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   193
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   194
		skb_reserve(skb, NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   195
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   196
		buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   197
map_skb:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   198
		buffer_info->dma = pci_map_single(pdev, skb->data,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   199
						  adapter->rx_buffer_len,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   200
						  PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   201
		if (pci_dma_mapping_error(pdev, buffer_info->dma)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   202
			dev_err(&pdev->dev, "RX DMA map failed\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   203
			adapter->rx_dma_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   204
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   205
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   206
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   207
		rx_desc = E1000_RX_DESC(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   208
		rx_desc->buffer_addr = cpu_to_le64(buffer_info->dma);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   209
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   210
		i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   211
		if (i == rx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   212
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   213
		buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   214
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   215
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   216
	if (rx_ring->next_to_use != i) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   217
		rx_ring->next_to_use = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   218
		if (i-- == 0)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   219
			i = (rx_ring->count - 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   220
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   221
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   222
		 * Force memory writes to complete before letting h/w
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   223
		 * know there are new descriptors to fetch.  (Only
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   224
		 * applicable for weak-ordered memory model archs,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   225
		 * such as IA-64).
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   226
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   227
		wmb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   228
		writel(i, adapter->hw.hw_addr + rx_ring->tail);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   229
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   230
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   231
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   232
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   233
 * e1000_alloc_rx_buffers_ps - Replace used receive buffers; packet split
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   234
 * @adapter: address of board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   235
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   236
static void e1000_alloc_rx_buffers_ps(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   237
				      int cleaned_count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   238
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   239
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   240
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   241
	union e1000_rx_desc_packet_split *rx_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   242
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   243
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   244
	struct e1000_ps_page *ps_page;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   245
	struct sk_buff *skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   246
	unsigned int i, j;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   247
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   248
	i = rx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   249
	buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   250
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   251
	while (cleaned_count--) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   252
		rx_desc = E1000_RX_DESC_PS(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   253
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   254
		for (j = 0; j < PS_PAGE_BUFFERS; j++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   255
			ps_page = &buffer_info->ps_pages[j];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   256
			if (j >= adapter->rx_ps_pages) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   257
				/* all unused desc entries get hw null ptr */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   258
				rx_desc->read.buffer_addr[j+1] = ~cpu_to_le64(0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   259
				continue;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   260
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   261
			if (!ps_page->page) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   262
				ps_page->page = alloc_page(GFP_ATOMIC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   263
				if (!ps_page->page) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   264
					adapter->alloc_rx_buff_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   265
					goto no_buffers;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   266
				}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   267
				ps_page->dma = pci_map_page(pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   268
						   ps_page->page,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   269
						   0, PAGE_SIZE,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   270
						   PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   271
				if (pci_dma_mapping_error(pdev, ps_page->dma)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   272
					dev_err(&adapter->pdev->dev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   273
					  "RX DMA page map failed\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   274
					adapter->rx_dma_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   275
					goto no_buffers;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   276
				}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   277
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   278
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   279
			 * Refresh the desc even if buffer_addrs
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   280
			 * didn't change because each write-back
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   281
			 * erases this info.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   282
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   283
			rx_desc->read.buffer_addr[j+1] =
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   284
			     cpu_to_le64(ps_page->dma);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   285
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   286
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   287
		skb = netdev_alloc_skb(netdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   288
				       adapter->rx_ps_bsize0 + NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   289
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   290
		if (!skb) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   291
			adapter->alloc_rx_buff_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   292
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   293
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   294
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   295
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   296
		 * Make buffer alignment 2 beyond a 16 byte boundary
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   297
		 * this will result in a 16 byte aligned IP header after
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   298
		 * the 14 byte MAC header is removed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   299
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   300
		skb_reserve(skb, NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   301
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   302
		buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   303
		buffer_info->dma = pci_map_single(pdev, skb->data,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   304
						  adapter->rx_ps_bsize0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   305
						  PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   306
		if (pci_dma_mapping_error(pdev, buffer_info->dma)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   307
			dev_err(&pdev->dev, "RX DMA map failed\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   308
			adapter->rx_dma_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   309
			/* cleanup skb */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   310
			dev_kfree_skb_any(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   311
			buffer_info->skb = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   312
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   313
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   314
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   315
		rx_desc->read.buffer_addr[0] = cpu_to_le64(buffer_info->dma);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   316
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   317
		i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   318
		if (i == rx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   319
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   320
		buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   321
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   322
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   323
no_buffers:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   324
	if (rx_ring->next_to_use != i) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   325
		rx_ring->next_to_use = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   326
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   327
		if (!(i--))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   328
			i = (rx_ring->count - 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   329
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   330
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   331
		 * Force memory writes to complete before letting h/w
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   332
		 * know there are new descriptors to fetch.  (Only
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   333
		 * applicable for weak-ordered memory model archs,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   334
		 * such as IA-64).
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   335
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   336
		wmb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   337
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   338
		 * Hardware increments by 16 bytes, but packet split
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   339
		 * descriptors are 32 bytes...so we increment tail
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   340
		 * twice as much.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   341
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   342
		writel(i<<1, adapter->hw.hw_addr + rx_ring->tail);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   343
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   344
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   345
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   346
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   347
 * e1000_alloc_jumbo_rx_buffers - Replace used jumbo receive buffers
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   348
 * @adapter: address of board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   349
 * @cleaned_count: number of buffers to allocate this pass
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   350
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   351
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   352
static void e1000_alloc_jumbo_rx_buffers(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   353
                                         int cleaned_count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   354
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   355
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   356
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   357
	struct e1000_rx_desc *rx_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   358
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   359
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   360
	struct sk_buff *skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   361
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   362
	unsigned int bufsz = 256 -
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   363
	                     16 /* for skb_reserve */ -
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   364
	                     NET_IP_ALIGN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   365
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   366
	i = rx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   367
	buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   368
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   369
	while (cleaned_count--) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   370
		skb = buffer_info->skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   371
		if (skb) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   372
			skb_trim(skb, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   373
			goto check_page;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   374
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   375
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   376
		skb = netdev_alloc_skb(netdev, bufsz);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   377
		if (unlikely(!skb)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   378
			/* Better luck next round */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   379
			adapter->alloc_rx_buff_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   380
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   381
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   382
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   383
		/* Make buffer alignment 2 beyond a 16 byte boundary
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   384
		 * this will result in a 16 byte aligned IP header after
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   385
		 * the 14 byte MAC header is removed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   386
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   387
		skb_reserve(skb, NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   388
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   389
		buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   390
check_page:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   391
		/* allocate a new page if necessary */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   392
		if (!buffer_info->page) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   393
			buffer_info->page = alloc_page(GFP_ATOMIC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   394
			if (unlikely(!buffer_info->page)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   395
				adapter->alloc_rx_buff_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   396
				break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   397
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   398
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   399
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   400
		if (!buffer_info->dma)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   401
			buffer_info->dma = pci_map_page(pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   402
			                                buffer_info->page, 0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   403
			                                PAGE_SIZE,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   404
			                                PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   405
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   406
		rx_desc = E1000_RX_DESC(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   407
		rx_desc->buffer_addr = cpu_to_le64(buffer_info->dma);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   408
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   409
		if (unlikely(++i == rx_ring->count))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   410
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   411
		buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   412
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   413
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   414
	if (likely(rx_ring->next_to_use != i)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   415
		rx_ring->next_to_use = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   416
		if (unlikely(i-- == 0))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   417
			i = (rx_ring->count - 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   418
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   419
		/* Force memory writes to complete before letting h/w
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   420
		 * know there are new descriptors to fetch.  (Only
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   421
		 * applicable for weak-ordered memory model archs,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   422
		 * such as IA-64). */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   423
		wmb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   424
		writel(i, adapter->hw.hw_addr + rx_ring->tail);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   425
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   426
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   427
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   428
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   429
 * e1000_clean_rx_irq - Send received data up the network stack; legacy
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   430
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   431
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   432
 * the return value indicates whether actual cleaning was done, there
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   433
 * is no guarantee that everything was cleaned
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   434
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   435
static bool e1000_clean_rx_irq(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   436
			       int *work_done, int work_to_do)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   437
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   438
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   439
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   440
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   441
	struct e1000_rx_desc *rx_desc, *next_rxd;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   442
	struct e1000_buffer *buffer_info, *next_buffer;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   443
	u32 length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   444
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   445
	int cleaned_count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   446
	bool cleaned = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   447
	unsigned int total_rx_bytes = 0, total_rx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   448
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   449
	i = rx_ring->next_to_clean;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   450
	rx_desc = E1000_RX_DESC(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   451
	buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   452
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   453
	while (rx_desc->status & E1000_RXD_STAT_DD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   454
		struct sk_buff *skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   455
		u8 status;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   456
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   457
		if (*work_done >= work_to_do)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   458
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   459
		(*work_done)++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   460
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   461
		status = rx_desc->status;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   462
		skb = buffer_info->skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   463
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   464
		if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   465
			buffer_info->skb = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   466
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   467
		prefetch(skb->data - NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   468
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   469
		i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   470
		if (i == rx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   471
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   472
		next_rxd = E1000_RX_DESC(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   473
		prefetch(next_rxd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   474
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   475
		next_buffer = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   476
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   477
		cleaned = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   478
		cleaned_count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   479
		pci_unmap_single(pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   480
				 buffer_info->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   481
				 adapter->rx_buffer_len,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   482
				 PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   483
		buffer_info->dma = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   484
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   485
		length = le16_to_cpu(rx_desc->length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   486
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   487
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   488
		 * !EOP means multiple descriptors were used to store a single
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   489
		 * packet, if that's the case we need to toss it.  In fact, we
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   490
		 * need to toss every packet with the EOP bit clear and the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   491
		 * next frame that _does_ have the EOP bit set, as it is by
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   492
		 * definition only a frame fragment
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   493
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   494
		if (unlikely(!(status & E1000_RXD_STAT_EOP)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   495
			adapter->flags2 |= FLAG2_IS_DISCARDING;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   496
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   497
		if (adapter->flags2 & FLAG2_IS_DISCARDING) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   498
			/* All receives must fit into a single buffer */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   499
			e_dbg("%s: Receive packet consumed multiple buffers\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   500
			      netdev->name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   501
			/* recycle */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   502
			buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   503
			if (status & E1000_RXD_STAT_EOP)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   504
				adapter->flags2 &= ~FLAG2_IS_DISCARDING;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   505
			goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   506
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   507
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   508
		if (!adapter->ecdev && (rx_desc->errors & E1000_RXD_ERR_FRAME_ERR_MASK)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   509
			/* recycle */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   510
			buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   511
			goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   512
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   513
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   514
		/* adjust length to remove Ethernet CRC */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   515
		if (!(adapter->flags2 & FLAG2_CRC_STRIPPING))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   516
			length -= 4;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   517
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   518
		total_rx_bytes += length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   519
		total_rx_packets++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   520
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   521
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   522
		 * code added for copybreak, this should improve
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   523
		 * performance for small packets with large amounts
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   524
		 * of reassembly being done in the stack
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   525
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   526
		if (!adapter->ecdev && length < copybreak) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   527
			struct sk_buff *new_skb =
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   528
			    netdev_alloc_skb(netdev, length + NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   529
			if (new_skb) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   530
				skb_reserve(new_skb, NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   531
				skb_copy_to_linear_data_offset(new_skb,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   532
							       -NET_IP_ALIGN,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   533
							       (skb->data -
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   534
								NET_IP_ALIGN),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   535
							       (length +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   536
								NET_IP_ALIGN));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   537
				/* save the skb in buffer_info as good */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   538
				buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   539
				skb = new_skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   540
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   541
			/* else just continue with the old one */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   542
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   543
		/* end copybreak code */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   544
		skb_put(skb, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   545
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   546
		/* Receive Checksum Offload */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   547
		e1000_rx_checksum(adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   548
				  (u32)(status) |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   549
				  ((u32)(rx_desc->errors) << 24),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   550
				  le16_to_cpu(rx_desc->csum), skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   551
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   552
		if (adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   553
			ecdev_receive(adapter->ecdev, skb->data, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   554
			adapter->ec_watchdog_jiffies = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   555
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   556
			e1000_receive_skb(adapter, netdev, skb,status,rx_desc->special);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   557
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   558
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   559
next_desc:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   560
		rx_desc->status = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   561
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   562
		/* return some buffers to hardware, one at a time is too slow */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   563
		if (cleaned_count >= E1000_RX_BUFFER_WRITE) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   564
			adapter->alloc_rx_buf(adapter, cleaned_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   565
			cleaned_count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   566
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   567
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   568
		/* use prefetched values */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   569
		rx_desc = next_rxd;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   570
		buffer_info = next_buffer;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   571
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   572
	rx_ring->next_to_clean = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   573
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   574
	cleaned_count = e1000_desc_unused(rx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   575
	if (cleaned_count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   576
		adapter->alloc_rx_buf(adapter, cleaned_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   577
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   578
	adapter->total_rx_bytes += total_rx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   579
	adapter->total_rx_packets += total_rx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   580
	adapter->net_stats.rx_bytes += total_rx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   581
	adapter->net_stats.rx_packets += total_rx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   582
	return cleaned;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   583
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   584
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   585
static void e1000_put_txbuf(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   586
			     struct e1000_buffer *buffer_info)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   587
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   588
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   589
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   590
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   591
	buffer_info->dma = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   592
	if (buffer_info->skb) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   593
		skb_dma_unmap(&adapter->pdev->dev, buffer_info->skb,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   594
		              DMA_TO_DEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   595
		dev_kfree_skb_any(buffer_info->skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   596
		buffer_info->skb = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   597
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   598
	buffer_info->time_stamp = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   599
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   600
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   601
static void e1000_print_tx_hang(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   602
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   603
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   604
	unsigned int i = tx_ring->next_to_clean;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   605
	unsigned int eop = tx_ring->buffer_info[i].next_to_watch;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   606
	struct e1000_tx_desc *eop_desc = E1000_TX_DESC(*tx_ring, eop);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   607
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   608
	/* detected Tx unit hang */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   609
	e_err("Detected Tx Unit Hang:\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   610
	      "  TDH                  <%x>\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   611
	      "  TDT                  <%x>\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   612
	      "  next_to_use          <%x>\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   613
	      "  next_to_clean        <%x>\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   614
	      "buffer_info[next_to_clean]:\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   615
	      "  time_stamp           <%lx>\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   616
	      "  next_to_watch        <%x>\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   617
	      "  jiffies              <%lx>\n"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   618
	      "  next_to_watch.status <%x>\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   619
	      readl(adapter->hw.hw_addr + tx_ring->head),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   620
	      readl(adapter->hw.hw_addr + tx_ring->tail),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   621
	      tx_ring->next_to_use,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   622
	      tx_ring->next_to_clean,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   623
	      tx_ring->buffer_info[eop].time_stamp,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   624
	      eop,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   625
	      jiffies,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   626
	      eop_desc->upper.fields.status);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   627
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   628
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   629
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   630
 * e1000_clean_tx_irq - Reclaim resources after transmit completes
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   631
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   632
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   633
 * the return value indicates whether actual cleaning was done, there
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   634
 * is no guarantee that everything was cleaned
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   635
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   636
static bool e1000_clean_tx_irq(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   637
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   638
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   639
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   640
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   641
	struct e1000_tx_desc *tx_desc, *eop_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   642
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   643
	unsigned int i, eop;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   644
	unsigned int count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   645
	unsigned int total_tx_bytes = 0, total_tx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   646
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   647
	i = tx_ring->next_to_clean;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   648
	eop = tx_ring->buffer_info[i].next_to_watch;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   649
	eop_desc = E1000_TX_DESC(*tx_ring, eop);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   650
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   651
	while ((eop_desc->upper.data & cpu_to_le32(E1000_TXD_STAT_DD)) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   652
	       (count < tx_ring->count)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   653
		bool cleaned = false;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   654
		for (; !cleaned; count++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   655
			tx_desc = E1000_TX_DESC(*tx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   656
			buffer_info = &tx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   657
			cleaned = (i == eop);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   658
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   659
			if (cleaned) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   660
				struct sk_buff *skb = buffer_info->skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   661
				unsigned int segs, bytecount;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   662
				segs = skb_shinfo(skb)->gso_segs ?: 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   663
				/* multiply data chunks by size of headers */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   664
				bytecount = ((segs - 1) * skb_headlen(skb)) +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   665
					    skb->len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   666
				total_tx_packets += segs;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   667
				total_tx_bytes += bytecount;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   668
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   669
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   670
			e1000_put_txbuf(adapter, buffer_info);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   671
			tx_desc->upper.data = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   672
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   673
			i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   674
			if (i == tx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   675
				i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   676
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   677
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   678
		eop = tx_ring->buffer_info[i].next_to_watch;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   679
		eop_desc = E1000_TX_DESC(*tx_ring, eop);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   680
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   681
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   682
	tx_ring->next_to_clean = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   683
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   684
#define TX_WAKE_THRESHOLD 32
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   685
	if (!adapter->ecdev && count && netif_carrier_ok(netdev) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   686
	    e1000_desc_unused(tx_ring) >= TX_WAKE_THRESHOLD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   687
		/* Make sure that anybody stopping the queue after this
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   688
		 * sees the new next_to_clean.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   689
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   690
		smp_mb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   691
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   692
		if (netif_queue_stopped(netdev) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   693
		    !(test_bit(__E1000_DOWN, &adapter->state))) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   694
			netif_wake_queue(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   695
			++adapter->restart_queue;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   696
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   697
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   698
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   699
	if (!adapter->ecdev && adapter->detect_tx_hung) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   700
		/* Detect a transmit hang in hardware, this serializes the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   701
		 * check with the clearing of time_stamp and movement of i */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   702
		adapter->detect_tx_hung = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   703
		if (tx_ring->buffer_info[i].time_stamp &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   704
		    time_after(jiffies, tx_ring->buffer_info[i].time_stamp
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   705
			       + (adapter->tx_timeout_factor * HZ))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   706
		    && !(er32(STATUS) & E1000_STATUS_TXOFF)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   707
			e1000_print_tx_hang(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   708
			netif_stop_queue(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   709
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   710
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   711
	adapter->total_tx_bytes += total_tx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   712
	adapter->total_tx_packets += total_tx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   713
	adapter->net_stats.tx_bytes += total_tx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   714
	adapter->net_stats.tx_packets += total_tx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   715
	return (count < tx_ring->count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   716
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   717
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   718
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   719
 * e1000_clean_rx_irq_ps - Send received data up the network stack; packet split
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   720
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   721
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   722
 * the return value indicates whether actual cleaning was done, there
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   723
 * is no guarantee that everything was cleaned
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   724
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   725
static bool e1000_clean_rx_irq_ps(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   726
				  int *work_done, int work_to_do)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   727
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   728
	union e1000_rx_desc_packet_split *rx_desc, *next_rxd;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   729
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   730
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   731
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   732
	struct e1000_buffer *buffer_info, *next_buffer;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   733
	struct e1000_ps_page *ps_page;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   734
	struct sk_buff *skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   735
	unsigned int i, j;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   736
	u32 length, staterr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   737
	int cleaned_count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   738
	bool cleaned = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   739
	unsigned int total_rx_bytes = 0, total_rx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   740
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   741
	i = rx_ring->next_to_clean;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   742
	rx_desc = E1000_RX_DESC_PS(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   743
	staterr = le32_to_cpu(rx_desc->wb.middle.status_error);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   744
	buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   745
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   746
	while (staterr & E1000_RXD_STAT_DD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   747
		if (*work_done >= work_to_do)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   748
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   749
		(*work_done)++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   750
		skb = buffer_info->skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   751
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   752
		/* in the packet split case this is header only */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   753
		prefetch(skb->data - NET_IP_ALIGN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   754
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   755
		i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   756
		if (i == rx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   757
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   758
		next_rxd = E1000_RX_DESC_PS(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   759
		prefetch(next_rxd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   760
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   761
		next_buffer = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   762
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   763
		cleaned = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   764
		cleaned_count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   765
		pci_unmap_single(pdev, buffer_info->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   766
				 adapter->rx_ps_bsize0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   767
				 PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   768
		buffer_info->dma = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   769
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   770
		/* see !EOP comment in other rx routine */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   771
		if (!(staterr & E1000_RXD_STAT_EOP))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   772
			adapter->flags2 |= FLAG2_IS_DISCARDING;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   773
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   774
		if (adapter->flags2 & FLAG2_IS_DISCARDING) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   775
			e_dbg("%s: Packet Split buffers didn't pick up the "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   776
			      "full packet\n", netdev->name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   777
			if (!adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   778
				dev_kfree_skb_irq(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   779
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   780
			if (staterr & E1000_RXD_STAT_EOP)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   781
				adapter->flags2 &= ~FLAG2_IS_DISCARDING;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   782
			goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   783
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   784
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   785
		if (staterr & E1000_RXDEXT_ERR_FRAME_ERR_MASK) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   786
			if (!adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   787
				dev_kfree_skb_irq(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   788
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   789
			goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   790
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   791
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   792
		length = le16_to_cpu(rx_desc->wb.middle.length0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   793
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   794
		if (!length) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   795
			e_dbg("%s: Last part of the packet spanning multiple "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   796
			      "descriptors\n", netdev->name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   797
			if (!adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   798
				dev_kfree_skb_irq(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   799
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   800
			goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   801
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   802
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   803
		/* Good Receive */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   804
		skb_put(skb, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   805
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   806
		{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   807
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   808
		 * this looks ugly, but it seems compiler issues make it
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   809
		 * more efficient than reusing j
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   810
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   811
		int l1 = le16_to_cpu(rx_desc->wb.upper.length[0]);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   812
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   813
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   814
		 * page alloc/put takes too long and effects small packet
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   815
		 * throughput, so unsplit small packets and save the alloc/put
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   816
		 * only valid in softirq (napi) context to call kmap_*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   817
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   818
		if (l1 && (l1 <= copybreak) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   819
		    ((length + l1) <= adapter->rx_ps_bsize0)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   820
			u8 *vaddr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   821
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   822
			ps_page = &buffer_info->ps_pages[0];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   823
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   824
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   825
			 * there is no documentation about how to call
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   826
			 * kmap_atomic, so we can't hold the mapping
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   827
			 * very long
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   828
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   829
			pci_dma_sync_single_for_cpu(pdev, ps_page->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   830
				PAGE_SIZE, PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   831
			vaddr = kmap_atomic(ps_page->page, KM_SKB_DATA_SOFTIRQ);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   832
			memcpy(skb_tail_pointer(skb), vaddr, l1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   833
			kunmap_atomic(vaddr, KM_SKB_DATA_SOFTIRQ);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   834
			pci_dma_sync_single_for_device(pdev, ps_page->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   835
				PAGE_SIZE, PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   836
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   837
			/* remove the CRC */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   838
			if (!(adapter->flags2 & FLAG2_CRC_STRIPPING))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   839
				l1 -= 4;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   840
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   841
			skb_put(skb, l1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   842
			goto copydone;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   843
		} /* if */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   844
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   845
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   846
		for (j = 0; j < PS_PAGE_BUFFERS; j++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   847
			length = le16_to_cpu(rx_desc->wb.upper.length[j]);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   848
			if (!length)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   849
				break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   850
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   851
			ps_page = &buffer_info->ps_pages[j];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   852
			pci_unmap_page(pdev, ps_page->dma, PAGE_SIZE,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   853
				       PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   854
			ps_page->dma = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   855
			skb_fill_page_desc(skb, j, ps_page->page, 0, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   856
			ps_page->page = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   857
			skb->len += length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   858
			skb->data_len += length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   859
			skb->truesize += length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   860
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   861
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   862
		/* strip the ethernet crc, problem is we're using pages now so
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   863
		 * this whole operation can get a little cpu intensive
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   864
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   865
		if (!(adapter->flags2 & FLAG2_CRC_STRIPPING))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   866
			pskb_trim(skb, skb->len - 4);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   867
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   868
copydone:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   869
		total_rx_bytes += skb->len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   870
		total_rx_packets++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   871
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   872
		e1000_rx_checksum(adapter, staterr, le16_to_cpu(
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   873
			rx_desc->wb.lower.hi_dword.csum_ip.csum), skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   874
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   875
		if (rx_desc->wb.upper.header_status &
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   876
			   cpu_to_le16(E1000_RXDPS_HDRSTAT_HDRSP))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   877
			adapter->rx_hdr_split++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   878
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   879
		if (adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   880
			ecdev_receive(adapter->ecdev, skb->data, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   881
			adapter->ec_watchdog_jiffies = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   882
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   883
			e1000_receive_skb(adapter, netdev, skb,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   884
					  staterr, rx_desc->wb.middle.vlan);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   885
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   886
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   887
next_desc:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   888
		rx_desc->wb.middle.status_error &= cpu_to_le32(~0xFF);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   889
		if (!adapter->ecdev) buffer_info->skb = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   890
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   891
		/* return some buffers to hardware, one at a time is too slow */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   892
		if (cleaned_count >= E1000_RX_BUFFER_WRITE) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   893
			adapter->alloc_rx_buf(adapter, cleaned_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   894
			cleaned_count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   895
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   896
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   897
		/* use prefetched values */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   898
		rx_desc = next_rxd;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   899
		buffer_info = next_buffer;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   900
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   901
		staterr = le32_to_cpu(rx_desc->wb.middle.status_error);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   902
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   903
	rx_ring->next_to_clean = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   904
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   905
	cleaned_count = e1000_desc_unused(rx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   906
	if (cleaned_count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   907
		adapter->alloc_rx_buf(adapter, cleaned_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   908
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   909
	adapter->total_rx_bytes += total_rx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   910
	adapter->total_rx_packets += total_rx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   911
	adapter->net_stats.rx_bytes += total_rx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   912
	adapter->net_stats.rx_packets += total_rx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   913
	return cleaned;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   914
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   915
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   916
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   917
 * e1000_consume_page - helper function
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   918
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   919
static void e1000_consume_page(struct e1000_buffer *bi, struct sk_buff *skb,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   920
                               u16 length)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   921
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   922
	bi->page = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   923
	skb->len += length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   924
	skb->data_len += length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   925
	skb->truesize += length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   926
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   927
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   928
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   929
 * e1000_clean_jumbo_rx_irq - Send received data up the network stack; legacy
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   930
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   931
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   932
 * the return value indicates whether actual cleaning was done, there
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   933
 * is no guarantee that everything was cleaned
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   934
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   935
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   936
static bool e1000_clean_jumbo_rx_irq(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   937
                                     int *work_done, int work_to_do)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   938
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   939
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   940
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   941
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   942
	struct e1000_rx_desc *rx_desc, *next_rxd;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   943
	struct e1000_buffer *buffer_info, *next_buffer;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   944
	u32 length;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   945
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   946
	int cleaned_count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   947
	bool cleaned = false;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   948
	unsigned int total_rx_bytes=0, total_rx_packets=0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   949
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   950
	i = rx_ring->next_to_clean;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   951
	rx_desc = E1000_RX_DESC(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   952
	buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   953
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   954
	while (rx_desc->status & E1000_RXD_STAT_DD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   955
		struct sk_buff *skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   956
		u8 status;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   957
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   958
		if (*work_done >= work_to_do)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   959
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   960
		(*work_done)++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   961
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   962
		status = rx_desc->status;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   963
		skb = buffer_info->skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   964
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   965
		if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   966
			buffer_info->skb = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   967
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   968
		++i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   969
		if (i == rx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   970
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   971
		next_rxd = E1000_RX_DESC(*rx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   972
		prefetch(next_rxd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   973
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   974
		next_buffer = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   975
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   976
		cleaned = true;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   977
		cleaned_count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   978
		pci_unmap_page(pdev, buffer_info->dma, PAGE_SIZE,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   979
		               PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   980
		buffer_info->dma = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   981
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   982
		length = le16_to_cpu(rx_desc->length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   983
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   984
		/* errors is only valid for DD + EOP descriptors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   985
		if (!adapter->ecdev && unlikely((status & E1000_RXD_STAT_EOP) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   986
		    (rx_desc->errors & E1000_RXD_ERR_FRAME_ERR_MASK))) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   987
				/* recycle both page and skb */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   988
				buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   989
				/* an error means any chain goes out the window
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   990
				 * too */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   991
				if (rx_ring->rx_skb_top)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   992
					dev_kfree_skb(rx_ring->rx_skb_top);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   993
				rx_ring->rx_skb_top = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   994
				goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   995
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   996
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   997
#define rxtop rx_ring->rx_skb_top
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   998
		if (!(status & E1000_RXD_STAT_EOP)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   999
			/* this descriptor is only the beginning (or middle) */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1000
			if (!rxtop) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1001
				/* this is the beginning of a chain */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1002
				rxtop = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1003
				skb_fill_page_desc(rxtop, 0, buffer_info->page,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1004
				                   0, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1005
			} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1006
				/* this is the middle of a chain */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1007
				skb_fill_page_desc(rxtop,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1008
				    skb_shinfo(rxtop)->nr_frags,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1009
				    buffer_info->page, 0, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1010
				/* re-use the skb, only consumed the page */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1011
				buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1012
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1013
			e1000_consume_page(buffer_info, rxtop, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1014
			goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1015
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1016
			if (rxtop) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1017
				/* end of the chain */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1018
				skb_fill_page_desc(rxtop,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1019
				    skb_shinfo(rxtop)->nr_frags,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1020
				    buffer_info->page, 0, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1021
				/* re-use the current skb, we only consumed the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1022
				 * page */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1023
				buffer_info->skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1024
				skb = rxtop;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1025
				rxtop = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1026
				e1000_consume_page(buffer_info, skb, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1027
			} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1028
				/* no chain, got EOP, this buf is the packet
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1029
				 * copybreak to save the put_page/alloc_page */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1030
				if (length <= copybreak &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1031
				    skb_tailroom(skb) >= length) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1032
					u8 *vaddr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1033
					vaddr = kmap_atomic(buffer_info->page,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1034
					                   KM_SKB_DATA_SOFTIRQ);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1035
					memcpy(skb_tail_pointer(skb), vaddr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1036
					       length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1037
					kunmap_atomic(vaddr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1038
					              KM_SKB_DATA_SOFTIRQ);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1039
					/* re-use the page, so don't erase
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1040
					 * buffer_info->page */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1041
					skb_put(skb, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1042
				} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1043
					skb_fill_page_desc(skb, 0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1044
					                   buffer_info->page, 0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1045
				                           length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1046
					e1000_consume_page(buffer_info, skb,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1047
					                   length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1048
				}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1049
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1050
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1051
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1052
		/* Receive Checksum Offload XXX recompute due to CRC strip? */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1053
		e1000_rx_checksum(adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1054
		                  (u32)(status) |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1055
		                  ((u32)(rx_desc->errors) << 24),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1056
		                  le16_to_cpu(rx_desc->csum), skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1057
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1058
		/* probably a little skewed due to removing CRC */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1059
		total_rx_bytes += skb->len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1060
		total_rx_packets++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1061
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1062
		/* eth type trans needs skb->data to point to something */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1063
		if (!adapter->ecdev && !pskb_may_pull(skb, ETH_HLEN)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1064
			e_err("pskb_may_pull failed.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1065
			dev_kfree_skb(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1066
			goto next_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1067
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1068
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1069
		if (adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1070
			ecdev_receive(adapter->ecdev, skb->data, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1071
			adapter->ec_watchdog_jiffies = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1072
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1073
			e1000_receive_skb(adapter, netdev, skb, status,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1074
			                  rx_desc->special);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1075
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1076
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1077
next_desc:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1078
		rx_desc->status = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1079
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1080
		/* return some buffers to hardware, one at a time is too slow */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1081
		if (unlikely(cleaned_count >= E1000_RX_BUFFER_WRITE)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1082
			adapter->alloc_rx_buf(adapter, cleaned_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1083
			cleaned_count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1084
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1085
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1086
		/* use prefetched values */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1087
		rx_desc = next_rxd;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1088
		buffer_info = next_buffer;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1089
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1090
	rx_ring->next_to_clean = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1091
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1092
	cleaned_count = e1000_desc_unused(rx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1093
	if (cleaned_count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1094
		adapter->alloc_rx_buf(adapter, cleaned_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1095
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1096
	adapter->total_rx_bytes += total_rx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1097
	adapter->total_rx_packets += total_rx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1098
	adapter->net_stats.rx_bytes += total_rx_bytes;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1099
	adapter->net_stats.rx_packets += total_rx_packets;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1100
	return cleaned;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1101
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1102
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1103
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1104
 * e1000_clean_rx_ring - Free Rx Buffers per Queue
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1105
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1106
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1107
static void e1000_clean_rx_ring(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1108
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1109
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1110
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1111
	struct e1000_ps_page *ps_page;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1112
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1113
	unsigned int i, j;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1114
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1115
	/* Free all the Rx ring sk_buffs */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1116
	for (i = 0; i < rx_ring->count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1117
		buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1118
		if (buffer_info->dma) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1119
			if (adapter->clean_rx == e1000_clean_rx_irq)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1120
				pci_unmap_single(pdev, buffer_info->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1121
						 adapter->rx_buffer_len,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1122
						 PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1123
			else if (adapter->clean_rx == e1000_clean_jumbo_rx_irq)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1124
				pci_unmap_page(pdev, buffer_info->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1125
				               PAGE_SIZE,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1126
				               PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1127
			else if (adapter->clean_rx == e1000_clean_rx_irq_ps)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1128
				pci_unmap_single(pdev, buffer_info->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1129
						 adapter->rx_ps_bsize0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1130
						 PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1131
			buffer_info->dma = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1132
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1133
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1134
		if (buffer_info->page) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1135
			put_page(buffer_info->page);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1136
			buffer_info->page = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1137
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1138
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1139
		if (buffer_info->skb) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1140
			dev_kfree_skb(buffer_info->skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1141
			buffer_info->skb = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1142
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1143
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1144
		for (j = 0; j < PS_PAGE_BUFFERS; j++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1145
			ps_page = &buffer_info->ps_pages[j];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1146
			if (!ps_page->page)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1147
				break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1148
			pci_unmap_page(pdev, ps_page->dma, PAGE_SIZE,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1149
				       PCI_DMA_FROMDEVICE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1150
			ps_page->dma = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1151
			put_page(ps_page->page);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1152
			ps_page->page = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1153
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1154
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1155
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1156
	/* there also may be some cached data from a chained receive */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1157
	if (rx_ring->rx_skb_top) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1158
		dev_kfree_skb(rx_ring->rx_skb_top);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1159
		rx_ring->rx_skb_top = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1160
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1161
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1162
	/* Zero out the descriptor ring */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1163
	memset(rx_ring->desc, 0, rx_ring->size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1164
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1165
	rx_ring->next_to_clean = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1166
	rx_ring->next_to_use = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1167
	adapter->flags2 &= ~FLAG2_IS_DISCARDING;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1168
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1169
	writel(0, adapter->hw.hw_addr + rx_ring->head);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1170
	writel(0, adapter->hw.hw_addr + rx_ring->tail);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1171
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1172
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1173
static void e1000e_downshift_workaround(struct work_struct *work)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1174
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1175
	struct e1000_adapter *adapter = container_of(work,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1176
					struct e1000_adapter, downshift_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1177
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1178
	e1000e_gig_downshift_workaround_ich8lan(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1179
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1180
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1181
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1182
 * e1000_intr_msi - Interrupt Handler
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1183
 * @irq: interrupt number
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1184
 * @data: pointer to a network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1185
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1186
static irqreturn_t e1000_intr_msi(int irq, void *data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1187
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1188
	struct net_device *netdev = data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1189
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1190
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1191
	u32 icr = er32(ICR);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1192
2473
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1193
	if (adapter->ecdev) {
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1194
		int ec_work_done = 0;
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1195
		adapter->clean_rx(adapter, &ec_work_done, 100);
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1196
		e1000_clean_tx_irq(adapter);
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1197
		return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1198
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1199
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1200
	 * read ICR disables interrupts using IAM
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1201
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1202
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1203
	if (icr & E1000_ICR_LSC) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1204
		hw->mac.get_link_status = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1205
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1206
		 * ICH8 workaround-- Call gig speed drop workaround on cable
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1207
		 * disconnect (LSC) before accessing any PHY registers
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1208
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1209
		if ((adapter->flags & FLAG_LSC_GIG_SPEED_DROP) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1210
		    (!(er32(STATUS) & E1000_STATUS_LU)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1211
			schedule_work(&adapter->downshift_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1212
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1213
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1214
		 * 80003ES2LAN workaround-- For packet buffer work-around on
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1215
		 * link down event; disable receives here in the ISR and reset
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1216
		 * adapter in watchdog
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1217
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1218
		if (netif_carrier_ok(netdev) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1219
		    adapter->flags & FLAG_RX_NEEDS_RESTART) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1220
			/* disable receives */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1221
			u32 rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1222
			ew32(RCTL, rctl & ~E1000_RCTL_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1223
			adapter->flags |= FLAG_RX_RESTART_NOW;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1224
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1225
		/* guard against interrupt when we're going down */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1226
		if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1227
			mod_timer(&adapter->watchdog_timer, jiffies + 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1228
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1229
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1230
	if (napi_schedule_prep(&adapter->napi)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1231
		adapter->total_tx_bytes = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1232
		adapter->total_tx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1233
		adapter->total_rx_bytes = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1234
		adapter->total_rx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1235
		__napi_schedule(&adapter->napi);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1236
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1237
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1238
	return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1239
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1240
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1241
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1242
 * e1000_intr - Interrupt Handler
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1243
 * @irq: interrupt number
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1244
 * @data: pointer to a network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1245
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1246
static irqreturn_t e1000_intr(int irq, void *data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1247
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1248
	struct net_device *netdev = data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1249
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1250
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1251
	u32 rctl, icr = er32(ICR);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1252
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1253
	if (!icr)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1254
		return IRQ_NONE;  /* Not our interrupt */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1255
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1256
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1257
	 * IMS will not auto-mask if INT_ASSERTED is not set, and if it is
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1258
	 * not set, then the adapter didn't send an interrupt
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1259
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1260
	if (!adapter->ecdev && !(icr & E1000_ICR_INT_ASSERTED))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1261
		return IRQ_NONE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1262
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1263
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1264
	 * Interrupt Auto-Mask...upon reading ICR,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1265
	 * interrupts are masked.  No need for the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1266
	 * IMC write
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1267
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1268
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1269
	if (!adapter->ecdev && (icr & E1000_ICR_LSC)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1270
		hw->mac.get_link_status = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1271
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1272
		 * ICH8 workaround-- Call gig speed drop workaround on cable
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1273
		 * disconnect (LSC) before accessing any PHY registers
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1274
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1275
		if ((adapter->flags & FLAG_LSC_GIG_SPEED_DROP) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1276
		    (!(er32(STATUS) & E1000_STATUS_LU)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1277
			schedule_work(&adapter->downshift_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1278
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1279
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1280
		 * 80003ES2LAN workaround--
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1281
		 * For packet buffer work-around on link down event;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1282
		 * disable receives here in the ISR and
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1283
		 * reset adapter in watchdog
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1284
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1285
		if (netif_carrier_ok(netdev) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1286
		    (adapter->flags & FLAG_RX_NEEDS_RESTART)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1287
			/* disable receives */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1288
			rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1289
			ew32(RCTL, rctl & ~E1000_RCTL_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1290
			adapter->flags |= FLAG_RX_RESTART_NOW;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1291
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1292
		/* guard against interrupt when we're going down */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1293
		if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1294
			mod_timer(&adapter->watchdog_timer, jiffies + 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1295
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1296
2473
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1297
	if (adapter->ecdev) {
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1298
		int ec_work_done = 0;
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1299
		adapter->clean_rx(adapter, &ec_work_done, 100);
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1300
		e1000_clean_tx_irq(adapter);
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1301
		return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1302
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1303
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1304
	if (napi_schedule_prep(&adapter->napi)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1305
		adapter->total_tx_bytes = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1306
		adapter->total_tx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1307
		adapter->total_rx_bytes = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1308
		adapter->total_rx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1309
		__napi_schedule(&adapter->napi);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1310
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1311
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1312
	return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1313
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1314
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1315
static irqreturn_t e1000_msix_other(int irq, void *data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1316
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1317
	struct net_device *netdev = data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1318
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1319
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1320
	u32 icr = er32(ICR);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1321
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1322
	if (!(icr & E1000_ICR_INT_ASSERTED)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1323
		if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1324
			ew32(IMS, E1000_IMS_OTHER);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1325
		return IRQ_NONE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1326
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1327
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1328
	if (icr & adapter->eiac_mask)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1329
		ew32(ICS, (icr & adapter->eiac_mask));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1330
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1331
	if (icr & E1000_ICR_OTHER) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1332
		if (!(icr & E1000_ICR_LSC))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1333
			goto no_link_interrupt;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1334
		hw->mac.get_link_status = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1335
		/* guard against interrupt when we're going down */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1336
		if (!adapter->ecdev && !test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1337
			mod_timer(&adapter->watchdog_timer, jiffies + 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1338
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1339
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1340
no_link_interrupt:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1341
	if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1342
		ew32(IMS, E1000_IMS_LSC | E1000_IMS_OTHER);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1343
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1344
	return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1345
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1346
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1347
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1348
static irqreturn_t e1000_intr_msix_tx(int irq, void *data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1349
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1350
	struct net_device *netdev = data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1351
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1352
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1353
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1354
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1355
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1356
	adapter->total_tx_bytes = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1357
	adapter->total_tx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1358
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1359
	if (!e1000_clean_tx_irq(adapter))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1360
		/* Ring was not completely cleaned, so fire another interrupt */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1361
		ew32(ICS, tx_ring->ims_val);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1362
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1363
	return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1364
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1365
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1366
static irqreturn_t e1000_intr_msix_rx(int irq, void *data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1367
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1368
	struct net_device *netdev = data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1369
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1370
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1371
	/* Write the ITR value calculated at the end of the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1372
	 * previous interrupt.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1373
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1374
	if (adapter->rx_ring->set_itr) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1375
		writel(1000000000 / (adapter->rx_ring->itr_val * 256),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1376
		       adapter->hw.hw_addr + adapter->rx_ring->itr_register);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1377
		adapter->rx_ring->set_itr = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1378
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1379
2473
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1380
	if (adapter->ecdev) {
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1381
		int ec_work_done = 0;
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  1382
		adapter->clean_rx(adapter, &ec_work_done, 100);
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1383
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1384
		if (napi_schedule_prep(&adapter->napi)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1385
			adapter->total_rx_bytes = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1386
			adapter->total_rx_packets = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1387
			__napi_schedule(&adapter->napi);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1388
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1389
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1390
	return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1391
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1392
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1393
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1394
 * e1000_configure_msix - Configure MSI-X hardware
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1395
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1396
 * e1000_configure_msix sets up the hardware to properly
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1397
 * generate MSI-X interrupts.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1398
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1399
static void e1000_configure_msix(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1400
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1401
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1402
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1403
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1404
	int vector = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1405
	u32 ctrl_ext, ivar = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1406
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1407
	adapter->eiac_mask = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1408
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1409
	/* Workaround issue with spurious interrupts on 82574 in MSI-X mode */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1410
	if (hw->mac.type == e1000_82574) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1411
		u32 rfctl = er32(RFCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1412
		rfctl |= E1000_RFCTL_ACK_DIS;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1413
		ew32(RFCTL, rfctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1414
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1415
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1416
#define E1000_IVAR_INT_ALLOC_VALID	0x8
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1417
	/* Configure Rx vector */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1418
	rx_ring->ims_val = E1000_IMS_RXQ0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1419
	adapter->eiac_mask |= rx_ring->ims_val;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1420
	if (rx_ring->itr_val)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1421
		writel(1000000000 / (rx_ring->itr_val * 256),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1422
		       hw->hw_addr + rx_ring->itr_register);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1423
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1424
		writel(1, hw->hw_addr + rx_ring->itr_register);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1425
	ivar = E1000_IVAR_INT_ALLOC_VALID | vector;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1426
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1427
	/* Configure Tx vector */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1428
	tx_ring->ims_val = E1000_IMS_TXQ0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1429
	vector++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1430
	if (tx_ring->itr_val)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1431
		writel(1000000000 / (tx_ring->itr_val * 256),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1432
		       hw->hw_addr + tx_ring->itr_register);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1433
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1434
		writel(1, hw->hw_addr + tx_ring->itr_register);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1435
	adapter->eiac_mask |= tx_ring->ims_val;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1436
	ivar |= ((E1000_IVAR_INT_ALLOC_VALID | vector) << 8);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1437
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1438
	/* set vector for Other Causes, e.g. link changes */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1439
	vector++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1440
	ivar |= ((E1000_IVAR_INT_ALLOC_VALID | vector) << 16);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1441
	if (rx_ring->itr_val)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1442
		writel(1000000000 / (rx_ring->itr_val * 256),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1443
		       hw->hw_addr + E1000_EITR_82574(vector));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1444
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1445
		writel(1, hw->hw_addr + E1000_EITR_82574(vector));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1446
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1447
	/* Cause Tx interrupts on every write back */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1448
	ivar |= (1 << 31);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1449
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1450
	ew32(IVAR, ivar);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1451
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1452
	/* enable MSI-X PBA support */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1453
	ctrl_ext = er32(CTRL_EXT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1454
	ctrl_ext |= E1000_CTRL_EXT_PBA_CLR;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1455
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1456
	/* Auto-Mask Other interrupts upon ICR read */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1457
#define E1000_EIAC_MASK_82574   0x01F00000
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1458
	ew32(IAM, ~E1000_EIAC_MASK_82574 | E1000_IMS_OTHER);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1459
	ctrl_ext |= E1000_CTRL_EXT_EIAME;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1460
	ew32(CTRL_EXT, ctrl_ext);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1461
	e1e_flush();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1462
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1463
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1464
void e1000e_reset_interrupt_capability(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1465
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1466
	if (adapter->msix_entries) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1467
		pci_disable_msix(adapter->pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1468
		kfree(adapter->msix_entries);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1469
		adapter->msix_entries = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1470
	} else if (adapter->flags & FLAG_MSI_ENABLED) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1471
		pci_disable_msi(adapter->pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1472
		adapter->flags &= ~FLAG_MSI_ENABLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1473
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1474
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1475
	return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1476
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1477
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1478
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1479
 * e1000e_set_interrupt_capability - set MSI or MSI-X if supported
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1480
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1481
 * Attempt to configure interrupts using the best available
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1482
 * capabilities of the hardware and kernel.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1483
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1484
void e1000e_set_interrupt_capability(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1485
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1486
	int err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1487
	int numvecs, i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1488
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1489
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1490
	switch (adapter->int_mode) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1491
	case E1000E_INT_MODE_MSIX:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1492
		if (adapter->flags & FLAG_HAS_MSIX) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1493
			numvecs = 3; /* RxQ0, TxQ0 and other */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1494
			adapter->msix_entries = kcalloc(numvecs,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1495
						      sizeof(struct msix_entry),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1496
						      GFP_KERNEL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1497
			if (adapter->msix_entries) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1498
				for (i = 0; i < numvecs; i++)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1499
					adapter->msix_entries[i].entry = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1500
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1501
				err = pci_enable_msix(adapter->pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1502
						      adapter->msix_entries,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1503
						      numvecs);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1504
				if (err == 0)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1505
					return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1506
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1507
			/* MSI-X failed, so fall through and try MSI */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1508
			e_err("Failed to initialize MSI-X interrupts.  "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1509
			      "Falling back to MSI interrupts.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1510
			e1000e_reset_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1511
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1512
		adapter->int_mode = E1000E_INT_MODE_MSI;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1513
		/* Fall through */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1514
	case E1000E_INT_MODE_MSI:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1515
		if (!pci_enable_msi(adapter->pdev)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1516
			adapter->flags |= FLAG_MSI_ENABLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1517
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1518
			adapter->int_mode = E1000E_INT_MODE_LEGACY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1519
			e_err("Failed to initialize MSI interrupts.  Falling "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1520
			      "back to legacy interrupts.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1521
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1522
		/* Fall through */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1523
	case E1000E_INT_MODE_LEGACY:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1524
		/* Don't do anything; this is the system default */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1525
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1526
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1527
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1528
	return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1529
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1530
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1531
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1532
 * e1000_request_msix - Initialize MSI-X interrupts
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1533
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1534
 * e1000_request_msix allocates MSI-X vectors and requests interrupts from the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1535
 * kernel.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1536
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1537
static int e1000_request_msix(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1538
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1539
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1540
	int err = 0, vector = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1541
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1542
	if (strlen(netdev->name) < (IFNAMSIZ - 5))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1543
		sprintf(adapter->rx_ring->name, "%s-rx-0", netdev->name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1544
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1545
		memcpy(adapter->rx_ring->name, netdev->name, IFNAMSIZ);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1546
	err = request_irq(adapter->msix_entries[vector].vector,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1547
			  &e1000_intr_msix_rx, 0, adapter->rx_ring->name,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1548
			  netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1549
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1550
		goto out;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1551
	adapter->rx_ring->itr_register = E1000_EITR_82574(vector);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1552
	adapter->rx_ring->itr_val = adapter->itr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1553
	vector++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1554
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1555
	if (strlen(netdev->name) < (IFNAMSIZ - 5))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1556
		sprintf(adapter->tx_ring->name, "%s-tx-0", netdev->name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1557
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1558
		memcpy(adapter->tx_ring->name, netdev->name, IFNAMSIZ);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1559
	err = request_irq(adapter->msix_entries[vector].vector,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1560
			  &e1000_intr_msix_tx, 0, adapter->tx_ring->name,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1561
			  netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1562
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1563
		goto out;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1564
	adapter->tx_ring->itr_register = E1000_EITR_82574(vector);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1565
	adapter->tx_ring->itr_val = adapter->itr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1566
	vector++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1567
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1568
	err = request_irq(adapter->msix_entries[vector].vector,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1569
			  &e1000_msix_other, 0, netdev->name, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1570
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1571
		goto out;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1572
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1573
	e1000_configure_msix(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1574
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1575
out:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1576
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1577
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1578
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1579
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1580
 * e1000_request_irq - initialize interrupts
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1581
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1582
 * Attempts to configure interrupts using the best available
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1583
 * capabilities of the hardware and kernel.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1584
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1585
static int e1000_request_irq(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1586
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1587
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1588
	int err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1589
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1590
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1591
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1592
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1593
	if (adapter->msix_entries) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1594
		err = e1000_request_msix(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1595
		if (!err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1596
			return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1597
		/* fall back to MSI */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1598
		e1000e_reset_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1599
		adapter->int_mode = E1000E_INT_MODE_MSI;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1600
		e1000e_set_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1601
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1602
	if (adapter->flags & FLAG_MSI_ENABLED) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1603
		err = request_irq(adapter->pdev->irq, &e1000_intr_msi, 0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1604
				  netdev->name, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1605
		if (!err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1606
			return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1607
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1608
		/* fall back to legacy interrupt */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1609
		e1000e_reset_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1610
		adapter->int_mode = E1000E_INT_MODE_LEGACY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1611
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1612
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1613
	err = request_irq(adapter->pdev->irq, &e1000_intr, IRQF_SHARED,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1614
			  netdev->name, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1615
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1616
		e_err("Unable to allocate interrupt, Error: %d\n", err);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1617
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1618
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1619
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1620
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1621
static void e1000_free_irq(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1622
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1623
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1624
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1625
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1626
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1627
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1628
	if (adapter->msix_entries) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1629
		int vector = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1630
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1631
		free_irq(adapter->msix_entries[vector].vector, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1632
		vector++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1633
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1634
		free_irq(adapter->msix_entries[vector].vector, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1635
		vector++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1636
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1637
		/* Other Causes interrupt vector */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1638
		free_irq(adapter->msix_entries[vector].vector, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1639
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1640
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1641
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1642
	free_irq(adapter->pdev->irq, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1643
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1644
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1645
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1646
 * e1000_irq_disable - Mask off interrupt generation on the NIC
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1647
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1648
static void e1000_irq_disable(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1649
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1650
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1651
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1652
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1653
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1654
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1655
	ew32(IMC, ~0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1656
	if (adapter->msix_entries)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1657
		ew32(EIAC_82574, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1658
	e1e_flush();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1659
	synchronize_irq(adapter->pdev->irq);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1660
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1661
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1662
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1663
 * e1000_irq_enable - Enable default interrupt generation settings
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1664
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1665
static void e1000_irq_enable(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1666
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1667
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1668
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1669
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1670
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1671
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1672
	if (adapter->msix_entries) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1673
		ew32(EIAC_82574, adapter->eiac_mask & E1000_EIAC_MASK_82574);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1674
		ew32(IMS, adapter->eiac_mask | E1000_IMS_OTHER | E1000_IMS_LSC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1675
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1676
		ew32(IMS, IMS_ENABLE_MASK);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1677
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1678
	e1e_flush();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1679
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1680
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1681
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1682
 * e1000_get_hw_control - get control of the h/w from f/w
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1683
 * @adapter: address of board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1684
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1685
 * e1000_get_hw_control sets {CTRL_EXT|SWSM}:DRV_LOAD bit.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1686
 * For ASF and Pass Through versions of f/w this means that
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1687
 * the driver is loaded. For AMT version (only with 82573)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1688
 * of the f/w this means that the network i/f is open.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1689
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1690
static void e1000_get_hw_control(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1691
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1692
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1693
	u32 ctrl_ext;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1694
	u32 swsm;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1695
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1696
	/* Let firmware know the driver has taken over */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1697
	if (adapter->flags & FLAG_HAS_SWSM_ON_LOAD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1698
		swsm = er32(SWSM);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1699
		ew32(SWSM, swsm | E1000_SWSM_DRV_LOAD);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1700
	} else if (adapter->flags & FLAG_HAS_CTRLEXT_ON_LOAD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1701
		ctrl_ext = er32(CTRL_EXT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1702
		ew32(CTRL_EXT, ctrl_ext | E1000_CTRL_EXT_DRV_LOAD);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1703
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1704
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1705
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1706
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1707
 * e1000_release_hw_control - release control of the h/w to f/w
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1708
 * @adapter: address of board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1709
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1710
 * e1000_release_hw_control resets {CTRL_EXT|SWSM}:DRV_LOAD bit.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1711
 * For ASF and Pass Through versions of f/w this means that the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1712
 * driver is no longer loaded. For AMT version (only with 82573) i
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1713
 * of the f/w this means that the network i/f is closed.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1714
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1715
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1716
static void e1000_release_hw_control(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1717
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1718
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1719
	u32 ctrl_ext;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1720
	u32 swsm;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1721
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1722
	/* Let firmware taken over control of h/w */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1723
	if (adapter->flags & FLAG_HAS_SWSM_ON_LOAD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1724
		swsm = er32(SWSM);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1725
		ew32(SWSM, swsm & ~E1000_SWSM_DRV_LOAD);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1726
	} else if (adapter->flags & FLAG_HAS_CTRLEXT_ON_LOAD) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1727
		ctrl_ext = er32(CTRL_EXT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1728
		ew32(CTRL_EXT, ctrl_ext & ~E1000_CTRL_EXT_DRV_LOAD);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1729
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1730
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1731
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1732
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1733
 * @e1000_alloc_ring - allocate memory for a ring structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1734
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1735
static int e1000_alloc_ring_dma(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1736
				struct e1000_ring *ring)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1737
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1738
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1739
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1740
	ring->desc = dma_alloc_coherent(&pdev->dev, ring->size, &ring->dma,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1741
					GFP_KERNEL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1742
	if (!ring->desc)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1743
		return -ENOMEM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1744
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1745
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1746
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1747
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1748
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1749
 * e1000e_setup_tx_resources - allocate Tx resources (Descriptors)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1750
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1751
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1752
 * Return 0 on success, negative on failure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1753
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1754
int e1000e_setup_tx_resources(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1755
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1756
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1757
	int err = -ENOMEM, size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1758
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1759
	size = sizeof(struct e1000_buffer) * tx_ring->count;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1760
	tx_ring->buffer_info = vmalloc(size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1761
	if (!tx_ring->buffer_info)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1762
		goto err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1763
	memset(tx_ring->buffer_info, 0, size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1764
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1765
	/* round up to nearest 4K */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1766
	tx_ring->size = tx_ring->count * sizeof(struct e1000_tx_desc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1767
	tx_ring->size = ALIGN(tx_ring->size, 4096);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1768
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1769
	err = e1000_alloc_ring_dma(adapter, tx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1770
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1771
		goto err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1772
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1773
	tx_ring->next_to_use = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1774
	tx_ring->next_to_clean = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1775
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1776
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1777
err:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1778
	vfree(tx_ring->buffer_info);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1779
	e_err("Unable to allocate memory for the transmit descriptor ring\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1780
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1781
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1782
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1783
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1784
 * e1000e_setup_rx_resources - allocate Rx resources (Descriptors)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1785
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1786
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1787
 * Returns 0 on success, negative on failure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1788
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1789
int e1000e_setup_rx_resources(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1790
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1791
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1792
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1793
	int i, size, desc_len, err = -ENOMEM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1794
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1795
	size = sizeof(struct e1000_buffer) * rx_ring->count;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1796
	rx_ring->buffer_info = vmalloc(size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1797
	if (!rx_ring->buffer_info)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1798
		goto err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1799
	memset(rx_ring->buffer_info, 0, size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1800
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1801
	for (i = 0; i < rx_ring->count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1802
		buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1803
		buffer_info->ps_pages = kcalloc(PS_PAGE_BUFFERS,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1804
						sizeof(struct e1000_ps_page),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1805
						GFP_KERNEL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1806
		if (!buffer_info->ps_pages)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1807
			goto err_pages;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1808
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1809
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1810
	desc_len = sizeof(union e1000_rx_desc_packet_split);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1811
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1812
	/* Round up to nearest 4K */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1813
	rx_ring->size = rx_ring->count * desc_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1814
	rx_ring->size = ALIGN(rx_ring->size, 4096);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1815
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1816
	err = e1000_alloc_ring_dma(adapter, rx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1817
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1818
		goto err_pages;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1819
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1820
	rx_ring->next_to_clean = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1821
	rx_ring->next_to_use = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1822
	rx_ring->rx_skb_top = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1823
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1824
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1825
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1826
err_pages:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1827
	for (i = 0; i < rx_ring->count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1828
		buffer_info = &rx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1829
		kfree(buffer_info->ps_pages);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1830
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1831
err:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1832
	vfree(rx_ring->buffer_info);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1833
	e_err("Unable to allocate memory for the transmit descriptor ring\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1834
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1835
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1836
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1837
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1838
 * e1000_clean_tx_ring - Free Tx Buffers
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1839
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1840
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1841
static void e1000_clean_tx_ring(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1842
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1843
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1844
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1845
	unsigned long size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1846
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1847
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1848
	for (i = 0; i < tx_ring->count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1849
		buffer_info = &tx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1850
		e1000_put_txbuf(adapter, buffer_info);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1851
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1852
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1853
	size = sizeof(struct e1000_buffer) * tx_ring->count;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1854
	memset(tx_ring->buffer_info, 0, size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1855
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1856
	memset(tx_ring->desc, 0, tx_ring->size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1857
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1858
	tx_ring->next_to_use = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1859
	tx_ring->next_to_clean = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1860
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1861
	writel(0, adapter->hw.hw_addr + tx_ring->head);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1862
	writel(0, adapter->hw.hw_addr + tx_ring->tail);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1863
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1864
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1865
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1866
 * e1000e_free_tx_resources - Free Tx Resources per Queue
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1867
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1868
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1869
 * Free all transmit software resources
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1870
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1871
void e1000e_free_tx_resources(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1872
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1873
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1874
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1875
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1876
	e1000_clean_tx_ring(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1877
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1878
	vfree(tx_ring->buffer_info);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1879
	tx_ring->buffer_info = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1880
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1881
	dma_free_coherent(&pdev->dev, tx_ring->size, tx_ring->desc,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1882
			  tx_ring->dma);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1883
	tx_ring->desc = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1884
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1885
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1886
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1887
 * e1000e_free_rx_resources - Free Rx Resources
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1888
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1889
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1890
 * Free all receive software resources
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1891
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1892
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1893
void e1000e_free_rx_resources(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1894
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1895
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1896
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1897
	int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1898
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1899
	e1000_clean_rx_ring(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1900
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1901
	for (i = 0; i < rx_ring->count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1902
		kfree(rx_ring->buffer_info[i].ps_pages);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1903
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1904
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1905
	vfree(rx_ring->buffer_info);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1906
	rx_ring->buffer_info = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1907
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1908
	dma_free_coherent(&pdev->dev, rx_ring->size, rx_ring->desc,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1909
			  rx_ring->dma);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1910
	rx_ring->desc = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1911
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1912
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1913
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1914
 * e1000_update_itr - update the dynamic ITR value based on statistics
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1915
 * @adapter: pointer to adapter
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1916
 * @itr_setting: current adapter->itr
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1917
 * @packets: the number of packets during this measurement interval
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1918
 * @bytes: the number of bytes during this measurement interval
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1919
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1920
 *      Stores a new ITR value based on packets and byte
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1921
 *      counts during the last interrupt.  The advantage of per interrupt
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1922
 *      computation is faster updates and more accurate ITR for the current
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1923
 *      traffic pattern.  Constants in this function were computed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1924
 *      based on theoretical maximum wire speed and thresholds were set based
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1925
 *      on testing data as well as attempting to minimize response time
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1926
 *      while increasing bulk throughput.  This functionality is controlled
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1927
 *      by the InterruptThrottleRate module parameter.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1928
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1929
static unsigned int e1000_update_itr(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1930
				     u16 itr_setting, int packets,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1931
				     int bytes)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1932
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1933
	unsigned int retval = itr_setting;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1934
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1935
	if (packets == 0)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1936
		goto update_itr_done;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1937
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1938
	switch (itr_setting) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1939
	case lowest_latency:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1940
		/* handle TSO and jumbo frames */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1941
		if (bytes/packets > 8000)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1942
			retval = bulk_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1943
		else if ((packets < 5) && (bytes > 512)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1944
			retval = low_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1945
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1946
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1947
	case low_latency:  /* 50 usec aka 20000 ints/s */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1948
		if (bytes > 10000) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1949
			/* this if handles the TSO accounting */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1950
			if (bytes/packets > 8000) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1951
				retval = bulk_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1952
			} else if ((packets < 10) || ((bytes/packets) > 1200)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1953
				retval = bulk_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1954
			} else if ((packets > 35)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1955
				retval = lowest_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1956
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1957
		} else if (bytes/packets > 2000) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1958
			retval = bulk_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1959
		} else if (packets <= 2 && bytes < 512) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1960
			retval = lowest_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1961
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1962
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1963
	case bulk_latency: /* 250 usec aka 4000 ints/s */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1964
		if (bytes > 25000) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1965
			if (packets > 35) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1966
				retval = low_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1967
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1968
		} else if (bytes < 6000) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1969
			retval = low_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1970
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1971
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1972
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1973
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1974
update_itr_done:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1975
	return retval;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1976
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1977
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1978
static void e1000_set_itr(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1979
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1980
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1981
	u16 current_itr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1982
	u32 new_itr = adapter->itr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1983
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1984
	/* for non-gigabit speeds, just fix the interrupt rate at 4000 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1985
	if (adapter->link_speed != SPEED_1000) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1986
		current_itr = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1987
		new_itr = 4000;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1988
		goto set_itr_now;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1989
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1990
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1991
	adapter->tx_itr = e1000_update_itr(adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1992
				    adapter->tx_itr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1993
				    adapter->total_tx_packets,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1994
				    adapter->total_tx_bytes);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1995
	/* conservative mode (itr 3) eliminates the lowest_latency setting */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1996
	if (adapter->itr_setting == 3 && adapter->tx_itr == lowest_latency)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1997
		adapter->tx_itr = low_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1998
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  1999
	adapter->rx_itr = e1000_update_itr(adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2000
				    adapter->rx_itr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2001
				    adapter->total_rx_packets,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2002
				    adapter->total_rx_bytes);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2003
	/* conservative mode (itr 3) eliminates the lowest_latency setting */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2004
	if (adapter->itr_setting == 3 && adapter->rx_itr == lowest_latency)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2005
		adapter->rx_itr = low_latency;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2006
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2007
	current_itr = max(adapter->rx_itr, adapter->tx_itr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2008
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2009
	switch (current_itr) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2010
	/* counts and packets in update_itr are dependent on these numbers */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2011
	case lowest_latency:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2012
		new_itr = 70000;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2013
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2014
	case low_latency:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2015
		new_itr = 20000; /* aka hwitr = ~200 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2016
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2017
	case bulk_latency:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2018
		new_itr = 4000;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2019
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2020
	default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2021
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2022
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2023
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2024
set_itr_now:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2025
	if (new_itr != adapter->itr) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2026
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2027
		 * this attempts to bias the interrupt rate towards Bulk
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2028
		 * by adding intermediate steps when interrupt rate is
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2029
		 * increasing
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2030
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2031
		new_itr = new_itr > adapter->itr ?
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2032
			     min(adapter->itr + (new_itr >> 2), new_itr) :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2033
			     new_itr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2034
		adapter->itr = new_itr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2035
		adapter->rx_ring->itr_val = new_itr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2036
		if (adapter->msix_entries)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2037
			adapter->rx_ring->set_itr = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2038
		else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2039
			ew32(ITR, 1000000000 / (new_itr * 256));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2040
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2041
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2042
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2043
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2044
 * e1000_alloc_queues - Allocate memory for all rings
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2045
 * @adapter: board private structure to initialize
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2046
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2047
static int __devinit e1000_alloc_queues(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2048
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2049
	adapter->tx_ring = kzalloc(sizeof(struct e1000_ring), GFP_KERNEL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2050
	if (!adapter->tx_ring)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2051
		goto err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2052
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2053
	adapter->rx_ring = kzalloc(sizeof(struct e1000_ring), GFP_KERNEL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2054
	if (!adapter->rx_ring)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2055
		goto err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2056
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2057
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2058
err:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2059
	e_err("Unable to allocate memory for queues\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2060
	kfree(adapter->rx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2061
	kfree(adapter->tx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2062
	return -ENOMEM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2063
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2064
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2065
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2066
 * e1000_clean - NAPI Rx polling callback
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2067
 * @napi: struct associated with this polling callback
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2068
 * @budget: amount of packets driver is allowed to process this poll
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2069
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2070
static int e1000_clean(struct napi_struct *napi, int budget)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2071
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2072
	struct e1000_adapter *adapter = container_of(napi, struct e1000_adapter, napi);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2073
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2074
	struct net_device *poll_dev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2075
	int tx_cleaned = 1, work_done = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2076
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2077
	adapter = netdev_priv(poll_dev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2078
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2079
	if (adapter->msix_entries &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2080
	    !(adapter->rx_ring->ims_val & adapter->tx_ring->ims_val))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2081
		goto clean_rx;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2082
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2083
	tx_cleaned = e1000_clean_tx_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2084
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2085
clean_rx:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2086
	adapter->clean_rx(adapter, &work_done, budget);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2087
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2088
	if (!tx_cleaned)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2089
		work_done = budget;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2090
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2091
	/* If budget not fully consumed, exit the polling mode */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2092
	if (work_done < budget) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2093
		if (adapter->itr_setting & 3)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2094
			e1000_set_itr(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2095
		napi_complete(napi);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2096
		if (!test_bit(__E1000_DOWN, &adapter->state)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2097
			if (adapter->msix_entries)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2098
				ew32(IMS, adapter->rx_ring->ims_val);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2099
			else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2100
				e1000_irq_enable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2101
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2102
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2103
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2104
	return work_done;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2105
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2106
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2107
static void e1000_vlan_rx_add_vid(struct net_device *netdev, u16 vid)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2108
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2109
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2110
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2111
	u32 vfta, index;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2112
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2113
	/* don't update vlan cookie if already programmed */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2114
	if ((adapter->hw.mng_cookie.status &
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2115
	     E1000_MNG_DHCP_COOKIE_STATUS_VLAN) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2116
	    (vid == adapter->mng_vlan_id))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2117
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2118
	/* add VID to filter table */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2119
	index = (vid >> 5) & 0x7F;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2120
	vfta = E1000_READ_REG_ARRAY(hw, E1000_VFTA, index);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2121
	vfta |= (1 << (vid & 0x1F));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2122
	e1000e_write_vfta(hw, index, vfta);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2123
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2124
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2125
static void e1000_vlan_rx_kill_vid(struct net_device *netdev, u16 vid)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2126
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2127
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2128
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2129
	u32 vfta, index;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2130
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2131
	if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2132
		e1000_irq_disable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2133
	vlan_group_set_device(adapter->vlgrp, vid, NULL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2134
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2135
	if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2136
		e1000_irq_enable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2137
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2138
	if ((adapter->hw.mng_cookie.status &
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2139
	     E1000_MNG_DHCP_COOKIE_STATUS_VLAN) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2140
	    (vid == adapter->mng_vlan_id)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2141
		/* release control to f/w */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2142
		e1000_release_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2143
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2144
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2145
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2146
	/* remove VID from filter table */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2147
	index = (vid >> 5) & 0x7F;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2148
	vfta = E1000_READ_REG_ARRAY(hw, E1000_VFTA, index);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2149
	vfta &= ~(1 << (vid & 0x1F));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2150
	e1000e_write_vfta(hw, index, vfta);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2151
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2152
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2153
static void e1000_update_mng_vlan(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2154
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2155
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2156
	u16 vid = adapter->hw.mng_cookie.vlan_id;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2157
	u16 old_vid = adapter->mng_vlan_id;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2158
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2159
	if (!adapter->vlgrp)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2160
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2161
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2162
	if (!vlan_group_get_device(adapter->vlgrp, vid)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2163
		adapter->mng_vlan_id = E1000_MNG_VLAN_NONE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2164
		if (adapter->hw.mng_cookie.status &
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2165
			E1000_MNG_DHCP_COOKIE_STATUS_VLAN) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2166
			e1000_vlan_rx_add_vid(netdev, vid);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2167
			adapter->mng_vlan_id = vid;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2168
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2169
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2170
		if ((old_vid != (u16)E1000_MNG_VLAN_NONE) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2171
				(vid != old_vid) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2172
		    !vlan_group_get_device(adapter->vlgrp, old_vid))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2173
			e1000_vlan_rx_kill_vid(netdev, old_vid);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2174
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2175
		adapter->mng_vlan_id = vid;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2176
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2177
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2178
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2179
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2180
static void e1000_vlan_rx_register(struct net_device *netdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2181
				   struct vlan_group *grp)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2182
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2183
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2184
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2185
	u32 ctrl, rctl;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2186
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2187
	if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2188
		e1000_irq_disable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2189
	adapter->vlgrp = grp;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2190
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2191
	if (grp) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2192
		/* enable VLAN tag insert/strip */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2193
		ctrl = er32(CTRL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2194
		ctrl |= E1000_CTRL_VME;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2195
		ew32(CTRL, ctrl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2196
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2197
		if (adapter->flags & FLAG_HAS_HW_VLAN_FILTER) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2198
			/* enable VLAN receive filtering */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2199
			rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2200
			rctl &= ~E1000_RCTL_CFIEN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2201
			ew32(RCTL, rctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2202
			e1000_update_mng_vlan(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2203
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2204
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2205
		/* disable VLAN tag insert/strip */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2206
		ctrl = er32(CTRL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2207
		ctrl &= ~E1000_CTRL_VME;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2208
		ew32(CTRL, ctrl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2209
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2210
		if (adapter->flags & FLAG_HAS_HW_VLAN_FILTER) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2211
			if (adapter->mng_vlan_id !=
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2212
			    (u16)E1000_MNG_VLAN_NONE) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2213
				e1000_vlan_rx_kill_vid(netdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2214
						       adapter->mng_vlan_id);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2215
				adapter->mng_vlan_id = E1000_MNG_VLAN_NONE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2216
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2217
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2218
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2219
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2220
	if (!test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2221
		e1000_irq_enable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2222
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2223
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2224
static void e1000_restore_vlan(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2225
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2226
	u16 vid;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2227
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2228
	e1000_vlan_rx_register(adapter->netdev, adapter->vlgrp);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2229
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2230
	if (!adapter->vlgrp)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2231
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2232
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2233
	for (vid = 0; vid < VLAN_GROUP_ARRAY_LEN; vid++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2234
		if (!vlan_group_get_device(adapter->vlgrp, vid))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2235
			continue;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2236
		e1000_vlan_rx_add_vid(adapter->netdev, vid);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2237
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2238
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2239
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2240
static void e1000_init_manageability(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2241
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2242
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2243
	u32 manc, manc2h;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2244
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2245
	if (!(adapter->flags & FLAG_MNG_PT_ENABLED))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2246
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2247
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2248
	manc = er32(MANC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2249
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2250
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2251
	 * enable receiving management packets to the host. this will probably
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2252
	 * generate destination unreachable messages from the host OS, but
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2253
	 * the packets will be handled on SMBUS
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2254
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2255
	manc |= E1000_MANC_EN_MNG2HOST;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2256
	manc2h = er32(MANC2H);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2257
#define E1000_MNG2HOST_PORT_623 (1 << 5)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2258
#define E1000_MNG2HOST_PORT_664 (1 << 6)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2259
	manc2h |= E1000_MNG2HOST_PORT_623;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2260
	manc2h |= E1000_MNG2HOST_PORT_664;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2261
	ew32(MANC2H, manc2h);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2262
	ew32(MANC, manc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2263
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2264
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2265
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2266
 * e1000_configure_tx - Configure 8254x Transmit Unit after Reset
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2267
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2268
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2269
 * Configure the Tx unit of the MAC after a reset.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2270
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2271
static void e1000_configure_tx(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2272
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2273
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2274
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2275
	u64 tdba;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2276
	u32 tdlen, tctl, tipg, tarc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2277
	u32 ipgr1, ipgr2;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2278
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2279
	/* Setup the HW Tx Head and Tail descriptor pointers */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2280
	tdba = tx_ring->dma;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2281
	tdlen = tx_ring->count * sizeof(struct e1000_tx_desc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2282
	ew32(TDBAL, (tdba & DMA_BIT_MASK(32)));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2283
	ew32(TDBAH, (tdba >> 32));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2284
	ew32(TDLEN, tdlen);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2285
	ew32(TDH, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2286
	ew32(TDT, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2287
	tx_ring->head = E1000_TDH;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2288
	tx_ring->tail = E1000_TDT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2289
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2290
	/* Set the default values for the Tx Inter Packet Gap timer */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2291
	tipg = DEFAULT_82543_TIPG_IPGT_COPPER;          /*  8  */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2292
	ipgr1 = DEFAULT_82543_TIPG_IPGR1;               /*  8  */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2293
	ipgr2 = DEFAULT_82543_TIPG_IPGR2;               /*  6  */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2294
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2295
	if (adapter->flags & FLAG_TIPG_MEDIUM_FOR_80003ESLAN)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2296
		ipgr2 = DEFAULT_80003ES2LAN_TIPG_IPGR2; /*  7  */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2297
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2298
	tipg |= ipgr1 << E1000_TIPG_IPGR1_SHIFT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2299
	tipg |= ipgr2 << E1000_TIPG_IPGR2_SHIFT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2300
	ew32(TIPG, tipg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2301
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2302
	/* Set the Tx Interrupt Delay register */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2303
	ew32(TIDV, adapter->tx_int_delay);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2304
	/* Tx irq moderation */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2305
	ew32(TADV, adapter->tx_abs_int_delay);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2306
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2307
	/* Program the Transmit Control Register */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2308
	tctl = er32(TCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2309
	tctl &= ~E1000_TCTL_CT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2310
	tctl |= E1000_TCTL_PSP | E1000_TCTL_RTLC |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2311
		(E1000_COLLISION_THRESHOLD << E1000_CT_SHIFT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2312
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2313
	if (adapter->flags & FLAG_TARC_SPEED_MODE_BIT) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2314
		tarc = er32(TARC(0));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2315
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2316
		 * set the speed mode bit, we'll clear it if we're not at
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2317
		 * gigabit link later
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2318
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2319
#define SPEED_MODE_BIT (1 << 21)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2320
		tarc |= SPEED_MODE_BIT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2321
		ew32(TARC(0), tarc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2322
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2323
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2324
	/* errata: program both queues to unweighted RR */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2325
	if (adapter->flags & FLAG_TARC_SET_BIT_ZERO) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2326
		tarc = er32(TARC(0));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2327
		tarc |= 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2328
		ew32(TARC(0), tarc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2329
		tarc = er32(TARC(1));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2330
		tarc |= 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2331
		ew32(TARC(1), tarc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2332
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2333
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2334
	/* Setup Transmit Descriptor Settings for eop descriptor */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2335
	adapter->txd_cmd = E1000_TXD_CMD_EOP | E1000_TXD_CMD_IFCS;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2336
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2337
	/* only set IDE if we are delaying interrupts using the timers */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2338
	if (adapter->tx_int_delay)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2339
		adapter->txd_cmd |= E1000_TXD_CMD_IDE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2340
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2341
	/* enable Report Status bit */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2342
	adapter->txd_cmd |= E1000_TXD_CMD_RS;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2343
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2344
	ew32(TCTL, tctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2345
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2346
	e1000e_config_collision_dist(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2347
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2348
	adapter->tx_queue_len = adapter->netdev->tx_queue_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2349
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2350
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2351
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2352
 * e1000_setup_rctl - configure the receive control registers
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2353
 * @adapter: Board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2354
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2355
#define PAGE_USE_COUNT(S) (((S) >> PAGE_SHIFT) + \
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2356
			   (((S) & (PAGE_SIZE - 1)) ? 1 : 0))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2357
static void e1000_setup_rctl(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2358
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2359
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2360
	u32 rctl, rfctl;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2361
	u32 psrctl = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2362
	u32 pages = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2363
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2364
	/* Program MC offset vector base */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2365
	rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2366
	rctl &= ~(3 << E1000_RCTL_MO_SHIFT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2367
	rctl |= E1000_RCTL_EN | E1000_RCTL_BAM |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2368
		E1000_RCTL_LBM_NO | E1000_RCTL_RDMTS_HALF |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2369
		(adapter->hw.mac.mc_filter_type << E1000_RCTL_MO_SHIFT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2370
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2371
	/* Do not Store bad packets */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2372
	rctl &= ~E1000_RCTL_SBP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2373
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2374
	/* Enable Long Packet receive */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2375
	if (adapter->netdev->mtu <= ETH_DATA_LEN)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2376
		rctl &= ~E1000_RCTL_LPE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2377
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2378
		rctl |= E1000_RCTL_LPE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2379
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2380
	/* Some systems expect that the CRC is included in SMBUS traffic. The
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2381
	 * hardware strips the CRC before sending to both SMBUS (BMC) and to
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2382
	 * host memory when this is enabled
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2383
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2384
	if (adapter->flags2 & FLAG2_CRC_STRIPPING)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2385
		rctl |= E1000_RCTL_SECRC;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2386
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2387
	/* Workaround Si errata on 82577 PHY - configure IPG for jumbos */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2388
	if ((hw->phy.type == e1000_phy_82577) && (rctl & E1000_RCTL_LPE)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2389
		u16 phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2390
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2391
		e1e_rphy(hw, PHY_REG(770, 26), &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2392
		phy_data &= 0xfff8;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2393
		phy_data |= (1 << 2);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2394
		e1e_wphy(hw, PHY_REG(770, 26), phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2395
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2396
		e1e_rphy(hw, 22, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2397
		phy_data &= 0x0fff;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2398
		phy_data |= (1 << 14);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2399
		e1e_wphy(hw, 0x10, 0x2823);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2400
		e1e_wphy(hw, 0x11, 0x0003);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2401
		e1e_wphy(hw, 22, phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2402
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2403
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2404
	/* Setup buffer sizes */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2405
	rctl &= ~E1000_RCTL_SZ_4096;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2406
	rctl |= E1000_RCTL_BSEX;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2407
	switch (adapter->rx_buffer_len) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2408
	case 2048:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2409
	default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2410
		rctl |= E1000_RCTL_SZ_2048;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2411
		rctl &= ~E1000_RCTL_BSEX;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2412
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2413
	case 4096:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2414
		rctl |= E1000_RCTL_SZ_4096;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2415
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2416
	case 8192:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2417
		rctl |= E1000_RCTL_SZ_8192;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2418
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2419
	case 16384:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2420
		rctl |= E1000_RCTL_SZ_16384;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2421
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2422
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2423
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2424
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2425
	 * 82571 and greater support packet-split where the protocol
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2426
	 * header is placed in skb->data and the packet data is
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2427
	 * placed in pages hanging off of skb_shinfo(skb)->nr_frags.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2428
	 * In the case of a non-split, skb->data is linearly filled,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2429
	 * followed by the page buffers.  Therefore, skb->data is
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2430
	 * sized to hold the largest protocol header.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2431
	 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2432
	 * allocations using alloc_page take too long for regular MTU
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2433
	 * so only enable packet split for jumbo frames
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2434
	 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2435
	 * Using pages when the page size is greater than 16k wastes
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2436
	 * a lot of memory, since we allocate 3 pages at all times
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2437
	 * per packet.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2438
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2439
	pages = PAGE_USE_COUNT(adapter->netdev->mtu);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2440
	if (!(adapter->flags & FLAG_IS_ICH) && (pages <= 3) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2441
	    (PAGE_SIZE <= 16384) && (rctl & E1000_RCTL_LPE))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2442
		adapter->rx_ps_pages = pages;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2443
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2444
		adapter->rx_ps_pages = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2445
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2446
	if (adapter->rx_ps_pages) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2447
		/* Configure extra packet-split registers */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2448
		rfctl = er32(RFCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2449
		rfctl |= E1000_RFCTL_EXTEN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2450
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2451
		 * disable packet split support for IPv6 extension headers,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2452
		 * because some malformed IPv6 headers can hang the Rx
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2453
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2454
		rfctl |= (E1000_RFCTL_IPV6_EX_DIS |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2455
			  E1000_RFCTL_NEW_IPV6_EXT_DIS);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2456
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2457
		ew32(RFCTL, rfctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2458
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2459
		/* Enable Packet split descriptors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2460
		rctl |= E1000_RCTL_DTYP_PS;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2461
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2462
		psrctl |= adapter->rx_ps_bsize0 >>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2463
			E1000_PSRCTL_BSIZE0_SHIFT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2464
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2465
		switch (adapter->rx_ps_pages) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2466
		case 3:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2467
			psrctl |= PAGE_SIZE <<
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2468
				E1000_PSRCTL_BSIZE3_SHIFT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2469
		case 2:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2470
			psrctl |= PAGE_SIZE <<
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2471
				E1000_PSRCTL_BSIZE2_SHIFT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2472
		case 1:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2473
			psrctl |= PAGE_SIZE >>
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2474
				E1000_PSRCTL_BSIZE1_SHIFT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2475
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2476
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2477
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2478
		ew32(PSRCTL, psrctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2479
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2480
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2481
	ew32(RCTL, rctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2482
	/* just started the receive unit, no need to restart */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2483
	adapter->flags &= ~FLAG_RX_RESTART_NOW;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2484
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2485
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2486
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2487
 * e1000_configure_rx - Configure Receive Unit after Reset
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2488
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2489
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2490
 * Configure the Rx unit of the MAC after a reset.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2491
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2492
static void e1000_configure_rx(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2493
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2494
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2495
	struct e1000_ring *rx_ring = adapter->rx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2496
	u64 rdba;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2497
	u32 rdlen, rctl, rxcsum, ctrl_ext;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2498
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2499
	if (adapter->rx_ps_pages) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2500
		/* this is a 32 byte descriptor */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2501
		rdlen = rx_ring->count *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2502
			sizeof(union e1000_rx_desc_packet_split);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2503
		adapter->clean_rx = e1000_clean_rx_irq_ps;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2504
		adapter->alloc_rx_buf = e1000_alloc_rx_buffers_ps;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2505
	} else if (adapter->netdev->mtu > ETH_FRAME_LEN + ETH_FCS_LEN) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2506
		rdlen = rx_ring->count * sizeof(struct e1000_rx_desc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2507
		adapter->clean_rx = e1000_clean_jumbo_rx_irq;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2508
		adapter->alloc_rx_buf = e1000_alloc_jumbo_rx_buffers;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2509
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2510
		rdlen = rx_ring->count * sizeof(struct e1000_rx_desc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2511
		adapter->clean_rx = e1000_clean_rx_irq;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2512
		adapter->alloc_rx_buf = e1000_alloc_rx_buffers;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2513
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2514
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2515
	/* disable receives while setting up the descriptors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2516
	rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2517
	ew32(RCTL, rctl & ~E1000_RCTL_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2518
	e1e_flush();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2519
	msleep(10);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2520
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2521
	/* set the Receive Delay Timer Register */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2522
	ew32(RDTR, adapter->rx_int_delay);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2523
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2524
	/* irq moderation */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2525
	ew32(RADV, adapter->rx_abs_int_delay);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2526
	if (adapter->itr_setting != 0)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2527
		ew32(ITR, 1000000000 / (adapter->itr * 256));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2528
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2529
	ctrl_ext = er32(CTRL_EXT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2530
	/* Reset delay timers after every interrupt */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2531
	ctrl_ext |= E1000_CTRL_EXT_INT_TIMER_CLR;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2532
	/* Auto-Mask interrupts upon ICR access */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2533
	ctrl_ext |= E1000_CTRL_EXT_IAME;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2534
	ew32(IAM, 0xffffffff);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2535
	ew32(CTRL_EXT, ctrl_ext);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2536
	e1e_flush();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2537
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2538
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2539
	 * Setup the HW Rx Head and Tail Descriptor Pointers and
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2540
	 * the Base and Length of the Rx Descriptor Ring
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2541
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2542
	rdba = rx_ring->dma;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2543
	ew32(RDBAL, (rdba & DMA_BIT_MASK(32)));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2544
	ew32(RDBAH, (rdba >> 32));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2545
	ew32(RDLEN, rdlen);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2546
	ew32(RDH, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2547
	ew32(RDT, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2548
	rx_ring->head = E1000_RDH;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2549
	rx_ring->tail = E1000_RDT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2550
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2551
	/* Enable Receive Checksum Offload for TCP and UDP */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2552
	rxcsum = er32(RXCSUM);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2553
	if (adapter->flags & FLAG_RX_CSUM_ENABLED) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2554
		rxcsum |= E1000_RXCSUM_TUOFL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2555
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2556
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2557
		 * IPv4 payload checksum for UDP fragments must be
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2558
		 * used in conjunction with packet-split.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2559
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2560
		if (adapter->rx_ps_pages)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2561
			rxcsum |= E1000_RXCSUM_IPPCSE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2562
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2563
		rxcsum &= ~E1000_RXCSUM_TUOFL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2564
		/* no need to clear IPPCSE as it defaults to 0 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2565
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2566
	ew32(RXCSUM, rxcsum);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2567
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2568
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2569
	 * Enable early receives on supported devices, only takes effect when
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2570
	 * packet size is equal or larger than the specified value (in 8 byte
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2571
	 * units), e.g. using jumbo frames when setting to E1000_ERT_2048
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2572
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2573
	if ((adapter->flags & FLAG_HAS_ERT) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2574
	    (adapter->netdev->mtu > ETH_DATA_LEN)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2575
		u32 rxdctl = er32(RXDCTL(0));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2576
		ew32(RXDCTL(0), rxdctl | 0x3);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2577
		ew32(ERT, E1000_ERT_2048 | (1 << 13));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2578
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2579
		 * With jumbo frames and early-receive enabled, excessive
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2580
		 * C4->C2 latencies result in dropped transactions.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2581
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2582
		pm_qos_update_requirement(PM_QOS_CPU_DMA_LATENCY,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2583
					  e1000e_driver_name, 55);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2584
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2585
		pm_qos_update_requirement(PM_QOS_CPU_DMA_LATENCY,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2586
					  e1000e_driver_name,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2587
					  PM_QOS_DEFAULT_VALUE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2588
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2589
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2590
	/* Enable Receives */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2591
	ew32(RCTL, rctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2592
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2593
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2594
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2595
 *  e1000_update_mc_addr_list - Update Multicast addresses
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2596
 *  @hw: pointer to the HW structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2597
 *  @mc_addr_list: array of multicast addresses to program
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2598
 *  @mc_addr_count: number of multicast addresses to program
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2599
 *  @rar_used_count: the first RAR register free to program
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2600
 *  @rar_count: total number of supported Receive Address Registers
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2601
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2602
 *  Updates the Receive Address Registers and Multicast Table Array.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2603
 *  The caller must have a packed mc_addr_list of multicast addresses.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2604
 *  The parameter rar_count will usually be hw->mac.rar_entry_count
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2605
 *  unless there are workarounds that change this.  Currently no func pointer
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2606
 *  exists and all implementations are handled in the generic version of this
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2607
 *  function.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2608
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2609
static void e1000_update_mc_addr_list(struct e1000_hw *hw, u8 *mc_addr_list,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2610
				      u32 mc_addr_count, u32 rar_used_count,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2611
				      u32 rar_count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2612
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2613
	hw->mac.ops.update_mc_addr_list(hw, mc_addr_list, mc_addr_count,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2614
				        rar_used_count, rar_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2615
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2616
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2617
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2618
 * e1000_set_multi - Multicast and Promiscuous mode set
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2619
 * @netdev: network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2620
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2621
 * The set_multi entry point is called whenever the multicast address
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2622
 * list or the network interface flags are updated.  This routine is
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2623
 * responsible for configuring the hardware for proper multicast,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2624
 * promiscuous mode, and all-multi behavior.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2625
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2626
static void e1000_set_multi(struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2627
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2628
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2629
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2630
	struct e1000_mac_info *mac = &hw->mac;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2631
	struct dev_mc_list *mc_ptr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2632
	u8  *mta_list;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2633
	u32 rctl;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2634
	int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2635
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2636
	/* Check for Promiscuous and All Multicast modes */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2637
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2638
	rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2639
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2640
	if (netdev->flags & IFF_PROMISC) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2641
		rctl |= (E1000_RCTL_UPE | E1000_RCTL_MPE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2642
		rctl &= ~E1000_RCTL_VFE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2643
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2644
		if (netdev->flags & IFF_ALLMULTI) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2645
			rctl |= E1000_RCTL_MPE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2646
			rctl &= ~E1000_RCTL_UPE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2647
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2648
			rctl &= ~(E1000_RCTL_UPE | E1000_RCTL_MPE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2649
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2650
		if (adapter->flags & FLAG_HAS_HW_VLAN_FILTER)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2651
			rctl |= E1000_RCTL_VFE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2652
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2653
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2654
	ew32(RCTL, rctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2655
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2656
	if (netdev->mc_count) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2657
		mta_list = kmalloc(netdev->mc_count * 6, GFP_ATOMIC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2658
		if (!mta_list)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2659
			return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2660
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2661
		/* prepare a packed array of only addresses. */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2662
		mc_ptr = netdev->mc_list;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2663
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2664
		for (i = 0; i < netdev->mc_count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2665
			if (!mc_ptr)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2666
				break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2667
			memcpy(mta_list + (i*ETH_ALEN), mc_ptr->dmi_addr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2668
			       ETH_ALEN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2669
			mc_ptr = mc_ptr->next;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2670
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2671
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2672
		e1000_update_mc_addr_list(hw, mta_list, i, 1,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2673
					  mac->rar_entry_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2674
		kfree(mta_list);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2675
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2676
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2677
		 * if we're called from probe, we might not have
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2678
		 * anything to do here, so clear out the list
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2679
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2680
		e1000_update_mc_addr_list(hw, NULL, 0, 1, mac->rar_entry_count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2681
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2682
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2683
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2684
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2685
 * e1000_configure - configure the hardware for Rx and Tx
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2686
 * @adapter: private board structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2687
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2688
static void e1000_configure(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2689
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2690
	e1000_set_multi(adapter->netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2691
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2692
	e1000_restore_vlan(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2693
	e1000_init_manageability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2694
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2695
	e1000_configure_tx(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2696
	e1000_setup_rctl(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2697
	e1000_configure_rx(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2698
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2699
	if (adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2700
		adapter->alloc_rx_buf(adapter, adapter->rx_ring->count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2701
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2702
		adapter->alloc_rx_buf(adapter, e1000_desc_unused(adapter->rx_ring));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2703
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2704
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2705
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2706
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2707
 * e1000e_power_up_phy - restore link in case the phy was powered down
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2708
 * @adapter: address of board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2709
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2710
 * The phy may be powered down to save power and turn off link when the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2711
 * driver is unloaded and wake on lan is not enabled (among others)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2712
 * *** this routine MUST be followed by a call to e1000e_reset ***
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2713
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2714
void e1000e_power_up_phy(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2715
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2716
	u16 mii_reg = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2717
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2718
	/* Just clear the power down bit to wake the phy back up */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2719
	if (adapter->hw.phy.media_type == e1000_media_type_copper) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2720
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2721
		 * According to the manual, the phy will retain its
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2722
		 * settings across a power-down/up cycle
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2723
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2724
		e1e_rphy(&adapter->hw, PHY_CONTROL, &mii_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2725
		mii_reg &= ~MII_CR_POWER_DOWN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2726
		e1e_wphy(&adapter->hw, PHY_CONTROL, mii_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2727
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2728
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2729
	adapter->hw.mac.ops.setup_link(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2730
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2731
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2732
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2733
 * e1000_power_down_phy - Power down the PHY
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2734
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2735
 * Power down the PHY so no link is implied when interface is down
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2736
 * The PHY cannot be powered down is management or WoL is active
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2737
 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2738
static void e1000_power_down_phy(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2739
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2740
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2741
	u16 mii_reg;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2742
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2743
	/* WoL is enabled */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2744
	if (adapter->wol)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2745
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2746
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2747
	/* non-copper PHY? */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2748
	if (adapter->hw.phy.media_type != e1000_media_type_copper)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2749
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2750
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2751
	/* reset is blocked because of a SoL/IDER session */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2752
	if (e1000e_check_mng_mode(hw) || e1000_check_reset_block(hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2753
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2754
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2755
	/* manageability (AMT) is enabled */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2756
	if (er32(MANC) & E1000_MANC_SMBUS_EN)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2757
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2758
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2759
	/* power down the PHY */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2760
	e1e_rphy(hw, PHY_CONTROL, &mii_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2761
	mii_reg |= MII_CR_POWER_DOWN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2762
	e1e_wphy(hw, PHY_CONTROL, mii_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2763
	mdelay(1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2764
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2765
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2766
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2767
 * e1000e_reset - bring the hardware into a known good state
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2768
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2769
 * This function boots the hardware and enables some settings that
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2770
 * require a configuration cycle of the hardware - those cannot be
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2771
 * set/changed during runtime. After reset the device needs to be
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2772
 * properly configured for Rx, Tx etc.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2773
 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2774
void e1000e_reset(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2775
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2776
	struct e1000_mac_info *mac = &adapter->hw.mac;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2777
	struct e1000_fc_info *fc = &adapter->hw.fc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2778
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2779
	u32 tx_space, min_tx_space, min_rx_space;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2780
	u32 pba = adapter->pba;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2781
	u16 hwm;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2782
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2783
	/* reset Packet Buffer Allocation to default */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2784
	ew32(PBA, pba);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2785
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2786
	if (adapter->max_frame_size > ETH_FRAME_LEN + ETH_FCS_LEN) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2787
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2788
		 * To maintain wire speed transmits, the Tx FIFO should be
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2789
		 * large enough to accommodate two full transmit packets,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2790
		 * rounded up to the next 1KB and expressed in KB.  Likewise,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2791
		 * the Rx FIFO should be large enough to accommodate at least
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2792
		 * one full receive packet and is similarly rounded up and
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2793
		 * expressed in KB.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2794
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2795
		pba = er32(PBA);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2796
		/* upper 16 bits has Tx packet buffer allocation size in KB */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2797
		tx_space = pba >> 16;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2798
		/* lower 16 bits has Rx packet buffer allocation size in KB */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2799
		pba &= 0xffff;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2800
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2801
		 * the Tx fifo also stores 16 bytes of information about the tx
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2802
		 * but don't include ethernet FCS because hardware appends it
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2803
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2804
		min_tx_space = (adapter->max_frame_size +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2805
				sizeof(struct e1000_tx_desc) -
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2806
				ETH_FCS_LEN) * 2;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2807
		min_tx_space = ALIGN(min_tx_space, 1024);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2808
		min_tx_space >>= 10;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2809
		/* software strips receive CRC, so leave room for it */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2810
		min_rx_space = adapter->max_frame_size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2811
		min_rx_space = ALIGN(min_rx_space, 1024);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2812
		min_rx_space >>= 10;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2813
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2814
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2815
		 * If current Tx allocation is less than the min Tx FIFO size,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2816
		 * and the min Tx FIFO size is less than the current Rx FIFO
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2817
		 * allocation, take space away from current Rx allocation
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2818
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2819
		if ((tx_space < min_tx_space) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2820
		    ((min_tx_space - tx_space) < pba)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2821
			pba -= min_tx_space - tx_space;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2822
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2823
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2824
			 * if short on Rx space, Rx wins and must trump tx
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2825
			 * adjustment or use Early Receive if available
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2826
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2827
			if ((pba < min_rx_space) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2828
			    (!(adapter->flags & FLAG_HAS_ERT)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2829
				/* ERT enabled in e1000_configure_rx */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2830
				pba = min_rx_space;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2831
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2832
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2833
		ew32(PBA, pba);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2834
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2835
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2836
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2837
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2838
	 * flow control settings
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2839
	 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2840
	 * The high water mark must be low enough to fit one full frame
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2841
	 * (or the size used for early receive) above it in the Rx FIFO.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2842
	 * Set it to the lower of:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2843
	 * - 90% of the Rx FIFO size, and
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2844
	 * - the full Rx FIFO size minus the early receive size (for parts
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2845
	 *   with ERT support assuming ERT set to E1000_ERT_2048), or
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2846
	 * - the full Rx FIFO size minus one full frame
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2847
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2848
	if (hw->mac.type == e1000_pchlan) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2849
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2850
		 * Workaround PCH LOM adapter hangs with certain network
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2851
		 * loads.  If hangs persist, try disabling Tx flow control.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2852
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2853
		if (adapter->netdev->mtu > ETH_DATA_LEN) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2854
			fc->high_water = 0x3500;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2855
			fc->low_water  = 0x1500;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2856
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2857
			fc->high_water = 0x5000;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2858
			fc->low_water  = 0x3000;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2859
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2860
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2861
		if ((adapter->flags & FLAG_HAS_ERT) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2862
		    (adapter->netdev->mtu > ETH_DATA_LEN))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2863
			hwm = min(((pba << 10) * 9 / 10),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2864
				  ((pba << 10) - (E1000_ERT_2048 << 3)));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2865
		else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2866
			hwm = min(((pba << 10) * 9 / 10),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2867
				  ((pba << 10) - adapter->max_frame_size));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2868
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2869
		fc->high_water = hwm & E1000_FCRTH_RTH; /* 8-byte granularity */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2870
		fc->low_water = fc->high_water - 8;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2871
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2872
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2873
	if (adapter->flags & FLAG_DISABLE_FC_PAUSE_TIME)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2874
		fc->pause_time = 0xFFFF;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2875
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2876
		fc->pause_time = E1000_FC_PAUSE_TIME;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2877
	fc->send_xon = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2878
	fc->current_mode = fc->requested_mode;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2879
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2880
	/* Allow time for pending master requests to run */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2881
	mac->ops.reset_hw(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2882
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2883
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2884
	 * For parts with AMT enabled, let the firmware know
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2885
	 * that the network interface is in control
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2886
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2887
	if (adapter->flags & FLAG_HAS_AMT)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2888
		e1000_get_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2889
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2890
	ew32(WUC, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2891
	if (adapter->flags2 & FLAG2_HAS_PHY_WAKEUP)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2892
		e1e_wphy(&adapter->hw, BM_WUC, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2893
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2894
	if (mac->ops.init_hw(hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2895
		e_err("Hardware Error\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2896
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2897
	/* additional part of the flow-control workaround above */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2898
	if (hw->mac.type == e1000_pchlan)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2899
		ew32(FCRTV_PCH, 0x1000);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2900
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2901
	e1000_update_mng_vlan(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2902
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2903
	/* Enable h/w to recognize an 802.1Q VLAN Ethernet packet */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2904
	ew32(VET, ETH_P_8021Q);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2905
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2906
	e1000e_reset_adaptive(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2907
	e1000_get_phy_info(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2908
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2909
	if ((adapter->flags & FLAG_HAS_SMART_POWER_DOWN) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2910
	    !(adapter->flags & FLAG_SMART_POWER_DOWN)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2911
		u16 phy_data = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2912
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2913
		 * speed up time to link by disabling smart power down, ignore
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2914
		 * the return value of this function because there is nothing
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2915
		 * different we would do if it failed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2916
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2917
		e1e_rphy(hw, IGP02E1000_PHY_POWER_MGMT, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2918
		phy_data &= ~IGP02E1000_PM_SPD;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2919
		e1e_wphy(hw, IGP02E1000_PHY_POWER_MGMT, phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2920
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2921
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2922
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2923
int e1000e_up(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2924
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2925
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2926
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2927
	/* hardware has been reset, we need to reload some things */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2928
	e1000_configure(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2929
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2930
	clear_bit(__E1000_DOWN, &adapter->state);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2931
2421
bc2d4bf9cbe5 Removed trailing spaces.
Florian Pose <fp@igh-essen.com>
parents: 2217
diff changeset
  2932
	if (!adapter->ecdev)
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2933
		napi_enable(&adapter->napi);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2934
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2935
	if (adapter->msix_entries)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2936
		e1000_configure_msix(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2937
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2938
	if (!adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2939
		e1000_irq_enable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2940
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2941
		netif_wake_queue(adapter->netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2942
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2943
		/* fire a link change interrupt to start the watchdog */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2944
		ew32(ICS, E1000_ICS_LSC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2945
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2946
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2947
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2948
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2949
void e1000e_down(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2950
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2951
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2952
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2953
	u32 tctl, rctl;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2954
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2955
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2956
	 * signal that we're down so the interrupt handler does not
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2957
	 * reschedule our watchdog timer
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2958
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2959
	set_bit(__E1000_DOWN, &adapter->state);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2960
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2961
	/* disable receives in the hardware */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2962
	rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2963
	ew32(RCTL, rctl & ~E1000_RCTL_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2964
	/* flush and sleep below */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2965
2421
bc2d4bf9cbe5 Removed trailing spaces.
Florian Pose <fp@igh-essen.com>
parents: 2217
diff changeset
  2966
	if (!adapter->ecdev)
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2967
		netif_stop_queue(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2968
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2969
	/* disable transmits in the hardware */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2970
	tctl = er32(TCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2971
	tctl &= ~E1000_TCTL_EN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2972
	ew32(TCTL, tctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2973
	/* flush both disables and wait for them to finish */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2974
	e1e_flush();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2975
	msleep(10);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2976
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2977
	if (!adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2978
		napi_disable(&adapter->napi);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2979
		e1000_irq_disable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2980
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2981
		del_timer_sync(&adapter->watchdog_timer);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2982
		del_timer_sync(&adapter->phy_info_timer);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2983
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2984
		netdev->tx_queue_len = adapter->tx_queue_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2985
		netif_carrier_off(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2986
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2987
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2988
	adapter->link_speed = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2989
	adapter->link_duplex = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2990
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2991
	if (!pci_channel_offline(adapter->pdev))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2992
		e1000e_reset(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2993
	e1000_clean_tx_ring(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2994
	e1000_clean_rx_ring(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2995
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2996
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2997
	 * TODO: for power management, we could drop the link and
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2998
	 * pci_disable_device here.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  2999
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3000
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3001
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3002
void e1000e_reinit_locked(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3003
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3004
	might_sleep();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3005
	while (test_and_set_bit(__E1000_RESETTING, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3006
		msleep(1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3007
	e1000e_down(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3008
	e1000e_up(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3009
	clear_bit(__E1000_RESETTING, &adapter->state);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3010
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3011
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3012
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3013
 * e1000_sw_init - Initialize general software structures (struct e1000_adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3014
 * @adapter: board private structure to initialize
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3015
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3016
 * e1000_sw_init initializes the Adapter private data structure.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3017
 * Fields are initialized based on PCI device information and
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3018
 * OS network device settings (MTU size).
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3019
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3020
static int __devinit e1000_sw_init(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3021
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3022
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3023
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3024
	adapter->rx_buffer_len = ETH_FRAME_LEN + VLAN_HLEN + ETH_FCS_LEN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3025
	adapter->rx_ps_bsize0 = 128;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3026
	adapter->max_frame_size = netdev->mtu + ETH_HLEN + ETH_FCS_LEN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3027
	adapter->min_frame_size = ETH_ZLEN + ETH_FCS_LEN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3028
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3029
	e1000e_set_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3030
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3031
	if (e1000_alloc_queues(adapter))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3032
		return -ENOMEM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3033
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3034
	/* Explicitly disable IRQ since the NIC can be in any state. */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3035
	e1000_irq_disable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3036
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3037
	set_bit(__E1000_DOWN, &adapter->state);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3038
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3039
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3040
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3041
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3042
 * e1000_intr_msi_test - Interrupt Handler
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3043
 * @irq: interrupt number
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3044
 * @data: pointer to a network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3045
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3046
static irqreturn_t e1000_intr_msi_test(int irq, void *data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3047
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3048
	struct net_device *netdev = data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3049
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3050
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3051
	u32 icr = er32(ICR);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3052
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3053
	e_dbg("%s: icr is %08X\n", netdev->name, icr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3054
	if (icr & E1000_ICR_RXSEQ) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3055
		adapter->flags &= ~FLAG_MSI_TEST_FAILED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3056
		wmb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3057
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3058
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3059
	return IRQ_HANDLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3060
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3061
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3062
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3063
 * e1000_test_msi_interrupt - Returns 0 for successful test
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3064
 * @adapter: board private struct
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3065
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3066
 * code flow taken from tg3.c
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3067
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3068
static int e1000_test_msi_interrupt(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3069
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3070
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3071
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3072
	int err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3073
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3074
	/* poll_enable hasn't been called yet, so don't need disable */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3075
	/* clear any pending events */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3076
	er32(ICR);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3077
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3078
	/* free the real vector and request a test handler */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3079
	e1000_free_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3080
	e1000e_reset_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3081
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3082
	/* Assume that the test fails, if it succeeds then the test
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3083
	 * MSI irq handler will unset this flag */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3084
	adapter->flags |= FLAG_MSI_TEST_FAILED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3085
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3086
	err = pci_enable_msi(adapter->pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3087
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3088
		goto msi_test_failed;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3089
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3090
	err = request_irq(adapter->pdev->irq, &e1000_intr_msi_test, 0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3091
			  netdev->name, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3092
	if (err) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3093
		pci_disable_msi(adapter->pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3094
		goto msi_test_failed;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3095
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3096
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3097
	wmb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3098
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3099
	e1000_irq_enable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3100
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3101
	/* fire an unusual interrupt on the test handler */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3102
	ew32(ICS, E1000_ICS_RXSEQ);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3103
	e1e_flush();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3104
	msleep(50);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3105
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3106
	e1000_irq_disable(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3107
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3108
	rmb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3109
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3110
	if (adapter->flags & FLAG_MSI_TEST_FAILED) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3111
		adapter->int_mode = E1000E_INT_MODE_LEGACY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3112
		err = -EIO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3113
		e_info("MSI interrupt test failed!\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3114
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3115
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3116
	free_irq(adapter->pdev->irq, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3117
	pci_disable_msi(adapter->pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3118
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3119
	if (err == -EIO)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3120
		goto msi_test_failed;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3121
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3122
	/* okay so the test worked, restore settings */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3123
	e_dbg("%s: MSI interrupt test succeeded!\n", netdev->name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3124
msi_test_failed:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3125
	e1000e_set_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3126
	e1000_request_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3127
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3128
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3129
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3130
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3131
 * e1000_test_msi - Returns 0 if MSI test succeeds or INTx mode is restored
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3132
 * @adapter: board private struct
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3133
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3134
 * code flow taken from tg3.c, called with e1000 interrupts disabled.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3135
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3136
static int e1000_test_msi(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3137
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3138
	int err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3139
	u16 pci_cmd;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3140
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3141
	if (!(adapter->flags & FLAG_MSI_ENABLED))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3142
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3143
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3144
	/* disable SERR in case the MSI write causes a master abort */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3145
	pci_read_config_word(adapter->pdev, PCI_COMMAND, &pci_cmd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3146
	pci_write_config_word(adapter->pdev, PCI_COMMAND,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3147
			      pci_cmd & ~PCI_COMMAND_SERR);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3148
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3149
	err = e1000_test_msi_interrupt(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3150
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3151
	/* restore previous setting of command word */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3152
	pci_write_config_word(adapter->pdev, PCI_COMMAND, pci_cmd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3153
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3154
	/* success ! */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3155
	if (!err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3156
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3157
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3158
	/* EIO means MSI test failed */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3159
	if (err != -EIO)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3160
		return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3161
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3162
	/* back to INTx mode */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3163
	e_warn("MSI interrupt test failed, using legacy interrupt.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3164
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3165
	e1000_free_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3166
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3167
	err = e1000_request_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3168
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3169
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3170
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3171
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3172
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3173
 * e1000_open - Called when a network interface is made active
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3174
 * @netdev: network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3175
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3176
 * Returns 0 on success, negative value on failure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3177
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3178
 * The open entry point is called when a network interface is made
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3179
 * active by the system (IFF_UP).  At this point all resources needed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3180
 * for transmit and receive operations are allocated, the interrupt
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3181
 * handler is registered with the OS, the watchdog timer is started,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3182
 * and the stack is notified that the interface is ready.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3183
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3184
static int e1000_open(struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3185
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3186
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3187
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3188
	int err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3189
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3190
	/* disallow open during test */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3191
	if (test_bit(__E1000_TESTING, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3192
		return -EBUSY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3193
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3194
	if (adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3195
		ecdev_set_link(adapter->ecdev, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3196
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3197
		netif_carrier_off(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3198
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3199
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3200
	/* allocate transmit descriptors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3201
	err = e1000e_setup_tx_resources(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3202
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3203
		goto err_setup_tx;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3204
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3205
	/* allocate receive descriptors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3206
	err = e1000e_setup_rx_resources(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3207
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3208
		goto err_setup_rx;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3209
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3210
	e1000e_power_up_phy(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3211
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3212
	adapter->mng_vlan_id = E1000_MNG_VLAN_NONE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3213
	if ((adapter->hw.mng_cookie.status &
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3214
	     E1000_MNG_DHCP_COOKIE_STATUS_VLAN))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3215
		e1000_update_mng_vlan(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3216
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3217
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3218
	 * If AMT is enabled, let the firmware know that the network
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3219
	 * interface is now open
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3220
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3221
	if (adapter->flags & FLAG_HAS_AMT)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3222
		e1000_get_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3223
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3224
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3225
	 * before we allocate an interrupt, we must be ready to handle it.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3226
	 * Setting DEBUG_SHIRQ in the kernel makes it fire an interrupt
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3227
	 * as soon as we call pci_request_irq, so we have to setup our
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3228
	 * clean_rx handler before we do so.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3229
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3230
	e1000_configure(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3231
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3232
	err = e1000_request_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3233
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3234
		goto err_req_irq;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3235
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3236
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3237
	 * Work around PCIe errata with MSI interrupts causing some chipsets to
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3238
	 * ignore e1000e MSI messages, which means we need to test our MSI
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3239
	 * interrupt now
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3240
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3241
	if (adapter->int_mode != E1000E_INT_MODE_LEGACY) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3242
		err = e1000_test_msi(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3243
		if (err) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3244
			e_err("Interrupt allocation failed\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3245
			goto err_req_irq;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3246
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3247
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3248
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3249
	/* From here on the code is the same as e1000e_up() */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3250
	clear_bit(__E1000_DOWN, &adapter->state);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3251
2473
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  3252
	if (!adapter->ecdev) {
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  3253
		napi_enable(&adapter->napi);
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  3254
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  3255
		e1000_irq_enable(adapter);
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  3256
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  3257
		netif_start_queue(netdev);
f62b64fdbc23 Fixed e1000_open() in e1000e drivers.
Florian Pose <fp@igh-essen.com>
parents: 2472
diff changeset
  3258
	}
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3259
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3260
	/* fire a link status change interrupt to start the watchdog */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3261
	ew32(ICS, E1000_ICS_LSC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3262
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3263
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3264
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3265
err_req_irq:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3266
	e1000_release_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3267
	e1000_power_down_phy(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3268
	e1000e_free_rx_resources(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3269
err_setup_rx:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3270
	e1000e_free_tx_resources(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3271
err_setup_tx:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3272
	e1000e_reset(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3273
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3274
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3275
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3276
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3277
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3278
 * e1000_close - Disables a network interface
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3279
 * @netdev: network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3280
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3281
 * Returns 0, this is not allowed to fail
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3282
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3283
 * The close entry point is called when an interface is de-activated
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3284
 * by the OS.  The hardware is still under the drivers control, but
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3285
 * needs to be disabled.  A global MAC reset is issued to stop the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3286
 * hardware, and all transmit and receive resources are freed.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3287
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3288
static int e1000_close(struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3289
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3290
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3291
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3292
	WARN_ON(test_bit(__E1000_RESETTING, &adapter->state));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3293
	e1000e_down(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3294
	e1000_power_down_phy(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3295
	e1000_free_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3296
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3297
	e1000e_free_tx_resources(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3298
	e1000e_free_rx_resources(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3299
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3300
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3301
	 * kill manageability vlan ID if supported, but not if a vlan with
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3302
	 * the same ID is registered on the host OS (let 8021q kill it)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3303
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3304
	if ((adapter->hw.mng_cookie.status &
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3305
			  E1000_MNG_DHCP_COOKIE_STATUS_VLAN) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3306
	     !(adapter->vlgrp &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3307
	       vlan_group_get_device(adapter->vlgrp, adapter->mng_vlan_id)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3308
		e1000_vlan_rx_kill_vid(netdev, adapter->mng_vlan_id);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3309
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3310
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3311
	 * If AMT is enabled, let the firmware know that the network
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3312
	 * interface is now closed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3313
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3314
	if (adapter->flags & FLAG_HAS_AMT)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3315
		e1000_release_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3316
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3317
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3318
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3319
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3320
 * e1000_set_mac - Change the Ethernet Address of the NIC
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3321
 * @netdev: network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3322
 * @p: pointer to an address structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3323
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3324
 * Returns 0 on success, negative on failure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3325
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3326
static int e1000_set_mac(struct net_device *netdev, void *p)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3327
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3328
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3329
	struct sockaddr *addr = p;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3330
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3331
	if (!is_valid_ether_addr(addr->sa_data))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3332
		return -EADDRNOTAVAIL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3333
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3334
	memcpy(netdev->dev_addr, addr->sa_data, netdev->addr_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3335
	memcpy(adapter->hw.mac.addr, addr->sa_data, netdev->addr_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3336
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3337
	e1000e_rar_set(&adapter->hw, adapter->hw.mac.addr, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3338
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3339
	if (adapter->flags & FLAG_RESET_OVERWRITES_LAA) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3340
		/* activate the work around */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3341
		e1000e_set_laa_state_82571(&adapter->hw, 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3342
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3343
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3344
		 * Hold a copy of the LAA in RAR[14] This is done so that
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3345
		 * between the time RAR[0] gets clobbered  and the time it
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3346
		 * gets fixed (in e1000_watchdog), the actual LAA is in one
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3347
		 * of the RARs and no incoming packets directed to this port
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3348
		 * are dropped. Eventually the LAA will be in RAR[0] and
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3349
		 * RAR[14]
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3350
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3351
		e1000e_rar_set(&adapter->hw,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3352
			      adapter->hw.mac.addr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3353
			      adapter->hw.mac.rar_entry_count - 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3354
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3355
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3356
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3357
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3358
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3359
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3360
 * e1000e_update_phy_task - work thread to update phy
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3361
 * @work: pointer to our work struct
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3362
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3363
 * this worker thread exists because we must acquire a
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3364
 * semaphore to read the phy, which we could msleep while
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3365
 * waiting for it, and we can't msleep in a timer.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3366
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3367
static void e1000e_update_phy_task(struct work_struct *work)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3368
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3369
	struct e1000_adapter *adapter = container_of(work,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3370
					struct e1000_adapter, update_phy_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3371
	e1000_get_phy_info(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3372
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3373
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3374
/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3375
 * Need to wait a few seconds after link up to get diagnostic information from
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3376
 * the phy
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3377
 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3378
static void e1000_update_phy_info(unsigned long data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3379
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3380
	struct e1000_adapter *adapter = (struct e1000_adapter *) data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3381
	schedule_work(&adapter->update_phy_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3382
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3383
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3384
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3385
 * e1000e_update_stats - Update the board statistics counters
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3386
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3387
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3388
void e1000e_update_stats(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3389
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3390
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3391
	struct pci_dev *pdev = adapter->pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3392
	u16 phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3393
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3394
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3395
	 * Prevent stats update while adapter is being reset, or if the pci
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3396
	 * connection is down.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3397
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3398
	if (adapter->link_speed == 0)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3399
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3400
	if (pci_channel_offline(pdev))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3401
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3402
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3403
	adapter->stats.crcerrs += er32(CRCERRS);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3404
	adapter->stats.gprc += er32(GPRC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3405
	adapter->stats.gorc += er32(GORCL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3406
	er32(GORCH); /* Clear gorc */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3407
	adapter->stats.bprc += er32(BPRC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3408
	adapter->stats.mprc += er32(MPRC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3409
	adapter->stats.roc += er32(ROC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3410
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3411
	adapter->stats.mpc += er32(MPC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3412
	if ((hw->phy.type == e1000_phy_82578) ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3413
	    (hw->phy.type == e1000_phy_82577)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3414
		e1e_rphy(hw, HV_SCC_UPPER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3415
		e1e_rphy(hw, HV_SCC_LOWER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3416
		adapter->stats.scc += phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3417
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3418
		e1e_rphy(hw, HV_ECOL_UPPER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3419
		e1e_rphy(hw, HV_ECOL_LOWER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3420
		adapter->stats.ecol += phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3421
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3422
		e1e_rphy(hw, HV_MCC_UPPER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3423
		e1e_rphy(hw, HV_MCC_LOWER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3424
		adapter->stats.mcc += phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3425
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3426
		e1e_rphy(hw, HV_LATECOL_UPPER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3427
		e1e_rphy(hw, HV_LATECOL_LOWER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3428
		adapter->stats.latecol += phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3429
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3430
		e1e_rphy(hw, HV_DC_UPPER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3431
		e1e_rphy(hw, HV_DC_LOWER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3432
		adapter->stats.dc += phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3433
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3434
		adapter->stats.scc += er32(SCC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3435
		adapter->stats.ecol += er32(ECOL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3436
		adapter->stats.mcc += er32(MCC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3437
		adapter->stats.latecol += er32(LATECOL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3438
		adapter->stats.dc += er32(DC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3439
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3440
	adapter->stats.xonrxc += er32(XONRXC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3441
	adapter->stats.xontxc += er32(XONTXC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3442
	adapter->stats.xoffrxc += er32(XOFFRXC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3443
	adapter->stats.xofftxc += er32(XOFFTXC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3444
	adapter->stats.gptc += er32(GPTC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3445
	adapter->stats.gotc += er32(GOTCL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3446
	er32(GOTCH); /* Clear gotc */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3447
	adapter->stats.rnbc += er32(RNBC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3448
	adapter->stats.ruc += er32(RUC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3449
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3450
	adapter->stats.mptc += er32(MPTC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3451
	adapter->stats.bptc += er32(BPTC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3452
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3453
	/* used for adaptive IFS */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3454
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3455
	hw->mac.tx_packet_delta = er32(TPT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3456
	adapter->stats.tpt += hw->mac.tx_packet_delta;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3457
	if ((hw->phy.type == e1000_phy_82578) ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3458
	    (hw->phy.type == e1000_phy_82577)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3459
		e1e_rphy(hw, HV_COLC_UPPER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3460
		e1e_rphy(hw, HV_COLC_LOWER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3461
		hw->mac.collision_delta = phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3462
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3463
		hw->mac.collision_delta = er32(COLC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3464
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3465
	adapter->stats.colc += hw->mac.collision_delta;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3466
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3467
	adapter->stats.algnerrc += er32(ALGNERRC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3468
	adapter->stats.rxerrc += er32(RXERRC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3469
	if ((hw->phy.type == e1000_phy_82578) ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3470
	    (hw->phy.type == e1000_phy_82577)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3471
		e1e_rphy(hw, HV_TNCRS_UPPER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3472
		e1e_rphy(hw, HV_TNCRS_LOWER, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3473
		adapter->stats.tncrs += phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3474
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3475
		if ((hw->mac.type != e1000_82574) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3476
		    (hw->mac.type != e1000_82583))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3477
			adapter->stats.tncrs += er32(TNCRS);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3478
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3479
	adapter->stats.cexterr += er32(CEXTERR);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3480
	adapter->stats.tsctc += er32(TSCTC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3481
	adapter->stats.tsctfc += er32(TSCTFC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3482
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3483
	/* Fill out the OS statistics structure */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3484
	adapter->net_stats.multicast = adapter->stats.mprc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3485
	adapter->net_stats.collisions = adapter->stats.colc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3486
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3487
	/* Rx Errors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3488
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3489
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3490
	 * RLEC on some newer hardware can be incorrect so build
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3491
	 * our own version based on RUC and ROC
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3492
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3493
	adapter->net_stats.rx_errors = adapter->stats.rxerrc +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3494
		adapter->stats.crcerrs + adapter->stats.algnerrc +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3495
		adapter->stats.ruc + adapter->stats.roc +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3496
		adapter->stats.cexterr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3497
	adapter->net_stats.rx_length_errors = adapter->stats.ruc +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3498
					      adapter->stats.roc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3499
	adapter->net_stats.rx_crc_errors = adapter->stats.crcerrs;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3500
	adapter->net_stats.rx_frame_errors = adapter->stats.algnerrc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3501
	adapter->net_stats.rx_missed_errors = adapter->stats.mpc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3502
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3503
	/* Tx Errors */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3504
	adapter->net_stats.tx_errors = adapter->stats.ecol +
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3505
				       adapter->stats.latecol;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3506
	adapter->net_stats.tx_aborted_errors = adapter->stats.ecol;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3507
	adapter->net_stats.tx_window_errors = adapter->stats.latecol;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3508
	adapter->net_stats.tx_carrier_errors = adapter->stats.tncrs;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3509
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3510
	/* Tx Dropped needs to be maintained elsewhere */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3511
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3512
	/* Management Stats */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3513
	adapter->stats.mgptc += er32(MGTPTC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3514
	adapter->stats.mgprc += er32(MGTPRC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3515
	adapter->stats.mgpdc += er32(MGTPDC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3516
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3517
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3518
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3519
 * e1000_phy_read_status - Update the PHY register status snapshot
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3520
 * @adapter: board private structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3521
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3522
static void e1000_phy_read_status(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3523
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3524
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3525
	struct e1000_phy_regs *phy = &adapter->phy_regs;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3526
	int ret_val;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3527
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3528
	if ((er32(STATUS) & E1000_STATUS_LU) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3529
	    (adapter->hw.phy.media_type == e1000_media_type_copper)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3530
		ret_val  = e1e_rphy(hw, PHY_CONTROL, &phy->bmcr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3531
		ret_val |= e1e_rphy(hw, PHY_STATUS, &phy->bmsr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3532
		ret_val |= e1e_rphy(hw, PHY_AUTONEG_ADV, &phy->advertise);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3533
		ret_val |= e1e_rphy(hw, PHY_LP_ABILITY, &phy->lpa);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3534
		ret_val |= e1e_rphy(hw, PHY_AUTONEG_EXP, &phy->expansion);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3535
		ret_val |= e1e_rphy(hw, PHY_1000T_CTRL, &phy->ctrl1000);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3536
		ret_val |= e1e_rphy(hw, PHY_1000T_STATUS, &phy->stat1000);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3537
		ret_val |= e1e_rphy(hw, PHY_EXT_STATUS, &phy->estatus);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3538
		if (ret_val)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3539
			e_warn("Error reading PHY register\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3540
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3541
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3542
		 * Do not read PHY registers if link is not up
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3543
		 * Set values to typical power-on defaults
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3544
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3545
		phy->bmcr = (BMCR_SPEED1000 | BMCR_ANENABLE | BMCR_FULLDPLX);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3546
		phy->bmsr = (BMSR_100FULL | BMSR_100HALF | BMSR_10FULL |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3547
			     BMSR_10HALF | BMSR_ESTATEN | BMSR_ANEGCAPABLE |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3548
			     BMSR_ERCAP);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3549
		phy->advertise = (ADVERTISE_PAUSE_ASYM | ADVERTISE_PAUSE_CAP |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3550
				  ADVERTISE_ALL | ADVERTISE_CSMA);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3551
		phy->lpa = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3552
		phy->expansion = EXPANSION_ENABLENPAGE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3553
		phy->ctrl1000 = ADVERTISE_1000FULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3554
		phy->stat1000 = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3555
		phy->estatus = (ESTATUS_1000_TFULL | ESTATUS_1000_THALF);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3556
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3557
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3558
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3559
static void e1000_print_link_info(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3560
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3561
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3562
	u32 ctrl = er32(CTRL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3563
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3564
	/* Link status message must follow this format for user tools */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3565
	printk(KERN_INFO "e1000e: %s NIC Link is Up %d Mbps %s, "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3566
	       "Flow Control: %s\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3567
	       adapter->netdev->name,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3568
	       adapter->link_speed,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3569
	       (adapter->link_duplex == FULL_DUPLEX) ?
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3570
	                        "Full Duplex" : "Half Duplex",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3571
	       ((ctrl & E1000_CTRL_TFCE) && (ctrl & E1000_CTRL_RFCE)) ?
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3572
	                        "RX/TX" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3573
	       ((ctrl & E1000_CTRL_RFCE) ? "RX" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3574
	       ((ctrl & E1000_CTRL_TFCE) ? "TX" : "None" )));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3575
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3576
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3577
bool e1000_has_link(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3578
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3579
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3580
	bool link_active = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3581
	s32 ret_val = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3582
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3583
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3584
	 * get_link_status is set on LSC (link status) interrupt or
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3585
	 * Rx sequence error interrupt.  get_link_status will stay
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3586
	 * false until the check_for_link establishes link
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3587
	 * for copper adapters ONLY
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3588
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3589
	switch (hw->phy.media_type) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3590
	case e1000_media_type_copper:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3591
		if (hw->mac.get_link_status) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3592
			ret_val = hw->mac.ops.check_for_link(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3593
			link_active = !hw->mac.get_link_status;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3594
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3595
			link_active = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3596
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3597
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3598
	case e1000_media_type_fiber:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3599
		ret_val = hw->mac.ops.check_for_link(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3600
		link_active = !!(er32(STATUS) & E1000_STATUS_LU);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3601
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3602
	case e1000_media_type_internal_serdes:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3603
		ret_val = hw->mac.ops.check_for_link(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3604
		link_active = adapter->hw.mac.serdes_has_link;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3605
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3606
	default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3607
	case e1000_media_type_unknown:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3608
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3609
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3610
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3611
	if ((ret_val == E1000_ERR_PHY) && (hw->phy.type == e1000_phy_igp_3) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3612
	    (er32(CTRL) & E1000_PHY_CTRL_GBE_DISABLE)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3613
		/* See e1000_kmrn_lock_loss_workaround_ich8lan() */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3614
		e_info("Gigabit has been disabled, downgrading speed\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3615
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3616
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3617
	return link_active;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3618
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3619
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3620
static void e1000e_enable_receives(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3621
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3622
	/* make sure the receive unit is started */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3623
	if ((adapter->flags & FLAG_RX_NEEDS_RESTART) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3624
	    (adapter->flags & FLAG_RX_RESTART_NOW)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3625
		struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3626
		u32 rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3627
		ew32(RCTL, rctl | E1000_RCTL_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3628
		adapter->flags &= ~FLAG_RX_RESTART_NOW;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3629
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3630
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3631
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3632
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3633
 * e1000_watchdog - Timer Call-back
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3634
 * @data: pointer to adapter cast into an unsigned long
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3635
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3636
static void e1000_watchdog(unsigned long data)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3637
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3638
	struct e1000_adapter *adapter = (struct e1000_adapter *) data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3639
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3640
	/* Do the rest outside of interrupt context */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3641
	schedule_work(&adapter->watchdog_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3642
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3643
	/* TODO: make this use queue_delayed_work() */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3644
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3645
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3646
static void e1000_watchdog_task(struct work_struct *work)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3647
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3648
	struct e1000_adapter *adapter = container_of(work,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3649
					struct e1000_adapter, watchdog_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3650
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3651
	struct e1000_mac_info *mac = &adapter->hw.mac;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3652
	struct e1000_phy_info *phy = &adapter->hw.phy;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3653
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3654
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3655
	u32 link, tctl;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3656
	int tx_pending = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3657
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3658
	link = e1000_has_link(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3659
	if ((adapter->ecdev && (ecdev_get_link(adapter->ecdev)) && link)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3660
			|| (!adapter->ecdev && (netif_carrier_ok(netdev)) && link)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3661
		e1000e_enable_receives(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3662
		goto link_up;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3663
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3664
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3665
	if ((e1000e_enable_tx_pkt_filtering(hw)) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3666
	    (adapter->mng_vlan_id != adapter->hw.mng_cookie.vlan_id))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3667
		e1000_update_mng_vlan(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3668
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3669
	if (link) {
2421
bc2d4bf9cbe5 Removed trailing spaces.
Florian Pose <fp@igh-essen.com>
parents: 2217
diff changeset
  3670
		if ((adapter->ecdev && !ecdev_get_link(adapter->ecdev))
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3671
				|| (!adapter->ecdev && !netif_carrier_ok(netdev))) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3672
			bool txb2b = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3673
			/* update snapshot of PHY registers on LSC */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3674
			e1000_phy_read_status(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3675
			mac->ops.get_link_up_info(&adapter->hw,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3676
						   &adapter->link_speed,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3677
						   &adapter->link_duplex);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3678
			e1000_print_link_info(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3679
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3680
			 * On supported PHYs, check for duplex mismatch only
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3681
			 * if link has autonegotiated at 10/100 half
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3682
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3683
			if ((hw->phy.type == e1000_phy_igp_3 ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3684
			     hw->phy.type == e1000_phy_bm) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3685
			    (hw->mac.autoneg == true) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3686
			    (adapter->link_speed == SPEED_10 ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3687
			     adapter->link_speed == SPEED_100) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3688
			    (adapter->link_duplex == HALF_DUPLEX)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3689
				u16 autoneg_exp;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3690
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3691
				e1e_rphy(hw, PHY_AUTONEG_EXP, &autoneg_exp);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3692
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3693
				if (!(autoneg_exp & NWAY_ER_LP_NWAY_CAPS))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3694
					e_info("Autonegotiated half duplex but"
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3695
					       " link partner cannot autoneg. "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3696
					       " Try forcing full duplex if "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3697
					       "link gets many collisions.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3698
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3699
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3700
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3701
			 * tweak tx_queue_len according to speed/duplex
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3702
			 * and adjust the timeout factor
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3703
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3704
			netdev->tx_queue_len = adapter->tx_queue_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3705
			adapter->tx_timeout_factor = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3706
			switch (adapter->link_speed) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3707
			case SPEED_10:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3708
				txb2b = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3709
				netdev->tx_queue_len = 10;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3710
				adapter->tx_timeout_factor = 16;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3711
				break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3712
			case SPEED_100:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3713
				txb2b = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3714
				netdev->tx_queue_len = 100;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3715
				adapter->tx_timeout_factor = 10;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3716
				break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3717
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3718
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3719
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3720
			 * workaround: re-program speed mode bit after
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3721
			 * link-up event
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3722
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3723
			if ((adapter->flags & FLAG_TARC_SPEED_MODE_BIT) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3724
			    !txb2b) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3725
				u32 tarc0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3726
				tarc0 = er32(TARC(0));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3727
				tarc0 &= ~SPEED_MODE_BIT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3728
				ew32(TARC(0), tarc0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3729
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3730
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3731
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3732
			 * disable TSO for pcie and 10/100 speeds, to avoid
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3733
			 * some hardware issues
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3734
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3735
			if (!(adapter->flags & FLAG_TSO_FORCE)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3736
				switch (adapter->link_speed) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3737
				case SPEED_10:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3738
				case SPEED_100:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3739
					e_info("10/100 speed: disabling TSO\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3740
					netdev->features &= ~NETIF_F_TSO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3741
					netdev->features &= ~NETIF_F_TSO6;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3742
					break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3743
				case SPEED_1000:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3744
					netdev->features |= NETIF_F_TSO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3745
					netdev->features |= NETIF_F_TSO6;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3746
					break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3747
				default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3748
					/* oops */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3749
					break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3750
				}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3751
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3752
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3753
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3754
			 * enable transmits in the hardware, need to do this
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3755
			 * after setting TARC(0)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3756
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3757
			tctl = er32(TCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3758
			tctl |= E1000_TCTL_EN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3759
			ew32(TCTL, tctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3760
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3761
                        /*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3762
			 * Perform any post-link-up configuration before
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3763
			 * reporting link up.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3764
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3765
			if (phy->ops.cfg_on_link_up)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3766
				phy->ops.cfg_on_link_up(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3767
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3768
			if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3769
				ecdev_set_link(adapter->ecdev, 1);
2421
bc2d4bf9cbe5 Removed trailing spaces.
Florian Pose <fp@igh-essen.com>
parents: 2217
diff changeset
  3770
			else
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3771
				netif_carrier_on(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3772
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3773
			if (!adapter->ecdev && !test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3774
				mod_timer(&adapter->phy_info_timer,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3775
					  round_jiffies(jiffies + 2 * HZ));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3776
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3777
	} else {
2421
bc2d4bf9cbe5 Removed trailing spaces.
Florian Pose <fp@igh-essen.com>
parents: 2217
diff changeset
  3778
		if ((adapter->ecdev && ecdev_get_link(adapter->ecdev))
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3779
				|| (!adapter->ecdev && netif_carrier_ok(netdev))) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3780
			adapter->link_speed = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3781
			adapter->link_duplex = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3782
			/* Link status message must follow this format */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3783
			printk(KERN_INFO "e1000e: %s NIC Link is Down\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3784
			       adapter->netdev->name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3785
			if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3786
				ecdev_set_link(adapter->ecdev, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3787
			else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3788
				netif_carrier_off(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3789
			if (!adapter->ecdev && !test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3790
				mod_timer(&adapter->phy_info_timer,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3791
					  round_jiffies(jiffies + 2 * HZ));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3792
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3793
			if (adapter->flags & FLAG_RX_NEEDS_RESTART)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3794
				schedule_work(&adapter->reset_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3795
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3796
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3797
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3798
link_up:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3799
	e1000e_update_stats(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3800
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3801
	mac->tx_packet_delta = adapter->stats.tpt - adapter->tpt_old;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3802
	adapter->tpt_old = adapter->stats.tpt;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3803
	mac->collision_delta = adapter->stats.colc - adapter->colc_old;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3804
	adapter->colc_old = adapter->stats.colc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3805
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3806
	adapter->gorc = adapter->stats.gorc - adapter->gorc_old;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3807
	adapter->gorc_old = adapter->stats.gorc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3808
	adapter->gotc = adapter->stats.gotc - adapter->gotc_old;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3809
	adapter->gotc_old = adapter->stats.gotc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3810
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3811
	e1000e_update_adaptive(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3812
2500
97fd83907c7c Fixed repeating e1000e reset while link down, thanks to J. Kunz.
Florian Pose <fp@igh-essen.com>
parents: 2473
diff changeset
  3813
	if (!adapter->ecdev && !netif_carrier_ok(netdev)) {
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3814
		tx_pending = (e1000_desc_unused(tx_ring) + 1 <
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3815
			       tx_ring->count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3816
		if (tx_pending) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3817
			/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3818
			 * We've lost link, so the controller stops DMA,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3819
			 * but we've got queued Tx work that's never going
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3820
			 * to get done, so reset controller to flush Tx.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3821
			 * (Do the reset outside of interrupt context).
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3822
			 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3823
			adapter->tx_timeout_count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3824
			schedule_work(&adapter->reset_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3825
			/* return immediately since reset is imminent */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3826
			return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3827
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3828
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3829
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3830
	/* Cause software interrupt to ensure Rx ring is cleaned */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3831
	if (adapter->msix_entries)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3832
		ew32(ICS, adapter->rx_ring->ims_val);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3833
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3834
		ew32(ICS, E1000_ICS_RXDMT0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3835
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3836
	/* Force detection of hung controller every watchdog period */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3837
	adapter->detect_tx_hung = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3838
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3839
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3840
	 * With 82571 controllers, LAA may be overwritten due to controller
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3841
	 * reset from the other port. Set the appropriate LAA in RAR[0]
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3842
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3843
	if (e1000e_get_laa_state_82571(hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3844
		e1000e_rar_set(hw, adapter->hw.mac.addr, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3845
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3846
	/* Reset the timer */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3847
	if (!adapter->ecdev && !test_bit(__E1000_DOWN, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3848
		mod_timer(&adapter->watchdog_timer,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3849
			  round_jiffies(jiffies + 2 * HZ));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3850
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3851
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3852
#define E1000_TX_FLAGS_CSUM		0x00000001
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3853
#define E1000_TX_FLAGS_VLAN		0x00000002
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3854
#define E1000_TX_FLAGS_TSO		0x00000004
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3855
#define E1000_TX_FLAGS_IPV4		0x00000008
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3856
#define E1000_TX_FLAGS_VLAN_MASK	0xffff0000
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3857
#define E1000_TX_FLAGS_VLAN_SHIFT	16
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3858
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3859
static int e1000_tso(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3860
		     struct sk_buff *skb)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3861
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3862
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3863
	struct e1000_context_desc *context_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3864
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3865
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3866
	u32 cmd_length = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3867
	u16 ipcse = 0, tucse, mss;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3868
	u8 ipcss, ipcso, tucss, tucso, hdr_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3869
	int err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3870
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3871
	if (skb_is_gso(skb)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3872
		if (skb_header_cloned(skb)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3873
			err = pskb_expand_head(skb, 0, 0, GFP_ATOMIC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3874
			if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3875
				return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3876
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3877
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3878
		hdr_len = skb_transport_offset(skb) + tcp_hdrlen(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3879
		mss = skb_shinfo(skb)->gso_size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3880
		if (skb->protocol == htons(ETH_P_IP)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3881
			struct iphdr *iph = ip_hdr(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3882
			iph->tot_len = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3883
			iph->check = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3884
			tcp_hdr(skb)->check = ~csum_tcpudp_magic(iph->saddr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3885
								 iph->daddr, 0,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3886
								 IPPROTO_TCP,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3887
								 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3888
			cmd_length = E1000_TXD_CMD_IP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3889
			ipcse = skb_transport_offset(skb) - 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3890
		} else if (skb_shinfo(skb)->gso_type == SKB_GSO_TCPV6) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3891
			ipv6_hdr(skb)->payload_len = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3892
			tcp_hdr(skb)->check =
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3893
				~csum_ipv6_magic(&ipv6_hdr(skb)->saddr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3894
						 &ipv6_hdr(skb)->daddr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3895
						 0, IPPROTO_TCP, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3896
			ipcse = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3897
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3898
		ipcss = skb_network_offset(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3899
		ipcso = (void *)&(ip_hdr(skb)->check) - (void *)skb->data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3900
		tucss = skb_transport_offset(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3901
		tucso = (void *)&(tcp_hdr(skb)->check) - (void *)skb->data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3902
		tucse = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3903
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3904
		cmd_length |= (E1000_TXD_CMD_DEXT | E1000_TXD_CMD_TSE |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3905
			       E1000_TXD_CMD_TCP | (skb->len - (hdr_len)));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3906
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3907
		i = tx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3908
		context_desc = E1000_CONTEXT_DESC(*tx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3909
		buffer_info = &tx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3910
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3911
		context_desc->lower_setup.ip_fields.ipcss  = ipcss;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3912
		context_desc->lower_setup.ip_fields.ipcso  = ipcso;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3913
		context_desc->lower_setup.ip_fields.ipcse  = cpu_to_le16(ipcse);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3914
		context_desc->upper_setup.tcp_fields.tucss = tucss;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3915
		context_desc->upper_setup.tcp_fields.tucso = tucso;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3916
		context_desc->upper_setup.tcp_fields.tucse = cpu_to_le16(tucse);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3917
		context_desc->tcp_seg_setup.fields.mss     = cpu_to_le16(mss);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3918
		context_desc->tcp_seg_setup.fields.hdr_len = hdr_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3919
		context_desc->cmd_and_length = cpu_to_le32(cmd_length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3920
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3921
		buffer_info->time_stamp = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3922
		buffer_info->next_to_watch = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3923
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3924
		i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3925
		if (i == tx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3926
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3927
		tx_ring->next_to_use = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3928
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3929
		return 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3930
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3931
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3932
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3933
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3934
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3935
static bool e1000_tx_csum(struct e1000_adapter *adapter, struct sk_buff *skb)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3936
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3937
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3938
	struct e1000_context_desc *context_desc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3939
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3940
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3941
	u8 css;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3942
	u32 cmd_len = E1000_TXD_CMD_DEXT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3943
	__be16 protocol;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3944
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3945
	if (skb->ip_summed != CHECKSUM_PARTIAL)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3946
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3947
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3948
	if (skb->protocol == cpu_to_be16(ETH_P_8021Q))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3949
		protocol = vlan_eth_hdr(skb)->h_vlan_encapsulated_proto;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3950
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3951
		protocol = skb->protocol;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3952
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3953
	switch (protocol) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3954
	case cpu_to_be16(ETH_P_IP):
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3955
		if (ip_hdr(skb)->protocol == IPPROTO_TCP)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3956
			cmd_len |= E1000_TXD_CMD_TCP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3957
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3958
	case cpu_to_be16(ETH_P_IPV6):
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3959
		/* XXX not handling all IPV6 headers */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3960
		if (ipv6_hdr(skb)->nexthdr == IPPROTO_TCP)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3961
			cmd_len |= E1000_TXD_CMD_TCP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3962
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3963
	default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3964
		if (unlikely(net_ratelimit()))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3965
			e_warn("checksum_partial proto=%x!\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3966
			       be16_to_cpu(protocol));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3967
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3968
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3969
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3970
	css = skb_transport_offset(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3971
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3972
	i = tx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3973
	buffer_info = &tx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3974
	context_desc = E1000_CONTEXT_DESC(*tx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3975
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3976
	context_desc->lower_setup.ip_config = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3977
	context_desc->upper_setup.tcp_fields.tucss = css;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3978
	context_desc->upper_setup.tcp_fields.tucso =
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3979
				css + skb->csum_offset;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3980
	context_desc->upper_setup.tcp_fields.tucse = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3981
	context_desc->tcp_seg_setup.data = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3982
	context_desc->cmd_and_length = cpu_to_le32(cmd_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3983
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3984
	buffer_info->time_stamp = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3985
	buffer_info->next_to_watch = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3986
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3987
	i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3988
	if (i == tx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3989
		i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3990
	tx_ring->next_to_use = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3991
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3992
	return 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3993
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3994
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3995
#define E1000_MAX_PER_TXD	8192
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3996
#define E1000_MAX_TXD_PWR	12
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3997
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3998
static int e1000_tx_map(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  3999
			struct sk_buff *skb, unsigned int first,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4000
			unsigned int max_per_txd, unsigned int nr_frags,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4001
			unsigned int mss)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4002
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4003
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4004
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4005
	unsigned int len = skb_headlen(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4006
	unsigned int offset, size, count = 0, i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4007
	unsigned int f;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4008
	dma_addr_t *map;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4009
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4010
	i = tx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4011
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4012
	if (skb_dma_map(&adapter->pdev->dev, skb, DMA_TO_DEVICE)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4013
		dev_err(&adapter->pdev->dev, "TX DMA map failed\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4014
		adapter->tx_dma_failed++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4015
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4016
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4017
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4018
	map = skb_shinfo(skb)->dma_maps;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4019
	offset = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4020
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4021
	while (len) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4022
		buffer_info = &tx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4023
		size = min(len, max_per_txd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4024
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4025
		buffer_info->length = size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4026
		buffer_info->time_stamp = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4027
		buffer_info->next_to_watch = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4028
		buffer_info->dma = skb_shinfo(skb)->dma_head + offset;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4029
		count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4030
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4031
		len -= size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4032
		offset += size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4033
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4034
		if (len) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4035
			i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4036
			if (i == tx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4037
				i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4038
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4039
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4040
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4041
	for (f = 0; f < nr_frags; f++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4042
		struct skb_frag_struct *frag;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4043
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4044
		frag = &skb_shinfo(skb)->frags[f];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4045
		len = frag->size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4046
		offset = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4047
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4048
		while (len) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4049
			i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4050
			if (i == tx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4051
				i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4052
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4053
			buffer_info = &tx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4054
			size = min(len, max_per_txd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4055
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4056
			buffer_info->length = size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4057
			buffer_info->time_stamp = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4058
			buffer_info->next_to_watch = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4059
			buffer_info->dma = map[f] + offset;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4060
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4061
			len -= size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4062
			offset += size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4063
			count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4064
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4065
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4066
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4067
	tx_ring->buffer_info[i].skb = skb;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4068
	tx_ring->buffer_info[first].next_to_watch = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4069
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4070
	return count;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4071
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4072
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4073
static void e1000_tx_queue(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4074
			   int tx_flags, int count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4075
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4076
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4077
	struct e1000_tx_desc *tx_desc = NULL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4078
	struct e1000_buffer *buffer_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4079
	u32 txd_upper = 0, txd_lower = E1000_TXD_CMD_IFCS;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4080
	unsigned int i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4081
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4082
	if (tx_flags & E1000_TX_FLAGS_TSO) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4083
		txd_lower |= E1000_TXD_CMD_DEXT | E1000_TXD_DTYP_D |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4084
			     E1000_TXD_CMD_TSE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4085
		txd_upper |= E1000_TXD_POPTS_TXSM << 8;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4086
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4087
		if (tx_flags & E1000_TX_FLAGS_IPV4)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4088
			txd_upper |= E1000_TXD_POPTS_IXSM << 8;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4089
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4090
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4091
	if (tx_flags & E1000_TX_FLAGS_CSUM) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4092
		txd_lower |= E1000_TXD_CMD_DEXT | E1000_TXD_DTYP_D;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4093
		txd_upper |= E1000_TXD_POPTS_TXSM << 8;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4094
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4095
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4096
	if (tx_flags & E1000_TX_FLAGS_VLAN) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4097
		txd_lower |= E1000_TXD_CMD_VLE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4098
		txd_upper |= (tx_flags & E1000_TX_FLAGS_VLAN_MASK);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4099
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4100
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4101
	i = tx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4102
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4103
	while (count--) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4104
		buffer_info = &tx_ring->buffer_info[i];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4105
		tx_desc = E1000_TX_DESC(*tx_ring, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4106
		tx_desc->buffer_addr = cpu_to_le64(buffer_info->dma);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4107
		tx_desc->lower.data =
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4108
			cpu_to_le32(txd_lower | buffer_info->length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4109
		tx_desc->upper.data = cpu_to_le32(txd_upper);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4110
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4111
		i++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4112
		if (i == tx_ring->count)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4113
			i = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4114
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4115
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4116
	tx_desc->lower.data |= cpu_to_le32(adapter->txd_cmd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4117
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4118
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4119
	 * Force memory writes to complete before letting h/w
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4120
	 * know there are new descriptors to fetch.  (Only
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4121
	 * applicable for weak-ordered memory model archs,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4122
	 * such as IA-64).
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4123
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4124
	wmb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4125
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4126
	tx_ring->next_to_use = i;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4127
	writel(i, adapter->hw.hw_addr + tx_ring->tail);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4128
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4129
	 * we need this if more than one processor can write to our tail
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4130
	 * at a time, it synchronizes IO on IA64/Altix systems
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4131
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4132
	mmiowb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4133
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4134
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4135
#define MINIMUM_DHCP_PACKET_SIZE 282
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4136
static int e1000_transfer_dhcp_info(struct e1000_adapter *adapter,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4137
				    struct sk_buff *skb)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4138
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4139
	struct e1000_hw *hw =  &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4140
	u16 length, offset;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4141
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4142
	if (vlan_tx_tag_present(skb)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4143
		if (!((vlan_tx_tag_get(skb) == adapter->hw.mng_cookie.vlan_id)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4144
		    && (adapter->hw.mng_cookie.status &
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4145
			E1000_MNG_DHCP_COOKIE_STATUS_VLAN)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4146
			return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4147
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4148
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4149
	if (skb->len <= MINIMUM_DHCP_PACKET_SIZE)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4150
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4151
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4152
	if (((struct ethhdr *) skb->data)->h_proto != htons(ETH_P_IP))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4153
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4154
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4155
	{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4156
		const struct iphdr *ip = (struct iphdr *)((u8 *)skb->data+14);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4157
		struct udphdr *udp;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4158
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4159
		if (ip->protocol != IPPROTO_UDP)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4160
			return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4161
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4162
		udp = (struct udphdr *)((u8 *)ip + (ip->ihl << 2));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4163
		if (ntohs(udp->dest) != 67)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4164
			return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4165
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4166
		offset = (u8 *)udp + 8 - skb->data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4167
		length = skb->len - offset;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4168
		return e1000e_mng_write_dhcp_info(hw, (u8 *)udp + 8, length);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4169
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4170
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4171
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4172
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4173
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4174
static int __e1000_maybe_stop_tx(struct net_device *netdev, int size)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4175
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4176
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4177
2472
50b861e981f7 Fixed __e1000_maybe_stop_tx() for e1000e.
Florian Pose <fp@igh-essen.com>
parents: 2421
diff changeset
  4178
	if (adapter->ecdev) {
50b861e981f7 Fixed __e1000_maybe_stop_tx() for e1000e.
Florian Pose <fp@igh-essen.com>
parents: 2421
diff changeset
  4179
		return -EBUSY;
50b861e981f7 Fixed __e1000_maybe_stop_tx() for e1000e.
Florian Pose <fp@igh-essen.com>
parents: 2421
diff changeset
  4180
	}
50b861e981f7 Fixed __e1000_maybe_stop_tx() for e1000e.
Florian Pose <fp@igh-essen.com>
parents: 2421
diff changeset
  4181
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4182
	netif_stop_queue(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4183
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4184
	 * Herbert's original patch had:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4185
	 *  smp_mb__after_netif_stop_queue();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4186
	 * but since that doesn't exist yet, just open code it.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4187
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4188
	smp_mb();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4189
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4190
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4191
	 * We need to check again in a case another CPU has just
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4192
	 * made room available.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4193
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4194
	if (e1000_desc_unused(adapter->tx_ring) < size)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4195
		return -EBUSY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4196
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4197
	/* A reprieve! */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4198
	netif_start_queue(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4199
	++adapter->restart_queue;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4200
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4201
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4202
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4203
static int e1000_maybe_stop_tx(struct net_device *netdev, int size)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4204
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4205
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4206
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4207
	if (e1000_desc_unused(adapter->tx_ring) >= size)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4208
		return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4209
	return __e1000_maybe_stop_tx(netdev, size);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4210
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4211
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4212
#define TXD_USE_COUNT(S, X) (((S) >> (X)) + 1 )
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4213
static netdev_tx_t e1000_xmit_frame(struct sk_buff *skb,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4214
				    struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4215
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4216
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4217
	struct e1000_ring *tx_ring = adapter->tx_ring;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4218
	unsigned int first;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4219
	unsigned int max_per_txd = E1000_MAX_PER_TXD;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4220
	unsigned int max_txd_pwr = E1000_MAX_TXD_PWR;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4221
	unsigned int tx_flags = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4222
	unsigned int len = skb->len - skb->data_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4223
	unsigned int nr_frags;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4224
	unsigned int mss;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4225
	int count = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4226
	int tso;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4227
	unsigned int f;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4228
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4229
	if (test_bit(__E1000_DOWN, &adapter->state)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4230
		if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4231
			dev_kfree_skb_any(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4232
		return NETDEV_TX_OK;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4233
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4234
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4235
	if (skb->len <= 0) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4236
		if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4237
			dev_kfree_skb_any(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4238
		return NETDEV_TX_OK;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4239
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4240
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4241
	mss = skb_shinfo(skb)->gso_size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4242
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4243
	 * The controller does a simple calculation to
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4244
	 * make sure there is enough room in the FIFO before
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4245
	 * initiating the DMA for each buffer.  The calc is:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4246
	 * 4 = ceil(buffer len/mss).  To make sure we don't
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4247
	 * overrun the FIFO, adjust the max buffer len if mss
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4248
	 * drops.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4249
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4250
	if (mss) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4251
		u8 hdr_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4252
		max_per_txd = min(mss << 2, max_per_txd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4253
		max_txd_pwr = fls(max_per_txd) - 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4254
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4255
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4256
		 * TSO Workaround for 82571/2/3 Controllers -- if skb->data
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4257
		 * points to just header, pull a few bytes of payload from
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4258
		 * frags into skb->data
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4259
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4260
		hdr_len = skb_transport_offset(skb) + tcp_hdrlen(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4261
		/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4262
		 * we do this workaround for ES2LAN, but it is un-necessary,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4263
		 * avoiding it could save a lot of cycles
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4264
		 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4265
		if (skb->data_len && (hdr_len == len)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4266
			unsigned int pull_size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4267
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4268
			pull_size = min((unsigned int)4, skb->data_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4269
			if (!__pskb_pull_tail(skb, pull_size)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4270
				e_err("__pskb_pull_tail failed.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4271
				if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4272
					dev_kfree_skb_any(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4273
				return NETDEV_TX_OK;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4274
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4275
			len = skb->len - skb->data_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4276
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4277
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4278
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4279
	/* reserve a descriptor for the offload context */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4280
	if ((mss) || (skb->ip_summed == CHECKSUM_PARTIAL))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4281
		count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4282
	count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4283
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4284
	count += TXD_USE_COUNT(len, max_txd_pwr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4285
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4286
	nr_frags = skb_shinfo(skb)->nr_frags;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4287
	for (f = 0; f < nr_frags; f++)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4288
		count += TXD_USE_COUNT(skb_shinfo(skb)->frags[f].size,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4289
				       max_txd_pwr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4290
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4291
	if (adapter->hw.mac.tx_pkt_filtering)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4292
		e1000_transfer_dhcp_info(adapter, skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4293
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4294
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4295
	 * need: count + 2 desc gap to keep tail from touching
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4296
	 * head, otherwise try next time
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4297
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4298
	if (!adapter->ecdev && e1000_maybe_stop_tx(netdev, count + 2))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4299
		return NETDEV_TX_BUSY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4300
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4301
	if (adapter->vlgrp && vlan_tx_tag_present(skb)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4302
		tx_flags |= E1000_TX_FLAGS_VLAN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4303
		tx_flags |= (vlan_tx_tag_get(skb) << E1000_TX_FLAGS_VLAN_SHIFT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4304
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4305
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4306
	first = tx_ring->next_to_use;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4307
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4308
	tso = e1000_tso(adapter, skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4309
	if (tso < 0) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4310
		if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4311
			dev_kfree_skb_any(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4312
		return NETDEV_TX_OK;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4313
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4314
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4315
	if (tso)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4316
		tx_flags |= E1000_TX_FLAGS_TSO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4317
	else if (e1000_tx_csum(adapter, skb))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4318
		tx_flags |= E1000_TX_FLAGS_CSUM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4319
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4320
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4321
	 * Old method was to assume IPv4 packet by default if TSO was enabled.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4322
	 * 82571 hardware supports TSO capabilities for IPv6 as well...
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4323
	 * no longer assume, we must.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4324
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4325
	if (skb->protocol == htons(ETH_P_IP))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4326
		tx_flags |= E1000_TX_FLAGS_IPV4;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4327
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4328
	/* if count is 0 then mapping error has occured */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4329
	count = e1000_tx_map(adapter, skb, first, max_per_txd, nr_frags, mss);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4330
	if (count) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4331
		e1000_tx_queue(adapter, tx_flags, count);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4332
		/* Make sure there is space in the ring for the next send. */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4333
		if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4334
			e1000_maybe_stop_tx(netdev, MAX_SKB_FRAGS + 2);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4335
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4336
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4337
		if (!adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4338
			dev_kfree_skb_any(skb);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4339
		tx_ring->buffer_info[first].time_stamp = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4340
		tx_ring->next_to_use = first;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4341
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4342
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4343
	return NETDEV_TX_OK;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4344
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4345
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4346
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4347
 * e1000_tx_timeout - Respond to a Tx Hang
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4348
 * @netdev: network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4349
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4350
static void e1000_tx_timeout(struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4351
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4352
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4353
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4354
	/* Do the reset outside of interrupt context */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4355
	adapter->tx_timeout_count++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4356
	schedule_work(&adapter->reset_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4357
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4358
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4359
static void e1000_reset_task(struct work_struct *work)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4360
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4361
	struct e1000_adapter *adapter;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4362
	adapter = container_of(work, struct e1000_adapter, reset_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4363
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4364
	e1000e_reinit_locked(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4365
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4366
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4367
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4368
 * e1000_get_stats - Get System Network Statistics
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4369
 * @netdev: network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4370
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4371
 * Returns the address of the device statistics structure.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4372
 * The statistics are actually updated from the timer callback.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4373
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4374
static struct net_device_stats *e1000_get_stats(struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4375
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4376
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4377
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4378
	/* only return the current stats */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4379
	return &adapter->net_stats;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4380
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4381
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4382
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4383
 * e1000_change_mtu - Change the Maximum Transfer Unit
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4384
 * @netdev: network interface device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4385
 * @new_mtu: new value for maximum frame size
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4386
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4387
 * Returns 0 on success, negative on failure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4388
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4389
static int e1000_change_mtu(struct net_device *netdev, int new_mtu)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4390
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4391
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4392
	int max_frame = new_mtu + ETH_HLEN + ETH_FCS_LEN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4393
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4394
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4395
		return -EBUSY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4396
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4397
	/* Jumbo frame support */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4398
	if ((max_frame > ETH_FRAME_LEN + ETH_FCS_LEN) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4399
	    !(adapter->flags & FLAG_HAS_JUMBO_FRAMES)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4400
		e_err("Jumbo Frames not supported.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4401
		return -EINVAL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4402
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4403
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4404
	/* Supported frame sizes */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4405
	if ((new_mtu < ETH_ZLEN + ETH_FCS_LEN + VLAN_HLEN) ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4406
	    (max_frame > adapter->max_hw_frame_size)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4407
		e_err("Unsupported MTU setting\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4408
		return -EINVAL;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4409
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4410
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4411
	while (test_and_set_bit(__E1000_RESETTING, &adapter->state))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4412
		msleep(1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4413
	/* e1000e_down -> e1000e_reset dependent on max_frame_size & mtu */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4414
	adapter->max_frame_size = max_frame;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4415
	e_info("changing MTU from %d to %d\n", netdev->mtu, new_mtu);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4416
	netdev->mtu = new_mtu;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4417
	if (netif_running(netdev))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4418
		e1000e_down(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4419
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4420
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4421
	 * NOTE: netdev_alloc_skb reserves 16 bytes, and typically NET_IP_ALIGN
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4422
	 * means we reserve 2 more, this pushes us to allocate from the next
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4423
	 * larger slab size.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4424
	 * i.e. RXBUFFER_2048 --> size-4096 slab
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4425
	 * However with the new *_jumbo_rx* routines, jumbo receives will use
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4426
	 * fragmented skbs
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4427
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4428
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4429
	if (max_frame <= 2048)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4430
		adapter->rx_buffer_len = 2048;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4431
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4432
		adapter->rx_buffer_len = 4096;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4433
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4434
	/* adjust allocation if LPE protects us, and we aren't using SBP */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4435
	if ((max_frame == ETH_FRAME_LEN + ETH_FCS_LEN) ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4436
	     (max_frame == ETH_FRAME_LEN + VLAN_HLEN + ETH_FCS_LEN))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4437
		adapter->rx_buffer_len = ETH_FRAME_LEN + VLAN_HLEN
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4438
					 + ETH_FCS_LEN;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4439
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4440
	if (netif_running(netdev))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4441
		e1000e_up(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4442
	else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4443
		e1000e_reset(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4444
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4445
	clear_bit(__E1000_RESETTING, &adapter->state);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4446
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4447
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4448
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4449
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4450
static int e1000_mii_ioctl(struct net_device *netdev, struct ifreq *ifr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4451
			   int cmd)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4452
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4453
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4454
	struct mii_ioctl_data *data = if_mii(ifr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4455
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4456
	if (adapter->hw.phy.media_type != e1000_media_type_copper)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4457
		return -EOPNOTSUPP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4458
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4459
	switch (cmd) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4460
	case SIOCGMIIPHY:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4461
		data->phy_id = adapter->hw.phy.addr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4462
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4463
	case SIOCGMIIREG:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4464
		switch (data->reg_num & 0x1F) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4465
		case MII_BMCR:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4466
			data->val_out = adapter->phy_regs.bmcr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4467
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4468
		case MII_BMSR:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4469
			data->val_out = adapter->phy_regs.bmsr;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4470
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4471
		case MII_PHYSID1:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4472
			data->val_out = (adapter->hw.phy.id >> 16);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4473
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4474
		case MII_PHYSID2:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4475
			data->val_out = (adapter->hw.phy.id & 0xFFFF);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4476
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4477
		case MII_ADVERTISE:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4478
			data->val_out = adapter->phy_regs.advertise;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4479
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4480
		case MII_LPA:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4481
			data->val_out = adapter->phy_regs.lpa;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4482
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4483
		case MII_EXPANSION:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4484
			data->val_out = adapter->phy_regs.expansion;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4485
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4486
		case MII_CTRL1000:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4487
			data->val_out = adapter->phy_regs.ctrl1000;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4488
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4489
		case MII_STAT1000:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4490
			data->val_out = adapter->phy_regs.stat1000;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4491
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4492
		case MII_ESTATUS:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4493
			data->val_out = adapter->phy_regs.estatus;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4494
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4495
		default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4496
			return -EIO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4497
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4498
		break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4499
	case SIOCSMIIREG:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4500
	default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4501
		return -EOPNOTSUPP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4502
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4503
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4504
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4505
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4506
static int e1000_ioctl(struct net_device *netdev, struct ifreq *ifr, int cmd)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4507
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4508
	switch (cmd) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4509
	case SIOCGMIIPHY:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4510
	case SIOCGMIIREG:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4511
	case SIOCSMIIREG:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4512
		return e1000_mii_ioctl(netdev, ifr, cmd);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4513
	default:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4514
		return -EOPNOTSUPP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4515
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4516
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4517
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4518
static int e1000_init_phy_wakeup(struct e1000_adapter *adapter, u32 wufc)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4519
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4520
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4521
	u32 i, mac_reg;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4522
	u16 phy_reg;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4523
	int retval = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4524
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4525
	/* copy MAC RARs to PHY RARs */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4526
	for (i = 0; i < adapter->hw.mac.rar_entry_count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4527
		mac_reg = er32(RAL(i));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4528
		e1e_wphy(hw, BM_RAR_L(i), (u16)(mac_reg & 0xFFFF));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4529
		e1e_wphy(hw, BM_RAR_M(i), (u16)((mac_reg >> 16) & 0xFFFF));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4530
		mac_reg = er32(RAH(i));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4531
		e1e_wphy(hw, BM_RAR_H(i), (u16)(mac_reg & 0xFFFF));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4532
		e1e_wphy(hw, BM_RAR_CTRL(i), (u16)((mac_reg >> 16) & 0xFFFF));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4533
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4534
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4535
	/* copy MAC MTA to PHY MTA */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4536
	for (i = 0; i < adapter->hw.mac.mta_reg_count; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4537
		mac_reg = E1000_READ_REG_ARRAY(hw, E1000_MTA, i);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4538
		e1e_wphy(hw, BM_MTA(i), (u16)(mac_reg & 0xFFFF));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4539
		e1e_wphy(hw, BM_MTA(i) + 1, (u16)((mac_reg >> 16) & 0xFFFF));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4540
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4541
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4542
	/* configure PHY Rx Control register */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4543
	e1e_rphy(&adapter->hw, BM_RCTL, &phy_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4544
	mac_reg = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4545
	if (mac_reg & E1000_RCTL_UPE)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4546
		phy_reg |= BM_RCTL_UPE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4547
	if (mac_reg & E1000_RCTL_MPE)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4548
		phy_reg |= BM_RCTL_MPE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4549
	phy_reg &= ~(BM_RCTL_MO_MASK);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4550
	if (mac_reg & E1000_RCTL_MO_3)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4551
		phy_reg |= (((mac_reg & E1000_RCTL_MO_3) >> E1000_RCTL_MO_SHIFT)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4552
				<< BM_RCTL_MO_SHIFT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4553
	if (mac_reg & E1000_RCTL_BAM)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4554
		phy_reg |= BM_RCTL_BAM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4555
	if (mac_reg & E1000_RCTL_PMCF)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4556
		phy_reg |= BM_RCTL_PMCF;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4557
	mac_reg = er32(CTRL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4558
	if (mac_reg & E1000_CTRL_RFCE)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4559
		phy_reg |= BM_RCTL_RFCE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4560
	e1e_wphy(&adapter->hw, BM_RCTL, phy_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4561
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4562
	/* enable PHY wakeup in MAC register */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4563
	ew32(WUFC, wufc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4564
	ew32(WUC, E1000_WUC_PHY_WAKE | E1000_WUC_PME_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4565
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4566
	/* configure and enable PHY wakeup in PHY registers */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4567
	e1e_wphy(&adapter->hw, BM_WUFC, wufc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4568
	e1e_wphy(&adapter->hw, BM_WUC, E1000_WUC_PME_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4569
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4570
	/* activate PHY wakeup */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4571
	retval = hw->phy.ops.acquire_phy(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4572
	if (retval) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4573
		e_err("Could not acquire PHY\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4574
		return retval;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4575
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4576
	e1000e_write_phy_reg_mdic(hw, IGP01E1000_PHY_PAGE_SELECT,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4577
	                         (BM_WUC_ENABLE_PAGE << IGP_PAGE_SHIFT));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4578
	retval = e1000e_read_phy_reg_mdic(hw, BM_WUC_ENABLE_REG, &phy_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4579
	if (retval) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4580
		e_err("Could not read PHY page 769\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4581
		goto out;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4582
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4583
	phy_reg |= BM_WUC_ENABLE_BIT | BM_WUC_HOST_WU_BIT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4584
	retval = e1000e_write_phy_reg_mdic(hw, BM_WUC_ENABLE_REG, phy_reg);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4585
	if (retval)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4586
		e_err("Could not set PHY Host Wakeup bit\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4587
out:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4588
	hw->phy.ops.release_phy(hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4589
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4590
	return retval;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4591
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4592
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4593
static int __e1000_shutdown(struct pci_dev *pdev, bool *enable_wake)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4594
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4595
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4596
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4597
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4598
	u32 ctrl, ctrl_ext, rctl, status;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4599
	u32 wufc = adapter->wol;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4600
	int retval = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4601
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4602
	netif_device_detach(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4603
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4604
	if (netif_running(netdev)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4605
		WARN_ON(test_bit(__E1000_RESETTING, &adapter->state));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4606
		e1000e_down(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4607
		e1000_free_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4608
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4609
	e1000e_reset_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4610
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4611
	retval = pci_save_state(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4612
	if (retval)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4613
		return retval;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4614
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4615
	status = er32(STATUS);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4616
	if (status & E1000_STATUS_LU)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4617
		wufc &= ~E1000_WUFC_LNKC;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4618
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4619
	if (wufc) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4620
		e1000_setup_rctl(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4621
		e1000_set_multi(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4622
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4623
		/* turn on all-multi mode if wake on multicast is enabled */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4624
		if (wufc & E1000_WUFC_MC) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4625
			rctl = er32(RCTL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4626
			rctl |= E1000_RCTL_MPE;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4627
			ew32(RCTL, rctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4628
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4629
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4630
		ctrl = er32(CTRL);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4631
		/* advertise wake from D3Cold */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4632
		#define E1000_CTRL_ADVD3WUC 0x00100000
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4633
		/* phy power management enable */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4634
		#define E1000_CTRL_EN_PHY_PWR_MGMT 0x00200000
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4635
		ctrl |= E1000_CTRL_ADVD3WUC;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4636
		if (!(adapter->flags2 & FLAG2_HAS_PHY_WAKEUP))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4637
			ctrl |= E1000_CTRL_EN_PHY_PWR_MGMT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4638
		ew32(CTRL, ctrl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4639
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4640
		if (adapter->hw.phy.media_type == e1000_media_type_fiber ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4641
		    adapter->hw.phy.media_type ==
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4642
		    e1000_media_type_internal_serdes) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4643
			/* keep the laser running in D3 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4644
			ctrl_ext = er32(CTRL_EXT);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4645
			ctrl_ext |= E1000_CTRL_EXT_SDP7_DATA;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4646
			ew32(CTRL_EXT, ctrl_ext);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4647
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4648
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4649
		if (adapter->flags & FLAG_IS_ICH)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4650
			e1000e_disable_gig_wol_ich8lan(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4651
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4652
		/* Allow time for pending master requests to run */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4653
		e1000e_disable_pcie_master(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4654
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4655
		if (adapter->flags2 & FLAG2_HAS_PHY_WAKEUP) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4656
			/* enable wakeup by the PHY */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4657
			retval = e1000_init_phy_wakeup(adapter, wufc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4658
			if (retval)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4659
				return retval;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4660
		} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4661
			/* enable wakeup by the MAC */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4662
			ew32(WUFC, wufc);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4663
			ew32(WUC, E1000_WUC_PME_EN);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4664
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4665
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4666
		ew32(WUC, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4667
		ew32(WUFC, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4668
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4669
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4670
	*enable_wake = !!wufc;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4671
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4672
	/* make sure adapter isn't asleep if manageability is enabled */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4673
	if ((adapter->flags & FLAG_MNG_PT_ENABLED) ||
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4674
	    (hw->mac.ops.check_mng_mode(hw)))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4675
		*enable_wake = true;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4676
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4677
	if (adapter->hw.phy.type == e1000_phy_igp_3)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4678
		e1000e_igp3_phy_powerdown_workaround_ich8lan(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4679
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4680
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4681
	 * Release control of h/w to f/w.  If f/w is AMT enabled, this
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4682
	 * would have already happened in close and is redundant.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4683
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4684
	e1000_release_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4685
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4686
	pci_disable_device(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4687
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4688
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4689
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4690
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4691
static void e1000_power_off(struct pci_dev *pdev, bool sleep, bool wake)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4692
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4693
	if (sleep && wake) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4694
		pci_prepare_to_sleep(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4695
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4696
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4697
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4698
	pci_wake_from_d3(pdev, wake);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4699
	pci_set_power_state(pdev, PCI_D3hot);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4700
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4701
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4702
static void e1000_complete_shutdown(struct pci_dev *pdev, bool sleep,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4703
                                    bool wake)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4704
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4705
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4706
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4707
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4708
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4709
	 * The pci-e switch on some quad port adapters will report a
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4710
	 * correctable error when the MAC transitions from D0 to D3.  To
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4711
	 * prevent this we need to mask off the correctable errors on the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4712
	 * downstream port of the pci-e switch.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4713
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4714
	if (adapter->flags & FLAG_IS_QUAD_PORT) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4715
		struct pci_dev *us_dev = pdev->bus->self;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4716
		int pos = pci_find_capability(us_dev, PCI_CAP_ID_EXP);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4717
		u16 devctl;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4718
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4719
		pci_read_config_word(us_dev, pos + PCI_EXP_DEVCTL, &devctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4720
		pci_write_config_word(us_dev, pos + PCI_EXP_DEVCTL,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4721
		                      (devctl & ~PCI_EXP_DEVCTL_CERE));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4722
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4723
		e1000_power_off(pdev, sleep, wake);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4724
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4725
		pci_write_config_word(us_dev, pos + PCI_EXP_DEVCTL, devctl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4726
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4727
		e1000_power_off(pdev, sleep, wake);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4728
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4729
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4730
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4731
static void e1000e_disable_l1aspm(struct pci_dev *pdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4732
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4733
	int pos;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4734
	u16 val;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4735
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4736
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4737
	 * 82573 workaround - disable L1 ASPM on mobile chipsets
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4738
	 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4739
	 * L1 ASPM on various mobile (ich7) chipsets do not behave properly
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4740
	 * resulting in lost data or garbage information on the pci-e link
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4741
	 * level. This could result in (false) bad EEPROM checksum errors,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4742
	 * long ping times (up to 2s) or even a system freeze/hang.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4743
	 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4744
	 * Unfortunately this feature saves about 1W power consumption when
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4745
	 * active.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4746
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4747
	pos = pci_find_capability(pdev, PCI_CAP_ID_EXP);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4748
	pci_read_config_word(pdev, pos + PCI_EXP_LNKCTL, &val);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4749
	if (val & 0x2) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4750
		dev_warn(&pdev->dev, "Disabling L1 ASPM\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4751
		val &= ~0x2;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4752
		pci_write_config_word(pdev, pos + PCI_EXP_LNKCTL, val);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4753
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4754
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4755
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4756
#ifdef CONFIG_PM
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4757
static int e1000_suspend(struct pci_dev *pdev, pm_message_t state)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4758
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4759
	int retval;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4760
	bool wake;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4761
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4762
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4763
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4764
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4765
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4766
		return -EBUSY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4767
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4768
	retval = __e1000_shutdown(pdev, &wake);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4769
	if (!retval)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4770
		e1000_complete_shutdown(pdev, true, wake);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4771
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4772
	return retval;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4773
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4774
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4775
static int e1000_resume(struct pci_dev *pdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4776
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4777
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4778
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4779
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4780
	u32 err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4781
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4782
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4783
		return -EBUSY;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4784
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4785
	pci_set_power_state(pdev, PCI_D0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4786
	pci_restore_state(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4787
	e1000e_disable_l1aspm(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4788
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4789
	err = pci_enable_device_mem(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4790
	if (err) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4791
		dev_err(&pdev->dev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4792
			"Cannot enable PCI device from suspend\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4793
		return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4794
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4795
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4796
	pci_set_master(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4797
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4798
	pci_enable_wake(pdev, PCI_D3hot, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4799
	pci_enable_wake(pdev, PCI_D3cold, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4800
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4801
	e1000e_set_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4802
	if (netif_running(netdev)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4803
		err = e1000_request_irq(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4804
		if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4805
			return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4806
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4807
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4808
	e1000e_power_up_phy(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4809
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4810
	/* report the system wakeup cause from S3/S4 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4811
	if (adapter->flags2 & FLAG2_HAS_PHY_WAKEUP) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4812
		u16 phy_data;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4813
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4814
		e1e_rphy(&adapter->hw, BM_WUS, &phy_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4815
		if (phy_data) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4816
			e_info("PHY Wakeup cause - %s\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4817
				phy_data & E1000_WUS_EX ? "Unicast Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4818
				phy_data & E1000_WUS_MC ? "Multicast Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4819
				phy_data & E1000_WUS_BC ? "Broadcast Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4820
				phy_data & E1000_WUS_MAG ? "Magic Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4821
				phy_data & E1000_WUS_LNKC ? "Link Status "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4822
				" Change" : "other");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4823
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4824
		e1e_wphy(&adapter->hw, BM_WUS, ~0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4825
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4826
		u32 wus = er32(WUS);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4827
		if (wus) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4828
			e_info("MAC Wakeup cause - %s\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4829
				wus & E1000_WUS_EX ? "Unicast Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4830
				wus & E1000_WUS_MC ? "Multicast Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4831
				wus & E1000_WUS_BC ? "Broadcast Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4832
				wus & E1000_WUS_MAG ? "Magic Packet" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4833
				wus & E1000_WUS_LNKC ? "Link Status Change" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4834
				"other");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4835
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4836
		ew32(WUS, ~0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4837
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4838
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4839
	e1000e_reset(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4840
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4841
	e1000_init_manageability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4842
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4843
	if (netif_running(netdev))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4844
		e1000e_up(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4845
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4846
	netif_device_attach(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4847
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4848
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4849
	 * If the controller has AMT, do not set DRV_LOAD until the interface
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4850
	 * is up.  For all other cases, let the f/w know that the h/w is now
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4851
	 * under the control of the driver.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4852
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4853
	if (!(adapter->flags & FLAG_HAS_AMT))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4854
		e1000_get_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4855
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4856
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4857
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4858
#endif
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4859
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4860
static void e1000_shutdown(struct pci_dev *pdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4861
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4862
	bool wake = false;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4863
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4864
	struct e1000_adapter *adapter = netdev_priv(netdev);
2421
bc2d4bf9cbe5 Removed trailing spaces.
Florian Pose <fp@igh-essen.com>
parents: 2217
diff changeset
  4865
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4866
	if (adapter->ecdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4867
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4868
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4869
	__e1000_shutdown(pdev, &wake);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4870
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4871
	if (system_state == SYSTEM_POWER_OFF)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4872
		e1000_complete_shutdown(pdev, false, wake);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4873
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4874
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4875
#ifdef CONFIG_NET_POLL_CONTROLLER
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4876
/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4877
 * Polling 'interrupt' - used by things like netconsole to send skbs
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4878
 * without having to re-enable interrupts. It's not called while
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4879
 * the interrupt routine is executing.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4880
 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4881
static void e1000_netpoll(struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4882
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4883
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4884
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4885
	disable_irq(adapter->pdev->irq);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4886
	e1000_intr(adapter->pdev->irq, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4887
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4888
	enable_irq(adapter->pdev->irq);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4889
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4890
#endif
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4891
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4892
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4893
 * e1000_io_error_detected - called when PCI error is detected
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4894
 * @pdev: Pointer to PCI device
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4895
 * @state: The current pci connection state
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4896
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4897
 * This function is called after a PCI bus error affecting
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4898
 * this device has been detected.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4899
 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4900
static pci_ers_result_t e1000_io_error_detected(struct pci_dev *pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4901
						pci_channel_state_t state)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4902
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4903
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4904
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4905
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4906
	netif_device_detach(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4907
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4908
	if (state == pci_channel_io_perm_failure)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4909
		return PCI_ERS_RESULT_DISCONNECT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4910
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4911
	if (netif_running(netdev))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4912
		e1000e_down(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4913
	pci_disable_device(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4914
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4915
	/* Request a slot slot reset. */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4916
	return PCI_ERS_RESULT_NEED_RESET;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4917
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4918
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4919
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4920
 * e1000_io_slot_reset - called after the pci bus has been reset.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4921
 * @pdev: Pointer to PCI device
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4922
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4923
 * Restart the card from scratch, as if from a cold-boot. Implementation
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4924
 * resembles the first-half of the e1000_resume routine.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4925
 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4926
static pci_ers_result_t e1000_io_slot_reset(struct pci_dev *pdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4927
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4928
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4929
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4930
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4931
	int err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4932
	pci_ers_result_t result;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4933
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4934
	e1000e_disable_l1aspm(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4935
	err = pci_enable_device_mem(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4936
	if (err) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4937
		dev_err(&pdev->dev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4938
			"Cannot re-enable PCI device after reset.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4939
		result = PCI_ERS_RESULT_DISCONNECT;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4940
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4941
		pci_set_master(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4942
		pci_restore_state(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4943
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4944
		pci_enable_wake(pdev, PCI_D3hot, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4945
		pci_enable_wake(pdev, PCI_D3cold, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4946
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4947
		e1000e_reset(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4948
		ew32(WUS, ~0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4949
		result = PCI_ERS_RESULT_RECOVERED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4950
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4951
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4952
	pci_cleanup_aer_uncorrect_error_status(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4953
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4954
	return result;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4955
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4956
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4957
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4958
 * e1000_io_resume - called when traffic can start flowing again.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4959
 * @pdev: Pointer to PCI device
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4960
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4961
 * This callback is called when the error recovery driver tells us that
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4962
 * its OK to resume normal operation. Implementation resembles the
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4963
 * second-half of the e1000_resume routine.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4964
 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4965
static void e1000_io_resume(struct pci_dev *pdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4966
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4967
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4968
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4969
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4970
	e1000_init_manageability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4971
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4972
	if (netif_running(netdev)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4973
		if (e1000e_up(adapter)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4974
			dev_err(&pdev->dev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4975
				"can't bring device back up after reset\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4976
			return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4977
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4978
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4979
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4980
	netif_device_attach(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4981
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4982
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4983
	 * If the controller has AMT, do not set DRV_LOAD until the interface
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4984
	 * is up.  For all other cases, let the f/w know that the h/w is now
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4985
	 * under the control of the driver.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4986
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4987
	if (!(adapter->flags & FLAG_HAS_AMT))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4988
		e1000_get_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4989
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4990
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4991
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4992
static void e1000_print_device_info(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4993
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4994
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4995
	struct net_device *netdev = adapter->netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4996
	u32 pba_num;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4997
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4998
	/* print bus type/speed/width info */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  4999
	e_info("(PCI Express:2.5GB/s:%s) %pM\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5000
	       /* bus width */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5001
	       ((hw->bus.width == e1000_bus_width_pcie_x4) ? "Width x4" :
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5002
	        "Width x1"),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5003
	       /* MAC address */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5004
	       netdev->dev_addr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5005
	e_info("Intel(R) PRO/%s Network Connection\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5006
	       (hw->phy.type == e1000_phy_ife) ? "10/100" : "1000");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5007
	e1000e_read_pba_num(hw, &pba_num);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5008
	e_info("MAC: %d, PHY: %d, PBA No: %06x-%03x\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5009
	       hw->mac.type, hw->phy.type, (pba_num >> 8), (pba_num & 0xff));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5010
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5011
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5012
static void e1000_eeprom_checks(struct e1000_adapter *adapter)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5013
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5014
	struct e1000_hw *hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5015
	int ret_val;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5016
	u16 buf = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5017
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5018
	if (hw->mac.type != e1000_82573)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5019
		return;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5020
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5021
	ret_val = e1000_read_nvm(hw, NVM_INIT_CONTROL2_REG, 1, &buf);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5022
	if (!ret_val && (!(le16_to_cpu(buf) & (1 << 0)))) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5023
		/* Deep Smart Power Down (DSPD) */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5024
		dev_warn(&adapter->pdev->dev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5025
			 "Warning: detected DSPD enabled in EEPROM\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5026
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5027
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5028
	ret_val = e1000_read_nvm(hw, NVM_INIT_3GIO_3, 1, &buf);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5029
	if (!ret_val && (le16_to_cpu(buf) & (3 << 2))) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5030
		/* ASPM enable */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5031
		dev_warn(&adapter->pdev->dev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5032
			 "Warning: detected ASPM enabled in EEPROM\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5033
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5034
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5035
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5036
static const struct net_device_ops e1000e_netdev_ops = {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5037
	.ndo_open		= e1000_open,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5038
	.ndo_stop		= e1000_close,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5039
	.ndo_start_xmit		= e1000_xmit_frame,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5040
	.ndo_get_stats		= e1000_get_stats,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5041
	.ndo_set_multicast_list	= e1000_set_multi,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5042
	.ndo_set_mac_address	= e1000_set_mac,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5043
	.ndo_change_mtu		= e1000_change_mtu,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5044
	.ndo_do_ioctl		= e1000_ioctl,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5045
	.ndo_tx_timeout		= e1000_tx_timeout,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5046
	.ndo_validate_addr	= eth_validate_addr,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5047
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5048
	.ndo_vlan_rx_register	= e1000_vlan_rx_register,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5049
	.ndo_vlan_rx_add_vid	= e1000_vlan_rx_add_vid,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5050
	.ndo_vlan_rx_kill_vid	= e1000_vlan_rx_kill_vid,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5051
#ifdef CONFIG_NET_POLL_CONTROLLER
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5052
	.ndo_poll_controller	= e1000_netpoll,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5053
#endif
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5054
};
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5055
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5056
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5057
 * ec_poll - Ethercat poll Routine
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5058
 * @netdev: net device structure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5059
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5060
 * This function can never fail.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5061
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5062
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5063
void ec_poll(struct net_device *netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5064
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5065
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5066
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5067
	if (jiffies - adapter->ec_watchdog_jiffies >= 2 * HZ) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5068
		e1000_watchdog((unsigned long) adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5069
		adapter->ec_watchdog_jiffies = jiffies;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5070
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5071
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5072
#ifdef CONFIG_PCI_MSI
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5073
	e1000_intr_msi(0,netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5074
#else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5075
	e1000_intr(0,netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5076
#endif
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5077
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5078
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5079
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5080
 * e1000_probe - Device Initialization Routine
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5081
 * @pdev: PCI device information struct
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5082
 * @ent: entry in e1000_pci_tbl
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5083
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5084
 * Returns 0 on success, negative on failure
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5085
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5086
 * e1000_probe initializes an adapter identified by a pci_dev structure.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5087
 * The OS initialization, configuring of the adapter private structure,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5088
 * and a hardware reset occur.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5089
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5090
static int __devinit e1000_probe(struct pci_dev *pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5091
				 const struct pci_device_id *ent)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5092
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5093
	struct net_device *netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5094
	struct e1000_adapter *adapter;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5095
	struct e1000_hw *hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5096
	const struct e1000_info *ei = e1000_info_tbl[ent->driver_data];
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5097
	resource_size_t mmio_start, mmio_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5098
	resource_size_t flash_start, flash_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5099
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5100
	static int cards_found;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5101
	int i, err, pci_using_dac;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5102
	u16 eeprom_data = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5103
	u16 eeprom_apme_mask = E1000_EEPROM_APME;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5104
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5105
	e1000e_disable_l1aspm(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5106
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5107
	err = pci_enable_device_mem(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5108
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5109
		return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5110
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5111
	pci_using_dac = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5112
	err = pci_set_dma_mask(pdev, DMA_BIT_MASK(64));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5113
	if (!err) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5114
		err = pci_set_consistent_dma_mask(pdev, DMA_BIT_MASK(64));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5115
		if (!err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5116
			pci_using_dac = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5117
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5118
		err = pci_set_dma_mask(pdev, DMA_BIT_MASK(32));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5119
		if (err) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5120
			err = pci_set_consistent_dma_mask(pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5121
							  DMA_BIT_MASK(32));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5122
			if (err) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5123
				dev_err(&pdev->dev, "No usable DMA "
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5124
					"configuration, aborting\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5125
				goto err_dma;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5126
			}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5127
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5128
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5129
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5130
	err = pci_request_selected_regions_exclusive(pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5131
	                                  pci_select_bars(pdev, IORESOURCE_MEM),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5132
	                                  e1000e_driver_name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5133
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5134
		goto err_pci_reg;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5135
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5136
	/* AER (Advanced Error Reporting) hooks */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5137
	pci_enable_pcie_error_reporting(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5138
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5139
	pci_set_master(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5140
	/* PCI config space info */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5141
	err = pci_save_state(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5142
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5143
		goto err_alloc_etherdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5144
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5145
	err = -ENOMEM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5146
	netdev = alloc_etherdev(sizeof(struct e1000_adapter));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5147
	if (!netdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5148
		goto err_alloc_etherdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5149
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5150
	SET_NETDEV_DEV(netdev, &pdev->dev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5151
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5152
	pci_set_drvdata(pdev, netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5153
	adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5154
	hw = &adapter->hw;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5155
	adapter->netdev = netdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5156
	adapter->pdev = pdev;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5157
	adapter->ei = ei;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5158
	adapter->pba = ei->pba;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5159
	adapter->flags = ei->flags;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5160
	adapter->flags2 = ei->flags2;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5161
	adapter->hw.adapter = adapter;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5162
	adapter->hw.mac.type = ei->mac;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5163
	adapter->max_hw_frame_size = ei->max_hw_frame_size;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5164
	adapter->msg_enable = (1 << NETIF_MSG_DRV | NETIF_MSG_PROBE) - 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5165
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5166
	mmio_start = pci_resource_start(pdev, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5167
	mmio_len = pci_resource_len(pdev, 0);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5168
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5169
	err = -EIO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5170
	adapter->hw.hw_addr = ioremap(mmio_start, mmio_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5171
	if (!adapter->hw.hw_addr)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5172
		goto err_ioremap;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5173
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5174
	if ((adapter->flags & FLAG_HAS_FLASH) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5175
	    (pci_resource_flags(pdev, 1) & IORESOURCE_MEM)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5176
		flash_start = pci_resource_start(pdev, 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5177
		flash_len = pci_resource_len(pdev, 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5178
		adapter->hw.flash_address = ioremap(flash_start, flash_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5179
		if (!adapter->hw.flash_address)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5180
			goto err_flashmap;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5181
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5182
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5183
	/* construct the net_device struct */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5184
	netdev->netdev_ops		= &e1000e_netdev_ops;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5185
	e1000e_set_ethtool_ops(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5186
	netdev->watchdog_timeo		= 5 * HZ;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5187
	netif_napi_add(netdev, &adapter->napi, e1000_clean, 64);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5188
	strncpy(netdev->name, pci_name(pdev), sizeof(netdev->name) - 1);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5189
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5190
	netdev->mem_start = mmio_start;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5191
	netdev->mem_end = mmio_start + mmio_len;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5192
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5193
	adapter->bd_number = cards_found++;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5194
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5195
	e1000e_check_options(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5196
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5197
	/* setup adapter struct */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5198
	err = e1000_sw_init(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5199
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5200
		goto err_sw_init;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5201
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5202
	err = -EIO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5203
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5204
	memcpy(&hw->mac.ops, ei->mac_ops, sizeof(hw->mac.ops));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5205
	memcpy(&hw->nvm.ops, ei->nvm_ops, sizeof(hw->nvm.ops));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5206
	memcpy(&hw->phy.ops, ei->phy_ops, sizeof(hw->phy.ops));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5207
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5208
	err = ei->get_variants(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5209
	if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5210
		goto err_hw_init;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5211
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5212
	if ((adapter->flags & FLAG_IS_ICH) &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5213
	    (adapter->flags & FLAG_READ_ONLY_NVM))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5214
		e1000e_write_protect_nvm_ich8lan(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5215
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5216
	hw->mac.ops.get_bus_info(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5218
	adapter->hw.phy.autoneg_wait_to_complete = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5219
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5220
	/* Copper options */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5221
	if (adapter->hw.phy.media_type == e1000_media_type_copper) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5222
		adapter->hw.phy.mdix = AUTO_ALL_MODES;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5223
		adapter->hw.phy.disable_polarity_correction = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5224
		adapter->hw.phy.ms_type = e1000_ms_hw_default;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5225
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5226
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5227
	if (e1000_check_reset_block(&adapter->hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5228
		e_info("PHY reset is blocked due to SOL/IDER session.\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5229
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5230
	netdev->features = NETIF_F_SG |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5231
			   NETIF_F_HW_CSUM |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5232
			   NETIF_F_HW_VLAN_TX |
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5233
			   NETIF_F_HW_VLAN_RX;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5234
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5235
	if (adapter->flags & FLAG_HAS_HW_VLAN_FILTER)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5236
		netdev->features |= NETIF_F_HW_VLAN_FILTER;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5237
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5238
	netdev->features |= NETIF_F_TSO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5239
	netdev->features |= NETIF_F_TSO6;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5240
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5241
	netdev->vlan_features |= NETIF_F_TSO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5242
	netdev->vlan_features |= NETIF_F_TSO6;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5243
	netdev->vlan_features |= NETIF_F_HW_CSUM;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5244
	netdev->vlan_features |= NETIF_F_SG;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5245
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5246
	if (pci_using_dac)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5247
		netdev->features |= NETIF_F_HIGHDMA;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5248
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5249
	if (e1000e_enable_mng_pass_thru(&adapter->hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5250
		adapter->flags |= FLAG_MNG_PT_ENABLED;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5251
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5252
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5253
	 * before reading the NVM, reset the controller to
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5254
	 * put the device in a known good starting state
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5255
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5256
	adapter->hw.mac.ops.reset_hw(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5257
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5258
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5259
	 * systems with ASPM and others may see the checksum fail on the first
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5260
	 * attempt. Let's give it a few tries
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5261
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5262
	for (i = 0;; i++) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5263
		if (e1000_validate_nvm_checksum(&adapter->hw) >= 0)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5264
			break;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5265
		if (i == 2) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5266
			e_err("The NVM Checksum Is Not Valid\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5267
			err = -EIO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5268
			goto err_eeprom;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5269
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5270
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5271
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5272
	e1000_eeprom_checks(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5273
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5274
	/* copy the MAC address out of the NVM */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5275
	if (e1000e_read_mac_addr(&adapter->hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5276
		e_err("NVM Read Error while reading MAC address\n");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5277
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5278
	memcpy(netdev->dev_addr, adapter->hw.mac.addr, netdev->addr_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5279
	memcpy(netdev->perm_addr, adapter->hw.mac.addr, netdev->addr_len);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5280
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5281
	if (!is_valid_ether_addr(netdev->perm_addr)) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5282
		e_err("Invalid MAC Address: %pM\n", netdev->perm_addr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5283
		err = -EIO;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5284
		goto err_eeprom;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5285
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5286
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5287
	init_timer(&adapter->watchdog_timer);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5288
	adapter->watchdog_timer.function = &e1000_watchdog;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5289
	adapter->watchdog_timer.data = (unsigned long) adapter;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5290
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5291
	init_timer(&adapter->phy_info_timer);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5292
	adapter->phy_info_timer.function = &e1000_update_phy_info;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5293
	adapter->phy_info_timer.data = (unsigned long) adapter;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5294
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5295
	INIT_WORK(&adapter->reset_task, e1000_reset_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5296
	INIT_WORK(&adapter->watchdog_task, e1000_watchdog_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5297
	INIT_WORK(&adapter->downshift_task, e1000e_downshift_workaround);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5298
	INIT_WORK(&adapter->update_phy_task, e1000e_update_phy_task);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5299
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5300
	/* Initialize link parameters. User can change them with ethtool */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5301
	adapter->hw.mac.autoneg = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5302
	adapter->fc_autoneg = 1;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5303
	adapter->hw.fc.requested_mode = e1000_fc_default;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5304
	adapter->hw.fc.current_mode = e1000_fc_default;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5305
	adapter->hw.phy.autoneg_advertised = 0x2f;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5306
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5307
	/* ring size defaults */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5308
	adapter->rx_ring->count = 256;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5309
	adapter->tx_ring->count = 256;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5310
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5311
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5312
	 * Initial Wake on LAN setting - If APM wake is enabled in
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5313
	 * the EEPROM, enable the ACPI Magic Packet filter
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5314
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5315
	if (adapter->flags & FLAG_APME_IN_WUC) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5316
		/* APME bit in EEPROM is mapped to WUC.APME */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5317
		eeprom_data = er32(WUC);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5318
		eeprom_apme_mask = E1000_WUC_APME;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5319
		if (eeprom_data & E1000_WUC_PHY_WAKE)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5320
			adapter->flags2 |= FLAG2_HAS_PHY_WAKEUP;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5321
	} else if (adapter->flags & FLAG_APME_IN_CTRL3) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5322
		if (adapter->flags & FLAG_APME_CHECK_PORT_B &&
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5323
		    (adapter->hw.bus.func == 1))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5324
			e1000_read_nvm(&adapter->hw,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5325
				NVM_INIT_CONTROL3_PORT_B, 1, &eeprom_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5326
		else
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5327
			e1000_read_nvm(&adapter->hw,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5328
				NVM_INIT_CONTROL3_PORT_A, 1, &eeprom_data);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5329
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5330
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5331
	/* fetch WoL from EEPROM */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5332
	if (eeprom_data & eeprom_apme_mask)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5333
		adapter->eeprom_wol |= E1000_WUFC_MAG;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5334
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5335
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5336
	 * now that we have the eeprom settings, apply the special cases
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5337
	 * where the eeprom may be wrong or the board simply won't support
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5338
	 * wake on lan on a particular port
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5339
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5340
	if (!(adapter->flags & FLAG_HAS_WOL))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5341
		adapter->eeprom_wol = 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5342
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5343
	/* initialize the wol settings based on the eeprom settings */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5344
	adapter->wol = adapter->eeprom_wol;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5345
	device_set_wakeup_enable(&adapter->pdev->dev, adapter->wol);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5346
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5347
	/* save off EEPROM version number */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5348
	e1000_read_nvm(&adapter->hw, 5, 1, &adapter->eeprom_vers);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5349
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5350
	/* reset the hardware with the new settings */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5351
	e1000e_reset(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5352
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5353
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5354
	 * If the controller has AMT, do not set DRV_LOAD until the interface
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5355
	 * is up.  For all other cases, let the f/w know that the h/w is now
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5356
	 * under the control of the driver.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5357
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5358
	if (!(adapter->flags & FLAG_HAS_AMT))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5359
		e1000_get_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5360
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5361
	adapter->ecdev = ecdev_offer(netdev,ec_poll,THIS_MODULE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5362
	if (adapter->ecdev) {
2582
87e502828b3f Use return value of ecdev_open(); thanks to Patrick Bruenn.
Florian Pose <fp@igh-essen.com>
parents: 2500
diff changeset
  5363
		err = ecdev_open(adapter->ecdev);
87e502828b3f Use return value of ecdev_open(); thanks to Patrick Bruenn.
Florian Pose <fp@igh-essen.com>
parents: 2500
diff changeset
  5364
		if (err) {
2217
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5365
			ecdev_withdraw(adapter->ecdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5366
			goto err_register;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5367
		}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5368
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5369
		strcpy(netdev->name, "eth%d");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5370
		err = register_netdev(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5371
		if (err)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5372
			goto err_register;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5373
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5374
		/* carrier off reporting is important to ethtool even BEFORE open */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5375
		netif_carrier_off(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5376
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5377
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5378
	e1000_print_device_info(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5379
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5380
	return 0;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5381
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5382
err_register:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5383
	if (!(adapter->flags & FLAG_HAS_AMT))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5384
		e1000_release_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5385
err_eeprom:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5386
	if (!e1000_check_reset_block(&adapter->hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5387
		e1000_phy_hw_reset(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5388
err_hw_init:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5389
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5390
	kfree(adapter->tx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5391
	kfree(adapter->rx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5392
err_sw_init:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5393
	if (adapter->hw.flash_address)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5394
		iounmap(adapter->hw.flash_address);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5395
	e1000e_reset_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5396
err_flashmap:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5397
	iounmap(adapter->hw.hw_addr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5398
err_ioremap:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5399
	free_netdev(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5400
err_alloc_etherdev:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5401
	pci_release_selected_regions(pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5402
	                             pci_select_bars(pdev, IORESOURCE_MEM));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5403
err_pci_reg:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5404
err_dma:
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5405
	pci_disable_device(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5406
	return err;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5407
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5408
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5409
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5410
 * e1000_remove - Device Removal Routine
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5411
 * @pdev: PCI device information struct
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5412
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5413
 * e1000_remove is called by the PCI subsystem to alert the driver
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5414
 * that it should release a PCI device.  The could be caused by a
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5415
 * Hot-Plug event, or because the driver is going to be removed from
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5416
 * memory.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5417
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5418
static void __devexit e1000_remove(struct pci_dev *pdev)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5419
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5420
	struct net_device *netdev = pci_get_drvdata(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5421
	struct e1000_adapter *adapter = netdev_priv(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5422
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5423
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5424
	 * flush_scheduled work may reschedule our watchdog task, so
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5425
	 * explicitly disable watchdog tasks from being rescheduled
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5426
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5427
	set_bit(__E1000_DOWN, &adapter->state);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5428
	del_timer_sync(&adapter->watchdog_timer);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5429
	del_timer_sync(&adapter->phy_info_timer);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5430
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5431
	flush_scheduled_work();
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5432
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5433
	/*
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5434
	 * Release control of h/w to f/w.  If f/w is AMT enabled, this
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5435
	 * would have already happened in close and is redundant.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5436
	 */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5437
	e1000_release_hw_control(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5438
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5439
	if (adapter->ecdev) {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5440
		ecdev_close(adapter->ecdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5441
		ecdev_withdraw(adapter->ecdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5442
	} else {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5443
		unregister_netdev(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5444
	}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5445
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5446
	if (!e1000_check_reset_block(&adapter->hw))
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5447
		e1000_phy_hw_reset(&adapter->hw);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5448
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5449
	e1000e_reset_interrupt_capability(adapter);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5450
	kfree(adapter->tx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5451
	kfree(adapter->rx_ring);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5452
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5453
	iounmap(adapter->hw.hw_addr);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5454
	if (adapter->hw.flash_address)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5455
		iounmap(adapter->hw.flash_address);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5456
	pci_release_selected_regions(pdev,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5457
	                             pci_select_bars(pdev, IORESOURCE_MEM));
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5458
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5459
	free_netdev(netdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5460
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5461
	/* AER disable */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5462
	pci_disable_pcie_error_reporting(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5463
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5464
	pci_disable_device(pdev);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5465
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5466
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5467
/* PCI Error Recovery (ERS) */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5468
static struct pci_error_handlers e1000_err_handler = {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5469
	.error_detected = e1000_io_error_detected,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5470
	.slot_reset = e1000_io_slot_reset,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5471
	.resume = e1000_io_resume,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5472
};
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5473
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5474
static struct pci_device_id e1000_pci_tbl[] = {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5475
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_COPPER), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5476
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_FIBER), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5477
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_QUAD_COPPER), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5478
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_QUAD_COPPER_LP), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5479
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_QUAD_FIBER), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5480
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_SERDES), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5481
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_SERDES_DUAL), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5482
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571EB_SERDES_QUAD), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5483
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82571PT_QUAD_COPPER), board_82571 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5484
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5485
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82572EI), board_82572 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5486
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82572EI_COPPER), board_82572 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5487
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82572EI_FIBER), board_82572 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5488
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82572EI_SERDES), board_82572 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5489
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5490
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82573E), board_82573 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5491
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82573E_IAMT), board_82573 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5492
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82573L), board_82573 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5493
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5494
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82574L), board_82574 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5495
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82574LA), board_82574 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5496
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_82583V), board_82583 },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5497
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5498
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_80003ES2LAN_COPPER_DPT),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5499
	  board_80003es2lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5500
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_80003ES2LAN_COPPER_SPT),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5501
	  board_80003es2lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5502
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_80003ES2LAN_SERDES_DPT),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5503
	  board_80003es2lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5504
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_80003ES2LAN_SERDES_SPT),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5505
	  board_80003es2lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5506
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5507
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_IFE), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5508
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_IFE_G), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5509
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_IFE_GT), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5510
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_IGP_AMT), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5511
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_IGP_C), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5512
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_IGP_M), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5513
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_IGP_M_AMT), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5514
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH8_82567V_3), board_ich8lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5515
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5516
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IFE), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5517
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IFE_G), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5518
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IFE_GT), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5519
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IGP_AMT), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5520
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IGP_C), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5521
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_BM), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5522
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IGP_M), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5523
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IGP_M_AMT), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5524
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH9_IGP_M_V), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5525
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5526
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH10_R_BM_LM), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5527
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH10_R_BM_LF), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5528
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH10_R_BM_V), board_ich9lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5529
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5530
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH10_D_BM_LM), board_ich10lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5531
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_ICH10_D_BM_LF), board_ich10lan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5532
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5533
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_PCH_M_HV_LM), board_pchlan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5534
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_PCH_M_HV_LC), board_pchlan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5535
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_PCH_D_HV_DM), board_pchlan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5536
	{ PCI_VDEVICE(INTEL, E1000_DEV_ID_PCH_D_HV_DC), board_pchlan },
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5537
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5538
	{ }	/* terminate list */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5539
};
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5540
//MODULE_DEVICE_TABLE(pci, e1000_pci_tbl);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5541
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5542
/* PCI Device API Driver */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5543
static struct pci_driver e1000_driver = {
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5544
	.name     = e1000e_driver_name,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5545
	.id_table = e1000_pci_tbl,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5546
	.probe    = e1000_probe,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5547
	.remove   = __devexit_p(e1000_remove),
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5548
#ifdef CONFIG_PM
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5549
	/* Power Management Hooks */
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5550
	.suspend  = e1000_suspend,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5551
	.resume   = e1000_resume,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5552
#endif
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5553
	.shutdown = e1000_shutdown,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5554
	.err_handler = &e1000_err_handler
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5555
};
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5556
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5557
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5558
 * e1000_init_module - Driver Registration Routine
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5559
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5560
 * e1000_init_module is the first routine called when the driver is
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5561
 * loaded. All it does is register with the PCI subsystem.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5562
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5563
static int __init e1000_init_module(void)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5564
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5565
	int ret;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5566
	printk(KERN_INFO "%s: Ethercat-capable Intel(R) PRO/1000 Network Driver - %s\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5567
	       e1000e_driver_name, e1000e_driver_version);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5568
	printk(KERN_INFO "%s: Copyright (c) 1999-2008 Intel Corporation.\n",
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5569
	       e1000e_driver_name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5570
	ret = pci_register_driver(&e1000_driver);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5571
	pm_qos_add_requirement(PM_QOS_CPU_DMA_LATENCY, e1000e_driver_name,
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5572
			       PM_QOS_DEFAULT_VALUE);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5573
				
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5574
	return ret;
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5575
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5576
module_init(e1000_init_module);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5577
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5578
/**
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5579
 * e1000_exit_module - Driver Exit Cleanup Routine
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5580
 *
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5581
 * e1000_exit_module is called just before the driver is removed
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5582
 * from memory.
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5583
 **/
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5584
static void __exit e1000_exit_module(void)
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5585
{
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5586
	pci_unregister_driver(&e1000_driver);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5587
	pm_qos_remove_requirement(PM_QOS_CPU_DMA_LATENCY, e1000e_driver_name);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5588
}
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5589
module_exit(e1000_exit_module);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5590
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5591
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5592
MODULE_AUTHOR("Intel Corporation, <linux.nics@intel.com>");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5593
MODULE_DESCRIPTION("Ethercat-capable Intel(R) PRO/1000 Network Driver");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5594
MODULE_LICENSE("GPL");
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5595
MODULE_VERSION(DRV_VERSION);
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5596
6787ee69205e Added e1000e driver for 2.6.32.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
  5597
/* e1000_main.c */