devices/e1000e/ptp-3.12-orig.c
author Patrick Bruenn <p.bruenn@beckhoff.com>
Tue, 12 Apr 2016 11:17:36 +0200
branchstable-1.5
changeset 2654 b3f6b3e5ef29
parent 2586 5b89b4e38cdc
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.
2586
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     1
/*******************************************************************************
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     2
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     3
  Intel PRO/1000 Linux driver
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     4
  Copyright(c) 1999 - 2013 Intel Corporation.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     5
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     6
  This program is free software; you can redistribute it and/or modify it
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     7
  under the terms and conditions of the GNU General Public License,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     8
  version 2, as published by the Free Software Foundation.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
     9
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    10
  This program is distributed in the hope it will be useful, but WITHOUT
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    11
  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    12
  FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    13
  more details.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    14
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    15
  You should have received a copy of the GNU General Public License along with
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    16
  this program; if not, write to the Free Software Foundation, Inc.,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    17
  51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    18
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    19
  The full GNU General Public License is included in this distribution in
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    20
  the file called "COPYING".
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    21
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    22
  Contact Information:
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    23
  Linux NICS <linux.nics@intel.com>
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    24
  e1000-devel Mailing List <e1000-devel@lists.sourceforge.net>
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    25
  Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    26
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    27
*******************************************************************************/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    28
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    29
/* PTP 1588 Hardware Clock (PHC)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    30
 * Derived from PTP Hardware Clock driver for Intel 82576 and 82580 (igb)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    31
 * Copyright (C) 2011 Richard Cochran <richardcochran@gmail.com>
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    32
 */
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    33
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    34
#include "e1000.h"
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    35
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    36
/**
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    37
 * e1000e_phc_adjfreq - adjust the frequency of the hardware clock
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    38
 * @ptp: ptp clock structure
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    39
 * @delta: Desired frequency change in parts per billion
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    40
 *
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    41
 * Adjust the frequency of the PHC cycle counter by the indicated delta from
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    42
 * the base frequency.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    43
 **/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    44
static int e1000e_phc_adjfreq(struct ptp_clock_info *ptp, s32 delta)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    45
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    46
	struct e1000_adapter *adapter = container_of(ptp, struct e1000_adapter,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    47
						     ptp_clock_info);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    48
	struct e1000_hw *hw = &adapter->hw;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    49
	bool neg_adj = false;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    50
	u64 adjustment;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    51
	u32 timinca, incvalue;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    52
	s32 ret_val;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    53
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    54
	if ((delta > ptp->max_adj) || (delta <= -1000000000))
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    55
		return -EINVAL;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    56
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    57
	if (delta < 0) {
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    58
		neg_adj = true;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    59
		delta = -delta;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    60
	}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    61
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    62
	/* Get the System Time Register SYSTIM base frequency */
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    63
	ret_val = e1000e_get_base_timinca(adapter, &timinca);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    64
	if (ret_val)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    65
		return ret_val;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    66
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    67
	incvalue = timinca & E1000_TIMINCA_INCVALUE_MASK;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    68
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    69
	adjustment = incvalue;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    70
	adjustment *= delta;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    71
	adjustment = div_u64(adjustment, 1000000000);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    72
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    73
	incvalue = neg_adj ? (incvalue - adjustment) : (incvalue + adjustment);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    74
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    75
	timinca &= ~E1000_TIMINCA_INCVALUE_MASK;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    76
	timinca |= incvalue;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    77
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    78
	ew32(TIMINCA, timinca);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    79
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    80
	return 0;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    81
}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    82
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    83
/**
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    84
 * e1000e_phc_adjtime - Shift the time of the hardware clock
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    85
 * @ptp: ptp clock structure
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    86
 * @delta: Desired change in nanoseconds
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    87
 *
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    88
 * Adjust the timer by resetting the timecounter structure.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    89
 **/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    90
