Commit 93501d48 authored by Jacob Keller's avatar Jacob Keller Committed by David S. Miller

ixgbe: implement SIOCGHWTSTAMP ioctl

This patch adds support for the new SIOCGHWTSTAMP ioctl, which enables a
process to determine the current timestamp configuration. In order to
implement this, store a copy of the timestamp configuration. In
addition, we can remove the 'int cmd' parameter as the new set_ts_config
function doesn't use it. I also fixed a typo in the function
description.

-v2
* Only save the settings after validating them
Signed-off-by: default avatarJacob Keller <jacob.e.keller@intel.com>
Tested-by: default avatarPhil Schmitt <phillip.j.schmitt@intel.com>
Signed-off-by: default avatarAaron Brown <aaron.f.brown@intel.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 14438464
...@@ -765,6 +765,7 @@ struct ixgbe_adapter { ...@@ -765,6 +765,7 @@ struct ixgbe_adapter {
struct ptp_clock_info ptp_caps; struct ptp_clock_info ptp_caps;
struct work_struct ptp_tx_work; struct work_struct ptp_tx_work;
struct sk_buff *ptp_tx_skb; struct sk_buff *ptp_tx_skb;
struct hwtstamp_config tstamp_config;
unsigned long ptp_tx_start; unsigned long ptp_tx_start;
unsigned long last_overflow_check; unsigned long last_overflow_check;
unsigned long last_rx_ptp_check; unsigned long last_rx_ptp_check;
...@@ -957,8 +958,8 @@ static inline void ixgbe_ptp_rx_hwtstamp(struct ixgbe_ring *rx_ring, ...@@ -957,8 +958,8 @@ static inline void ixgbe_ptp_rx_hwtstamp(struct ixgbe_ring *rx_ring,
rx_ring->last_rx_timestamp = jiffies; rx_ring->last_rx_timestamp = jiffies;
} }
int ixgbe_ptp_hwtstamp_ioctl(struct ixgbe_adapter *adapter, struct ifreq *ifr, int ixgbe_ptp_set_ts_config(struct ixgbe_adapter *adapter, struct ifreq *ifr);
int cmd); int ixgbe_ptp_get_ts_config(struct ixgbe_adapter *adapter, struct ifreq *ifr);
void ixgbe_ptp_start_cyclecounter(struct ixgbe_adapter *adapter); void ixgbe_ptp_start_cyclecounter(struct ixgbe_adapter *adapter);
void ixgbe_ptp_reset(struct ixgbe_adapter *adapter); void ixgbe_ptp_reset(struct ixgbe_adapter *adapter);
void ixgbe_ptp_check_pps_event(struct ixgbe_adapter *adapter, u32 eicr); void ixgbe_ptp_check_pps_event(struct ixgbe_adapter *adapter, u32 eicr);
......
...@@ -7197,7 +7197,9 @@ static int ixgbe_ioctl(struct net_device *netdev, struct ifreq *req, int cmd) ...@@ -7197,7 +7197,9 @@ static int ixgbe_ioctl(struct net_device *netdev, struct ifreq *req, int cmd)
switch (cmd) { switch (cmd) {
case SIOCSHWTSTAMP: case SIOCSHWTSTAMP:
return ixgbe_ptp_hwtstamp_ioctl(adapter, req, cmd); return ixgbe_ptp_set_ts_config(adapter, req);
case SIOCGHWTSTAMP:
return ixgbe_ptp_get_ts_config(adapter, req);
default: default:
return mdio_mii_ioctl(&adapter->hw.phy.mdio, if_mii(req), cmd); return mdio_mii_ioctl(&adapter->hw.phy.mdio, if_mii(req), cmd);
} }
......
...@@ -576,14 +576,21 @@ void __ixgbe_ptp_rx_hwtstamp(struct ixgbe_q_vector *q_vector, ...@@ -576,14 +576,21 @@ void __ixgbe_ptp_rx_hwtstamp(struct ixgbe_q_vector *q_vector,
shhwtstamps->hwtstamp = ns_to_ktime(ns); shhwtstamps->hwtstamp = ns_to_ktime(ns);
} }
int ixgbe_ptp_get_ts_config(struct ixgbe_adapter *adapter, struct ifreq *ifr)
{
struct hwtstamp_config *config = &adapter->tstamp_config;
return copy_to_user(ifr->ifr_data, config,
sizeof(*config)) ? -EFAULT : 0;
}
/** /**
* ixgbe_ptp_hwtstamp_ioctl - control hardware time stamping * ixgbe_ptp_set_ts_config - control hardware time stamping
* @adapter: pointer to adapter struct * @adapter: pointer to adapter struct
* @ifreq: ioctl data * @ifreq: ioctl data
* @cmd: particular ioctl requested
* *
* Outgoing time stamping can be enabled and disabled. Play nice and * Outgoing time stamping can be enabled and disabled. Play nice and
* disable it when requested, although it shouldn't case any overhead * disable it when requested, although it shouldn't cause any overhead
* when no packet needs it. At most one packet in the queue may be * when no packet needs it. At most one packet in the queue may be
* marked for time stamping, otherwise it would be impossible to tell * marked for time stamping, otherwise it would be impossible to tell
* for sure to which packet the hardware time stamp belongs. * for sure to which packet the hardware time stamp belongs.
...@@ -599,8 +606,7 @@ void __ixgbe_ptp_rx_hwtstamp(struct ixgbe_q_vector *q_vector, ...@@ -599,8 +606,7 @@ void __ixgbe_ptp_rx_hwtstamp(struct ixgbe_q_vector *q_vector,
* Event mode. This more accurately tells the user what the hardware is going * Event mode. This more accurately tells the user what the hardware is going
* to do anyways. * to do anyways.
*/ */
int ixgbe_ptp_hwtstamp_ioctl(struct ixgbe_adapter *adapter, int ixgbe_ptp_set_ts_config(struct ixgbe_adapter *adapter, struct ifreq *ifr)
struct ifreq *ifr, int cmd)
{ {
struct ixgbe_hw *hw = &adapter->hw; struct ixgbe_hw *hw = &adapter->hw;
struct hwtstamp_config config; struct hwtstamp_config config;
...@@ -702,6 +708,10 @@ int ixgbe_ptp_hwtstamp_ioctl(struct ixgbe_adapter *adapter, ...@@ -702,6 +708,10 @@ int ixgbe_ptp_hwtstamp_ioctl(struct ixgbe_adapter *adapter,
regval = IXGBE_READ_REG(hw, IXGBE_TXSTMPH); regval = IXGBE_READ_REG(hw, IXGBE_TXSTMPH);
regval = IXGBE_READ_REG(hw, IXGBE_RXSTMPH); regval = IXGBE_READ_REG(hw, IXGBE_RXSTMPH);
/* save these settings for future reference */
memcpy(&adapter->tstamp_config, &config,
sizeof(adapter->tstamp_config));
return copy_to_user(ifr->ifr_data, &config, sizeof(config)) ? return copy_to_user(ifr->ifr_data, &config, sizeof(config)) ?
-EFAULT : 0; -EFAULT : 0;
} }
...@@ -809,6 +819,9 @@ void ixgbe_ptp_reset(struct ixgbe_adapter *adapter) ...@@ -809,6 +819,9 @@ void ixgbe_ptp_reset(struct ixgbe_adapter *adapter)
IXGBE_WRITE_REG(hw, IXGBE_SYSTIMH, 0x00000000); IXGBE_WRITE_REG(hw, IXGBE_SYSTIMH, 0x00000000);
IXGBE_WRITE_FLUSH(hw); IXGBE_WRITE_FLUSH(hw);
/* Reset the saved tstamp_config */
memset(&adapter->tstamp_config, 0, sizeof(adapter->tstamp_config));
ixgbe_ptp_start_cyclecounter(adapter); ixgbe_ptp_start_cyclecounter(adapter);
spin_lock_irqsave(&adapter->tmreg_lock, flags); spin_lock_irqsave(&adapter->tmreg_lock, flags);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment