Skip to content

Commit 5f29580

Browse files
vcgomesJeff Kirsher
authored andcommitted
igc: Add basic skeleton for PTP
This allows the creation of the /dev/ptpX device for i225, and reading and writing the time. Signed-off-by: Vinicius Costa Gomes <[email protected]> Tested-by: Aaron Brown <[email protected]> Signed-off-by: Jeff Kirsher <[email protected]>
1 parent df2c2ba commit 5f29580

File tree

6 files changed

+439
-1
lines changed

6 files changed

+439
-1
lines changed

drivers/net/ethernet/intel/igc/Makefile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,4 +8,4 @@
88
obj-$(CONFIG_IGC) += igc.o
99

1010
igc-objs := igc_main.o igc_mac.o igc_i225.o igc_base.o igc_nvm.o igc_phy.o \
11-
igc_ethtool.o
11+
igc_ethtool.o igc_ptp.o

drivers/net/ethernet/intel/igc/igc.h

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,9 @@
1010
#include <linux/vmalloc.h>
1111
#include <linux/ethtool.h>
1212
#include <linux/sctp.h>
13+
#include <linux/ptp_clock_kernel.h>
14+
#include <linux/timecounter.h>
15+
#include <linux/net_tstamp.h>
1316

1417
#include "igc_hw.h"
1518

@@ -45,11 +48,15 @@ extern char igc_driver_version[];
4548
#define IGC_REGS_LEN 740
4649
#define IGC_RETA_SIZE 128
4750

51+
/* flags controlling PTP/1588 function */
52+
#define IGC_PTP_ENABLED BIT(0)
53+
4854
/* Interrupt defines */
4955
#define IGC_START_ITR 648 /* ~6000 ints/sec */
5056
#define IGC_FLAG_HAS_MSI BIT(0)
5157
#define IGC_FLAG_QUEUE_PAIRS BIT(3)
5258
#define IGC_FLAG_DMAC BIT(4)
59+
#define IGC_FLAG_PTP BIT(8)
5360
#define IGC_FLAG_NEED_LINK_UPDATE BIT(9)
5461
#define IGC_FLAG_MEDIA_RESET BIT(10)
5562
#define IGC_FLAG_MAS_ENABLE BIT(12)
@@ -432,6 +439,20 @@ struct igc_adapter {
432439

433440
unsigned long link_check_timeout;
434441
struct igc_info ei;
442+
443+
struct ptp_clock *ptp_clock;
444+
struct ptp_clock_info ptp_caps;
445+
struct work_struct ptp_tx_work;
446+
struct sk_buff *ptp_tx_skb;
447+
struct hwtstamp_config tstamp_config;
448+
unsigned long ptp_tx_start;
449+
unsigned long last_rx_ptp_check;
450+
unsigned long last_rx_timestamp;
451+
unsigned int ptp_flags;
452+
/* System time value lock */
453+
spinlock_t tmreg_lock;
454+
struct cyclecounter cc;
455+
struct timecounter tc;
435456
};
436457