static int e1000e_phc_adjtime(struct ptp_clock_info *ptp, s64 delta)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    91
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    92
	struct e1000_adapter *adapter = container_of(ptp, struct e1000_adapter,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    93
						     ptp_clock_info);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    94
	unsigned long flags;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    95
	s64 now;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    96
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    97
	spin_lock_irqsave(&adapter->systim_lock, flags);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    98
	now = timecounter_read(&adapter->tc);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
    99
	now += delta;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   100
	timecounter_init(&adapter->tc, &adapter->cc, now);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   101
	spin_unlock_irqrestore(&adapter->systim_lock, flags);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   102
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   103
	return 0;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   104
}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   105
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   106
/**
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   107
 * e1000e_phc_gettime - Reads the current time from the hardware clock
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   108
 * @ptp: ptp clock structure
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   109
 * @ts: timespec structure to hold the current time value
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   110
 *
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   111
 * Read the timecounter and return the correct value in ns after converting
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   112
 * it into a struct timespec.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   113
 **/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   114
static int e1000e_phc_gettime(struct ptp_clock_info *ptp, struct timespec *ts)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   115
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   116
	struct e1000_adapter *adapter = container_of(ptp, struct e1000_adapter,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   117
						     ptp_clock_info);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   118
	unsigned long flags;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   119
	u32 remainder;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   120
	u64 ns;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   121
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   122
	spin_lock_irqsave(&adapter->systim_lock, flags);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   123
	ns = timecounter_read(&adapter->tc);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   124
	spin_unlock_irqrestore(&adapter->systim_lock, flags);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   125
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   126
	ts->tv_sec = div_u64_rem(ns, NSEC_PER_SEC, &remainder);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   127
	ts->tv_nsec = remainder;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   128
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   129
	return 0;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   130
}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   131
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   132
/**
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   133
 * e1000e_phc_settime - Set the current time on the hardware clock
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   134
 * @ptp: ptp clock structure
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   135
 * @ts: timespec containing the new time for the cycle counter
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   136
 *
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   137
 * Reset the timecounter to use a new base value instead of the kernel
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   138
 * wall timer value.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   139
 **/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   140
static int e1000e_phc_settime(struct ptp_clock_info *ptp,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   141
			      const struct timespec *ts)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   142
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   143
	struct e1000_adapter *adapter = container_of(ptp, struct e1000_adapter,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   144
						     ptp_clock_info);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   145
	unsigned long flags;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   146
	u64 ns;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   147
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   148
	ns = timespec_to_ns(ts);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   149
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   150
	/* reset the timecounter */
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   151
	spin_lock_irqsave(&adapter->systim_lock, flags);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   152
	timecounter_init(&adapter->tc, &adapter->cc, ns);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   153
	spin_unlock_irqrestore(&adapter->systim_lock, flags);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   154
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   155
	return 0;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   156
}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   157
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   158
/**
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   159
 * e1000e_phc_enable - enable or disable an ancillary feature
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   160
 * @ptp: ptp clock structure
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   161
 * @request: Desired resource to enable or disable
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   162
 * @on: Caller passes one to enable or zero to disable
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   163
 *
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   164
 * Enable (or disable) ancillary features of the PHC subsystem.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   165
 * Currently, no ancillary features are supported.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   166
 **/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   167
