Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

net: dsa: microchip: ptp: Initial hardware time stamping support

This patch adds the routine for get_ts_info, hwstamp_get, set. This enables
the PTP support towards userspace applications such as linuxptp.

Signed-off-by: Christian Eggers <ceggers@arri.de>
Co-developed-by: Arun Ramadoss <arun.ramadoss@microchip.com>
Signed-off-by: Arun Ramadoss <arun.ramadoss@microchip.com>
Signed-off-by: David S. Miller <davem@davemloft.net>

authored by

Christian Eggers and committed by
David S. Miller
c59e12a1 eac1ea20

+118
+3
drivers/net/dsa/microchip/ksz_common.c
··· 2977 2977 .get_pause_stats = ksz_get_pause_stats, 2978 2978 .port_change_mtu = ksz_change_mtu, 2979 2979 .port_max_mtu = ksz_max_mtu, 2980 + .get_ts_info = ksz_get_ts_info, 2981 + .port_hwtstamp_get = ksz_hwtstamp_get, 2982 + .port_hwtstamp_set = ksz_hwtstamp_set, 2980 2983 }; 2981 2984 2982 2985 struct ksz_device *ksz_switch_alloc(struct device *base, void *priv)
+3
drivers/net/dsa/microchip/ksz_common.h
··· 102 102 struct ksz_device *ksz_dev; 103 103 struct ksz_irq pirq; 104 104 u8 num; 105 + #if IS_ENABLED(CONFIG_NET_DSA_MICROCHIP_KSZ_PTP) 106 + struct hwtstamp_config tstamp_config; 107 + #endif 105 108 }; 106 109 107 110 struct ksz_device {
+101
drivers/net/dsa/microchip/ksz_ptp.c
··· 24 24 #define KSZ_PTP_INC_NS 40ULL /* HW clock is incremented every 40 ns (by 40) */ 25 25 #define KSZ_PTP_SUBNS_BITS 32 26 26 27 + /* The function is return back the capability of timestamping feature when 28 + * requested through ethtool -T <interface> utility 29 + */ 30 + int ksz_get_ts_info(struct dsa_switch *ds, int port, struct ethtool_ts_info *ts) 31 + { 32 + struct ksz_device *dev = ds->priv; 33 + struct ksz_ptp_data *ptp_data; 34 + 35 + ptp_data = &dev->ptp_data; 36 + 37 + if (!ptp_data->clock) 38 + return -ENODEV; 39 + 40 + ts->so_timestamping = SOF_TIMESTAMPING_TX_HARDWARE | 41 + SOF_TIMESTAMPING_RX_HARDWARE | 42 + SOF_TIMESTAMPING_RAW_HARDWARE; 43 + 44 + ts->tx_types = BIT(HWTSTAMP_TX_OFF) | BIT(HWTSTAMP_TX_ONESTEP_P2P); 45 + 46 + ts->rx_filters = BIT(HWTSTAMP_FILTER_NONE) | 47 + BIT(HWTSTAMP_FILTER_PTP_V2_L4_EVENT) | 48 + BIT(HWTSTAMP_FILTER_PTP_V2_L2_EVENT) | 49 + BIT(HWTSTAMP_FILTER_PTP_V2_EVENT); 50 + 51 + ts->phc_index = ptp_clock_index(ptp_data->clock); 52 + 53 + return 0; 54 + } 55 + 56 + int ksz_hwtstamp_get(struct dsa_switch *ds, int port, struct ifreq *ifr) 57 + { 58 + struct ksz_device *dev = ds->priv; 59 + struct hwtstamp_config *config; 60 + struct ksz_port *prt; 61 + 62 + prt = &dev->ports[port]; 63 + config = &prt->tstamp_config; 64 + 65 + return copy_to_user(ifr->ifr_data, config, sizeof(*config)) ? 66 + -EFAULT : 0; 67 + } 68 + 69 + static int ksz_set_hwtstamp_config(struct ksz_device *dev, 70 + struct hwtstamp_config *config) 71 + { 72 + if (config->flags) 73 + return -EINVAL; 74 + 75 + switch (config->tx_type) { 76 + case HWTSTAMP_TX_OFF: 77 + case HWTSTAMP_TX_ONESTEP_P2P: 78 + break; 79 + default: 80 + return -ERANGE; 81 + } 82 + 83 + switch (config->rx_filter) { 84 + case HWTSTAMP_FILTER_NONE: 85 + break; 86 + case HWTSTAMP_FILTER_PTP_V2_L4_EVENT: 87 + case HWTSTAMP_FILTER_PTP_V2_L4_SYNC: 88 + config->rx_filter = HWTSTAMP_FILTER_PTP_V2_L4_EVENT; 89 + break; 90 + case HWTSTAMP_FILTER_PTP_V2_L2_EVENT: 91 + case HWTSTAMP_FILTER_PTP_V2_L2_SYNC: 92 + config->rx_filter = HWTSTAMP_FILTER_PTP_V2_L2_EVENT; 93 + break; 94 + case HWTSTAMP_FILTER_PTP_V2_EVENT: 95 + case HWTSTAMP_FILTER_PTP_V2_SYNC: 96 + config->rx_filter = HWTSTAMP_FILTER_PTP_V2_EVENT; 97 + break; 98 + default: 99 + config->rx_filter = HWTSTAMP_FILTER_NONE; 100 + return -ERANGE; 101 + } 102 + 103 + return 0; 104 + } 105 + 106 + int ksz_hwtstamp_set(struct dsa_switch *ds, int port, struct ifreq *ifr) 107 + { 108 + struct ksz_device *dev = ds->priv; 109 + struct hwtstamp_config config; 110 + struct ksz_port *prt; 111 + int ret; 112 + 113 + prt = &dev->ports[port]; 114 + 115 + ret = copy_from_user(&config, ifr->ifr_data, sizeof(config)); 116 + if (ret) 117 + return ret; 118 + 119 + ret = ksz_set_hwtstamp_config(dev, &config); 120 + if (ret) 121 + return ret; 122 + 123 + memcpy(&prt->tstamp_config, &config, sizeof(config)); 124 + 125 + return copy_to_user(ifr->ifr_data, &config, sizeof(config)); 126 + } 127 + 27 128 static int _ksz_ptp_gettime(struct ksz_device *dev, struct timespec64 *ts) 28 129 { 29 130 u32 nanoseconds;
+11
drivers/net/dsa/microchip/ksz_ptp.h
··· 23 23 24 24 void ksz_ptp_clock_unregister(struct dsa_switch *ds); 25 25 26 + int ksz_get_ts_info(struct dsa_switch *ds, int port, 27 + struct ethtool_ts_info *ts); 28 + int ksz_hwtstamp_get(struct dsa_switch *ds, int port, struct ifreq *ifr); 29 + int ksz_hwtstamp_set(struct dsa_switch *ds, int port, struct ifreq *ifr); 30 + 26 31 #else 27 32 28 33 struct ksz_ptp_data { ··· 41 36 } 42 37 43 38 static inline void ksz_ptp_clock_unregister(struct dsa_switch *ds) { } 39 + 40 + #define ksz_get_ts_info NULL 41 + 42 + #define ksz_hwtstamp_get NULL 43 + 44 + #define ksz_hwtstamp_set NULL 44 45 45 46 #endif /* End of CONFIG_NET_DSA_MICROCHIP_KSZ_PTP */ 46 47