437458
/* igc_desc_unused - calculate if we have unused descriptors */
@@ -515,6 +536,11 @@ int igc_add_filter(struct igc_adapter *adapter,
515536
int igc_erase_filter(struct igc_adapter *adapter,
516537
struct igc_nfc_filter *input);
517538

539+
void igc_ptp_init(struct igc_adapter *adapter);
540+
void igc_ptp_reset(struct igc_adapter *adapter);
541+
void igc_ptp_stop(struct igc_adapter *adapter);
542+
int igc_ptp_set_ts_config(struct net_device *netdev, struct ifreq *ifr);
543+
int igc_ptp_get_ts_config(struct net_device *netdev, struct ifreq *ifr);
518544
#define igc_rx_pg_size(_ring) (PAGE_SIZE << igc_rx_pg_order(_ring))
519545

520546
#define IGC_TXD_DCMD (IGC_ADVTXD_DCMD_EOP | IGC_ADVTXD_DCMD_RS)

drivers/net/ethernet/intel/igc/igc_defines.h

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -218,6 +218,7 @@
218218
#define IGC_ICR_RXDMT0 BIT(4) /* Rx desc min. threshold (0) */
219219
#define IGC_ICR_RXO BIT(6) /* Rx overrun */
220220
#define IGC_ICR_RXT0 BIT(7) /* Rx timer intr (ring 0) */
221+
#define IGC_ICR_TS BIT(19) /* Time Sync Interrupt */
221222
#define IGC_ICR_DRSTA BIT(30) /* Device Reset Asserted */
222223

223224
/* If this bit asserted, the driver should claim the interrupt */
@@ -240,6 +241,7 @@
240241
#define IGC_IMS_DRSTA IGC_ICR_DRSTA /* Device Reset Asserted */
241242
#define IGC_IMS_RXT0 IGC_ICR_RXT0 /* Rx timer intr */
242243
#define IGC_IMS_RXDMT0 IGC_ICR_RXDMT0 /* Rx desc min. threshold */
244+
#define IGC_IMS_TS IGC_ICR_TS /* Time Sync Interrupt */
243245

244246
#define IGC_QVECTOR_MASK 0x7FFC /* Q-vector mask */
245247
#define IGC_ITR_VAL_MASK 0x04 /* ITR value mask */
@@ -355,6 +357,16 @@
355357
#define I225_RXPBSIZE_DEFAULT 0x000000A2 /* RXPBSIZE default */
356358
#define I225_TXPBSIZE_DEFAULT 0x04000014 /* TXPBSIZE default */
357359

360+
/* Time Sync Interrupt Causes */
361+
#define IGC_TSICR_SYS_WRAP BIT(0) /* SYSTIM Wrap around. */
362+
#define IGC_TSICR_TXTS BIT(1) /* Transmit Timestamp. */
363+
#define IGC_TSICR_TT0 BIT(3) /* Target Time 0 Trigger. */
364+
#define IGC_TSICR_TT1 BIT(4) /* Target Time 1 Trigger. */
365+
#define IGC_TSICR_AUTT0 BIT(5) /* Auxiliary Timestamp 0 Taken. */
366+
#define IGC_TSICR_AUTT1 BIT(6) /* Auxiliary Timestamp 1 Taken. */
367+
368+
#define IGC_TSICR_INTERRUPTS IGC_TSICR_TXTS
369+
358370
/* Receive Checksum Control */
359371
#define IGC_RXCSUM_CRCOFL 0x00000800 /* CRC32 offload enable */
360372
#define IGC_RXCSUM_PCSD 0x00002000 /* packet checksum disabled */

drivers/net/ethernet/intel/igc/igc_main.c

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,9 @@ void igc_reset(struct igc_adapter *adapter)
102102
if (!netif_running(adapter->netdev))
103103
igc_power_down_link(adapter);
104104

105+
/* Re-enable PTP, where applicable. */
106+
igc_ptp_reset(adapter);
107+
105108
igc_get_phy_info(hw);
106109
}
107110

@@ -4277,6 +4280,24 @@ static int igc_close(struct net_device *netdev)
42774280
return 0;
42784281
}
42794282

4283+
/**
4284+
* igc_ioctl - Access the hwtstamp interface
4285+
* @netdev: network interface device structure
4286+
* @ifreq: interface request data
4287+
* @cmd: ioctl command
4288+
**/
4289+
static int igc_ioctl(struct net_device *netdev, struct ifreq *ifr, int cmd)
4290+
{
4291+
switch (cmd) {
4292+
case SIOCGHWTSTAMP:
4293+
return igc_ptp_get_ts_config(netdev, ifr);
4294+
case SIOCSHWTSTAMP:
4295+
return igc_ptp_set_ts_config(netdev, ifr);
4296+
default:
4297+
return -EOPNOTSUPP;
4298+
}
4299+
}
4300+
42804301
static const struct net_device_ops igc_netdev_ops = {
42814302
.ndo_open = igc_open,
42824303
.ndo_stop = igc_close,
@@ -4288,6 +4309,7 @@ static const struct net_device_ops igc_netdev_ops = {
42884309
.ndo_fix_features = igc_fix_features,
42894310
.ndo_set_features = igc_set_features,
42904311
.ndo_features_check = igc_features_check,
4312+
.ndo_do_ioctl = igc_ioctl,
42914313
};
42924314

42934315
/* PCIe configuration access */
@@ -4588,6 +4610,9 @@ static int igc_probe(struct pci_dev *pdev,
45884610
/* carrier off reporting is important to ethtool even BEFORE open */
45894611
netif_carrier_off(netdev);
45904612

4613+
/* do hw tstamp init after resetting */
4614+
igc_ptp_init(adapter);
4615+
45914616
/* Check if Media Autosense is enabled */
45924617
adapter->ei = *ei;
45934618

@@ -4629,6 +4654,8 @@ static void igc_remove(struct pci_dev *pdev)
46294654
struct net_device *netdev = pci_get_drvdata(pdev);
46304655
struct igc_adapter *adapter = netdev_priv(netdev);
46314656

4657+
igc_ptp_stop(adapter);
4658+
46324659
set_bit(__IGC_DOWN, &adapter->state);
46334660

46344661
del_timer_sync(&adapter->watchdog_timer);

0 commit comments

Comments
 (0)