static int e1000e_phc_enable(struct ptp_clock_info __always_unused *ptp,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   168
			     struct ptp_clock_request __always_unused *request,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   169
			     int __always_unused on)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   170
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   171
	return -EOPNOTSUPP;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   172
}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   173
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   174
static void e1000e_systim_overflow_work(struct work_struct *work)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   175
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   176
	struct e1000_adapter *adapter = container_of(work, struct e1000_adapter,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   177
						     systim_overflow_work.work);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   178
	struct e1000_hw *hw = &adapter->hw;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   179
	struct timespec ts;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   180
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   181
	adapter->ptp_clock_info.gettime(&adapter->ptp_clock_info, &ts);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   182
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   183
	e_dbg("SYSTIM overflow check at %ld.%09lu\n", ts.tv_sec, ts.tv_nsec);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   184
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   185
	schedule_delayed_work(&adapter->systim_overflow_work,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   186
			      E1000_SYSTIM_OVERFLOW_PERIOD);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   187
}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   188
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   189
static const struct ptp_clock_info e1000e_ptp_clock_info = {
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   190
	.owner		= THIS_MODULE,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   191
	.n_alarm	= 0,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   192
	.n_ext_ts	= 0,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   193
	.n_per_out	= 0,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   194
	.pps		= 0,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   195
	.adjfreq	= e1000e_phc_adjfreq,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   196
	.adjtime	= e1000e_phc_adjtime,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   197
	.gettime	= e1000e_phc_gettime,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   198
	.settime	= e1000e_phc_settime,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   199
	.enable		= e1000e_phc_enable,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   200
};
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   201
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   202
/**
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   203
 * e1000e_ptp_init - initialize PTP for devices which support it
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   204
 * @adapter: board private structure
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   205
 *
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   206
 * This function performs the required steps for enabling PTP support.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   207
 * If PTP support has already been loaded it simply calls the cyclecounter
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   208
 * init routine and exits.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   209
 **/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   210
void e1000e_ptp_init(struct e1000_adapter *adapter)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   211
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   212
	struct e1000_hw *hw = &adapter->hw;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   213
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   214
	adapter->ptp_clock = NULL;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   215
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   216
	if (!(adapter->flags & FLAG_HAS_HW_TIMESTAMP))
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   217
		return;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   218
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   219
	adapter->ptp_clock_info = e1000e_ptp_clock_info;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   220
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   221
	snprintf(adapter->ptp_clock_info.name,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   222
		 sizeof(adapter->ptp_clock_info.name), "%pm",
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   223
		 adapter->netdev->perm_addr);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   224
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   225
	switch (hw->mac.type) {
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   226
	case e1000_pch2lan:
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   227
	case e1000_pch_lpt:
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   228
		if ((hw->mac.type != e1000_pch_lpt) ||
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   229
		    (er32(TSYNCRXCTL) & E1000_TSYNCRXCTL_SYSCFI)) {
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   230
			adapter->ptp_clock_info.max_adj = 24000000 - 1;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   231
			break;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   232
		}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   233
		/* fall-through */
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   234
	case e1000_82574:
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   235
	case e1000_82583:
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   236
		adapter->ptp_clock_info.max_adj = 600000000 - 1;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   237
		break;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   238
	default:
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   239
		break;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   240
	}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   241
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   242
	INIT_DELAYED_WORK(&adapter->systim_overflow_work,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   243
			  e1000e_systim_overflow_work);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   244
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   245
	schedule_delayed_work(&adapter->systim_overflow_work,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   246
			      E1000_SYSTIM_OVERFLOW_PERIOD);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   247
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   248
	adapter->ptp_clock = ptp_clock_register(&adapter->ptp_clock_info,
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   249
						&adapter->pdev->dev);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   250
	if (IS_ERR(adapter->ptp_clock)) {
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   251
		adapter->ptp_clock = NULL;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   252
		e_err("ptp_clock_register failed\n");
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   253
	} else {
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   254
		e_info("registered PHC clock\n");
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   255
	}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   256
}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   257
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   258
/**
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   259
 * e1000e_ptp_remove - disable PTP device and stop the overflow check
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   260
 * @adapter: board private structure
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   261
 *
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   262
 * Stop the PTP support, and cancel the delayed work.
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   263
 **/
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   264
void e1000e_ptp_remove(struct e1000_adapter *adapter)
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   265
{
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   266
	if (!(adapter->flags & FLAG_HAS_HW_TIMESTAMP))
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   267
		return;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   268
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   269
	cancel_delayed_work_sync(&adapter->systim_overflow_work);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   270
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   271
	if (adapter->ptp_clock) {
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   272
		ptp_clock_unregister(adapter->ptp_clock);
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   273
		adapter->ptp_clock = NULL;
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   274
		e_info("removed PHC\n");
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   275
	}
5b89b4e38cdc Added all drivers for kernel 3.12.
Florian Pose <fp@igh-essen.com>
parents:
diff changeset
   276
}