Commit 6d71f164 authored by David S. Miller's avatar David S. Miller

Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/jkirsher/net-next

Jeff Kirsher says:

====================
Intel Wired LAN Driver Updates

This series contains updates to i40e and now i40evf.

Most notable is Jacob's patch to add PTP support to i40e.

Mitch cleans up additional memcpy's and use struct assignment instead.
Then fixes long lines to appease checkpatch.pl.  Mitch then provides
a fix to keep us from spamming the log with confusing errors.  If you
use ip to change the MAC address of a VF while the VF driver is loaded,
closing the VF interface or unloading the VF driver will cause the VF
driver to remove the MAC filter for its original (now invalid) MAC
address.

Jesse cleans up macros which are no longer needed or used.

I (Jeff) cleanup function header comments to ensure Doxygen/kdoc works
correctly to generate documentation without warnings.

Anjali fixes a bug where ethtool set-channels would return failure when
configuring only one Rx queue.  Then fixes a bug where the driver was
erroneously exiting the driver unload path if one part of the unload
failed.

Shannon fixes if the IPV6EXADD but is set in the Rx descriptor status,
there was an optional extension header with an alternate IP address
detected and the hardware checksum was not handling the alternate IP
address correctly.  Then adjusts the ITR max and min values to match
the hardware max value and recommended min value.  Shannon makes sure
to clear the PXE mode after the adminq is initialized.

v2:
 - fix patch 14 "i40e: enable PTP" to address Richard Cochran's spelling
   catch and Ben Hutchings Kconfig, SIOCGHWTSTAMP and sizeof() suggestions
 - added Paul Gortmaker's i40evf fix patch
v3:
 - fix patch 14 "i40e: enable PTP" to address Ben Hutchings concerns about
   a race with PTP init and cleanup and i40e_get_ts_info().
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents 45593c2b 7ed3f5f0
......@@ -243,6 +243,7 @@ config IXGBEVF
config I40E
tristate "Intel(R) Ethernet Controller XL710 Family support"
select PTP_1588_CLOCK
depends on PCI
---help---
This driver supports Intel(R) Ethernet Controller XL710 Family of
......
......@@ -40,4 +40,5 @@ i40e-objs := i40e_main.o \
i40e_debugfs.o \
i40e_diag.o \
i40e_txrx.o \
i40e_ptp.o \
i40e_virtchnl_pf.o
......@@ -50,6 +50,9 @@
#include <net/ip6_checksum.h>
#include <linux/ethtool.h>
#include <linux/if_vlan.h>
#include <linux/clocksource.h>
#include <linux/net_tstamp.h>
#include <linux/ptp_clock_kernel.h>
#include "i40e_type.h"
#include "i40e_prototype.h"
#include "i40e_virtchnl.h"
......@@ -88,7 +91,7 @@
/* The values in here are decimal coded as hex as is the case in the NVM map*/
#define I40E_CURRENT_NVM_VERSION_HI 0x2
#define I40E_CURRENT_NVM_VERSION_LO 0x1
#define I40E_CURRENT_NVM_VERSION_LO 0x30
/* magic for getting defines into strings */
......@@ -242,6 +245,7 @@ struct i40e_pf {
#define I40E_FLAG_DCB_ENABLED (u64)(1 << 20)
#define I40E_FLAG_FDIR_ENABLED (u64)(1 << 21)
#define I40E_FLAG_FDIR_ATR_ENABLED (u64)(1 << 22)
#define I40E_FLAG_PTP (u64)(1 << 25)
#define I40E_FLAG_MFP_ENABLED (u64)(1 << 26)
#ifdef CONFIG_I40E_VXLAN
#define I40E_FLAG_VXLAN_FILTER_SYNC (u64)(1 << 27)
......@@ -302,6 +306,20 @@ struct i40e_pf {
u32 fcoe_hmc_filt_num;
u32 fcoe_hmc_cntx_num;
struct i40e_filter_control_settings filter_settings;
struct ptp_clock *ptp_clock;
struct ptp_clock_info ptp_caps;
struct sk_buff *ptp_tx_skb;
struct work_struct ptp_tx_work;
struct hwtstamp_config tstamp_config;
unsigned long ptp_tx_start;
unsigned long last_rx_ptp_check;
spinlock_t tmreg_lock; /* Used to protect the device time registers. */
u64 ptp_base_adj;
u32 tx_hwtstamp_timeouts;
u32 rx_hwtstamp_cleared;
bool ptp_tx;
bool ptp_rx;
};
struct i40e_mac_filter {
......@@ -566,4 +584,12 @@ struct i40e_mac_filter *i40e_find_mac(struct i40e_vsi *vsi, u8 *macaddr,
bool is_vf, bool is_netdev);
void i40e_vlan_stripping_enable(struct i40e_vsi *vsi);
void i40e_ptp_rx_hang(struct i40e_vsi *vsi);
void i40e_ptp_tx_hwtstamp(struct i40e_pf *pf);
void i40e_ptp_rx_hwtstamp(struct i40e_pf *pf, struct sk_buff *skb, u8 index);
void i40e_ptp_set_increment(struct i40e_pf *pf);
int i40e_ptp_set_ts_config(struct i40e_pf *pf, struct ifreq *ifr);
int i40e_ptp_get_ts_config(struct i40e_pf *pf, struct ifreq *ifr);
void i40e_ptp_init(struct i40e_pf *pf);
void i40e_ptp_stop(struct i40e_pf *pf);
#endif /* _I40E_H_ */
......@@ -626,7 +626,7 @@ i40e_status i40e_shutdown_adminq(struct i40e_hw *hw)
/**
* i40e_clean_asq - cleans Admin send queue
* @asq: pointer to the adminq send ring
* @hw: pointer to the hardware structure
*
* returns the number of free desc
**/
......@@ -922,7 +922,7 @@ i40e_status i40e_clean_arq_element(struct i40e_hw *hw,
"AQRX: Event received with error 0x%X.\n",
hw->aq.arq_last_status);
} else {
memcpy(&e->desc, desc, sizeof(struct i40e_aq_desc));
e->desc = *desc;
datalen = le16_to_cpu(desc->datalen);
e->msg_size = min(datalen, e->msg_size);
if (e->msg_buf != NULL && (e->msg_size != 0))
......
......@@ -74,7 +74,8 @@ static i40e_status i40e_set_mac_type(struct i40e_hw *hw)
/**
* i40e_debug_aq
* @hw: debug mask related to admin queue
* @cap: pointer to adminq command descriptor
* @mask: debug mask
* @desc: pointer to admin queue descriptor
* @buffer: pointer to command buffer
*
* Dumps debug log about adminq command with descriptor contents.
......@@ -599,8 +600,7 @@ i40e_status i40e_aq_get_link_info(struct i40e_hw *hw,
goto aq_get_link_info_exit;
/* save off old link status information */
memcpy(&hw->phy.link_info_old, hw_link_info,
sizeof(struct i40e_link_status));
hw->phy.link_info_old = *hw_link_info;
/* update link status */
hw_link_info->phy_type = (enum i40e_aq_phy_type)resp->phy_type;
......@@ -630,7 +630,7 @@ i40e_status i40e_aq_get_link_info(struct i40e_hw *hw,
/**
* i40e_aq_add_vsi
* @hw: pointer to the hw struct
* @vsi: pointer to a vsi context struct
* @vsi_ctx: pointer to a vsi context struct
* @cmd_details: pointer to command details structure or NULL
*
* Add a VSI context to the hardware.
......@@ -682,7 +682,8 @@ i40e_status i40e_aq_add_vsi(struct i40e_hw *hw,
* @cmd_details: pointer to command details structure or NULL
**/
i40e_status i40e_aq_set_vsi_unicast_promiscuous(struct i40e_hw *hw,
u16 seid, bool set, struct i40e_asq_cmd_details *cmd_details)
u16 seid, bool set,
struct i40e_asq_cmd_details *cmd_details)
{
struct i40e_aq_desc desc;
struct i40e_aqc_set_vsi_promiscuous_modes *cmd =
......@@ -776,7 +777,7 @@ i40e_status i40e_aq_set_vsi_broadcast(struct i40e_hw *hw,
/**
* i40e_get_vsi_params - get VSI configuration info
* @hw: pointer to the hw struct
* @vsi: pointer to a vsi context struct
* @vsi_ctx: pointer to a vsi context struct
* @cmd_details: pointer to command details structure or NULL
**/
i40e_status i40e_aq_get_vsi_params(struct i40e_hw *hw,
......@@ -818,7 +819,7 @@ i40e_status i40e_aq_get_vsi_params(struct i40e_hw *hw,
/**
* i40e_aq_update_vsi_params
* @hw: pointer to the hw struct
* @vsi: pointer to a vsi context struct
* @vsi_ctx: pointer to a vsi context struct
* @cmd_details: pointer to command details structure or NULL
*
* Update a VSI context.
......@@ -921,7 +922,6 @@ i40e_status i40e_aq_get_firmware_version(struct i40e_hw *hw,
/**
* i40e_aq_send_driver_version
* @hw: pointer to the hw struct
* @event: driver event: driver ok, start or stop
* @dv: driver's major, minor version
* @cmd_details: pointer to command details structure or NULL
*
......@@ -1039,10 +1039,10 @@ i40e_status i40e_aq_add_veb(struct i40e_hw *hw, u16 uplink_seid,
* @hw: pointer to the hw struct
* @veb_seid: the SEID of the VEB to query
* @switch_id: the uplink switch id
* @floating_veb: set to true if the VEB is floating
* @floating: set to true if the VEB is floating
* @statistic_index: index of the stats counter block for this VEB
* @vebs_used: number of VEB's used by function
* @vebs_unallocated: total VEB's not reserved by any function
* @vebs_free: total VEB's not reserved by any function
* @cmd_details: pointer to command details structure or NULL
*
* This retrieves the parameters for a particular VEB, specified by
......@@ -1179,6 +1179,8 @@ i40e_status i40e_aq_remove_macvlan(struct i40e_hw *hw, u16 seid,
* i40e_aq_send_msg_to_vf
* @hw: pointer to the hardware structure
* @vfid: vf id to send msg
* @v_opcode: opcodes for VF-PF communication
* @v_retval: return error code
* @msg: pointer to the msg buffer
* @msglen: msg length
* @cmd_details: pointer to command details
......@@ -1723,6 +1725,7 @@ i40e_status i40e_aq_start_lldp(struct i40e_hw *hw,
* @udp_port: the UDP port to add
* @header_len: length of the tunneling header length in DWords
* @protocol_index: protocol index type
* @filter_index: pointer to filter index
* @cmd_details: pointer to command details structure or NULL
**/
i40e_status i40e_aq_add_udp_tunnel(struct i40e_hw *hw,
......
......@@ -1083,7 +1083,7 @@ static ssize_t i40e_dbg_command_write(struct file *filp,
vsi = i40e_dbg_find_vsi(pf, vsi_seid);
if (!vsi) {
dev_info(&pf->pdev->dev,
"add relay: vsi VSI %d not found\n", vsi_seid);
"add relay: VSI %d not found\n", vsi_seid);
goto command_write_done;
}
......
......@@ -108,6 +108,8 @@ static struct i40e_stats i40e_gstrings_stats[] = {
I40E_PF_STAT("rx_oversize", stats.rx_oversize),
I40E_PF_STAT("rx_jabber", stats.rx_jabber),
I40E_PF_STAT("VF_admin_queue_requests", vf_aq_requests),
I40E_PF_STAT("tx_hwtstamp_timeouts", tx_hwtstamp_timeouts),
I40E_PF_STAT("rx_hwtstamp_cleared", rx_hwtstamp_cleared),
};
#define I40E_QUEUE_STATS_LEN(n) \
......@@ -748,7 +750,36 @@ static void i40e_get_strings(struct net_device *netdev, u32 stringset,
static int i40e_get_ts_info(struct net_device *dev,
struct ethtool_ts_info *info)
{
return ethtool_op_get_ts_info(dev, info);
struct i40e_pf *pf = i40e_netdev_to_pf(dev);
info->so_timestamping = SOF_TIMESTAMPING_TX_SOFTWARE |
SOF_TIMESTAMPING_RX_SOFTWARE |
SOF_TIMESTAMPING_SOFTWARE |
SOF_TIMESTAMPING_TX_HARDWARE |
SOF_TIMESTAMPING_RX_HARDWARE |
SOF_TIMESTAMPING_RAW_HARDWARE;
if (pf->ptp_clock)
info->phc_index = ptp_clock_index(pf->ptp_clock);
else
info->phc_index = -1;
info->tx_types = (1 << HWTSTAMP_TX_OFF) | (1 << HWTSTAMP_TX_ON);
info->rx_filters = (1 << HWTSTAMP_FILTER_NONE) |
(1 << HWTSTAMP_FILTER_PTP_V1_L4_SYNC) |
(1 << HWTSTAMP_FILTER_PTP_V1_L4_DELAY_REQ) |
(1 << HWTSTAMP_FILTER_PTP_V2_EVENT) |
(1 << HWTSTAMP_FILTER_PTP_V2_L2_EVENT) |
(1 << HWTSTAMP_FILTER_PTP_V2_L4_EVENT) |
(1 << HWTSTAMP_FILTER_PTP_V2_SYNC) |
(1 << HWTSTAMP_FILTER_PTP_V2_L2_SYNC) |
(1 << HWTSTAMP_FILTER_PTP_V2_L4_SYNC) |
(1 << HWTSTAMP_FILTER_PTP_V2_DELAY_REQ) |
(1 << HWTSTAMP_FILTER_PTP_V2_L2_DELAY_REQ) |
(1 << HWTSTAMP_FILTER_PTP_V2_L4_DELAY_REQ);
return 0;
}
static int i40e_link_test(struct net_device *netdev, u64 *data)
......@@ -1634,7 +1665,7 @@ static int i40e_set_channels(struct net_device *dev,
* class queue mapping
*/
new_count = i40e_reconfig_rss_queues(pf, count);
if (new_count > 1)
if (new_count > 0)
return 0;
else
return -EINVAL;
......
......@@ -89,11 +89,9 @@ i40e_status i40e_add_sd_table_entry(struct i40e_hw *hw,
sd_entry->u.pd_table.pd_entry =
(struct i40e_hmc_pd_entry *)
sd_entry->u.pd_table.pd_entry_virt_mem.va;
memcpy(&sd_entry->u.pd_table.pd_page_addr, &mem,
sizeof(struct i40e_dma_mem));
sd_entry->u.pd_table.pd_page_addr = mem;
} else {
memcpy(&sd_entry->u.bp.addr, &mem,
sizeof(struct i40e_dma_mem));
sd_entry->u.bp.addr = mem;
sd_entry->u.bp.sd_pd_index = sd_index;
}
/* initialize the sd entry */
......@@ -164,7 +162,7 @@ i40e_status i40e_add_pd_table_entry(struct i40e_hw *hw,
if (ret_code)
goto exit;
memcpy(&pd_entry->bp.addr, &mem, sizeof(struct i40e_dma_mem));
pd_entry->bp.addr = mem;
pd_entry->bp.sd_pd_index = pd_index;
pd_entry->bp.entry_type = I40E_SD_TYPE_PAGED;
/* Set page address and valid bit */
......
......@@ -116,7 +116,6 @@ struct i40e_hmc_info {
* @hw: pointer to our hw struct
* @pa: pointer to physical address
* @sd_index: segment descriptor index
* @hmc_fn_id: hmc function id
* @type: if sd entry is direct or paged
**/
#define I40E_SET_PF_SD_ENTRY(hw, pa, sd_index, type) \
......@@ -138,7 +137,6 @@ struct i40e_hmc_info {
* I40E_CLEAR_PF_SD_ENTRY - marks the sd entry as invalid in the hardware
* @hw: pointer to our hw struct
* @sd_index: segment descriptor index
* @hmc_fn_id: hmc function id
* @type: if sd entry is direct or paged
**/
#define I40E_CLEAR_PF_SD_ENTRY(hw, sd_index, type) \
......@@ -159,7 +157,6 @@ struct i40e_hmc_info {
* @hw: pointer to our hw struct
* @sd_idx: segment descriptor index
* @pd_idx: page descriptor index
* @hmc_fn_id: hmc function id
**/
#define I40E_INVALIDATE_PF_HMC_PD(hw, sd_idx, pd_idx) \
wr32((hw), I40E_PFHMC_PDINV, \
......
......@@ -38,7 +38,7 @@ static const char i40e_driver_string[] =
#define DRV_VERSION_MAJOR 0
#define DRV_VERSION_MINOR 3
#define DRV_VERSION_BUILD 25
#define DRV_VERSION_BUILD 28
#define DRV_VERSION __stringify(DRV_VERSION_MAJOR) "." \
__stringify(DRV_VERSION_MINOR) "." \
__stringify(DRV_VERSION_BUILD) DRV_KERN
......@@ -1697,6 +1697,27 @@ static int i40e_change_mtu(struct net_device *netdev, int new_mtu)
return 0;
}
/**
* i40e_ioctl - Access the hwtstamp interface
* @netdev: network interface device structure
* @ifr: interface request data
* @cmd: ioctl command
**/
int i40e_ioctl(struct net_device *netdev, struct ifreq *ifr, int cmd)
{
struct i40e_netdev_priv *np = netdev_priv(netdev);
struct i40e_pf *pf = np->vsi->back;
switch (cmd) {
case SIOCGHWTSTAMP:
return i40e_ptp_get_ts_config(pf, ifr);
case SIOCSHWTSTAMP:
return i40e_ptp_set_ts_config(pf, ifr);
default:
return -EOPNOTSUPP;
}
}
/**
* i40e_vlan_stripping_enable - Turn on vlan stripping for the VSI
* @vsi: the vsi being adjusted
......@@ -2151,6 +2172,7 @@ static int i40e_configure_tx_ring(struct i40e_ring *ring)
tx_ctx.qlen = ring->count;
tx_ctx.fd_ena = !!(vsi->back->flags & (I40E_FLAG_FDIR_ENABLED |
I40E_FLAG_FDIR_ATR_ENABLED));
tx_ctx.timesync_ena = !!(vsi->back->flags & I40E_FLAG_PTP);
/* As part of VSI creation/update, FW allocates certain
* Tx arbitration queue sets for each TC enabled for
......@@ -2488,6 +2510,7 @@ static void i40e_enable_misc_int_causes(struct i40e_hw *hw)
I40E_PFINT_ICR0_ENA_GRST_MASK |
I40E_PFINT_ICR0_ENA_PCI_EXCEPTION_MASK |
I40E_PFINT_ICR0_ENA_GPIO_MASK |
I40E_PFINT_ICR0_ENA_TIMESYNC_MASK |
I40E_PFINT_ICR0_ENA_STORM_DETECT_MASK |
I40E_PFINT_ICR0_ENA_HMC_ERR_MASK |
I40E_PFINT_ICR0_ENA_VFLR_MASK |
......@@ -2831,6 +2854,18 @@ static irqreturn_t i40e_intr(int irq, void *data)
dev_info(&pf->pdev->dev, "HMC error interrupt\n");
}
if (icr0 & I40E_PFINT_ICR0_TIMESYNC_MASK) {
u32 prttsyn_stat = rd32(hw, I40E_PRTTSYN_STAT_0);
if (prttsyn_stat & I40E_PRTTSYN_STAT_0_TXTIME_MASK) {
ena_mask &= ~I40E_PFINT_ICR0_ENA_TIMESYNC_MASK;
i40e_ptp_tx_hwtstamp(pf);
prttsyn_stat &= ~I40E_PRTTSYN_STAT_0_TXTIME_MASK;
}
wr32(hw, I40E_PRTTSYN_STAT_0, prttsyn_stat);
}
/* If a critical error is pending we have no choice but to reset the
* device.
* Report and mask out any remaining unexpected interrupts.
......@@ -3008,11 +3043,13 @@ static int i40e_vsi_control_tx(struct i40e_vsi *vsi, bool enable)
continue;
/* turn on/off the queue */
if (enable)
if (enable) {
wr32(hw, I40E_QTX_HEAD(pf_q), 0);
tx_reg |= I40E_QTX_ENA_QENA_REQ_MASK |
I40E_QTX_ENA_QENA_STAT_MASK;
else
} else {
tx_reg &= ~I40E_QTX_ENA_QENA_REQ_MASK;
}
wr32(hw, I40E_QTX_ENA(pf_q), tx_reg);
......@@ -3113,7 +3150,7 @@ static int i40e_vsi_control_rx(struct i40e_vsi *vsi, bool enable)
**/
int i40e_vsi_control_rings(struct i40e_vsi *vsi, bool request)
{
int ret;
int ret = 0;
/* do rx first for enable and last for disable */
if (request) {
......@@ -3122,10 +3159,9 @@ int i40e_vsi_control_rings(struct i40e_vsi *vsi, bool request)
return ret;
ret = i40e_vsi_control_tx(vsi, request);
} else {
ret = i40e_vsi_control_tx(vsi, request);
if (ret)
return ret;
ret = i40e_vsi_control_rx(vsi, request);
/* Ignore return value, we need to shutdown whatever we can */
i40e_vsi_control_tx(vsi, request);
i40e_vsi_control_rx(vsi, request);
}
return ret;
......@@ -4303,6 +4339,9 @@ static void i40e_link_event(struct i40e_pf *pf)
if (pf->vf)
i40e_vc_notify_link_state(pf);
if (pf->flags & I40E_FLAG_PTP)
i40e_ptp_set_increment(pf);
}
/**
......@@ -4384,6 +4423,8 @@ static void i40e_watchdog_subtask(struct i40e_pf *pf)
for (i = 0; i < I40E_MAX_VEB; i++)
if (pf->veb[i])
i40e_update_veb_stats(pf->veb[i]);
i40e_ptp_rx_hang(pf->vsi[pf->lan_vsi]);
}
/**
......@@ -6032,6 +6073,7 @@ static const struct net_device_ops i40e_netdev_ops = {
.ndo_validate_addr = eth_validate_addr,
.ndo_set_mac_address = i40e_set_mac,
.ndo_change_mtu = i40e_change_mtu,
.ndo_do_ioctl = i40e_ioctl,
.ndo_tx_timeout = i40e_tx_timeout,
.ndo_vlan_rx_add_vid = i40e_vlan_rx_add_vid,
.ndo_vlan_rx_kill_vid = i40e_vlan_rx_kill_vid,
......@@ -7298,6 +7340,8 @@ static int i40e_setup_pf_switch(struct i40e_pf *pf, bool reinit)
~I40E_PRTDCB_MFLCN_RFCE_MASK);
fc_complete:
i40e_ptp_init(pf);
return ret;
}
......@@ -7611,6 +7655,7 @@ static int i40e_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
goto err_pf_reset;
}
i40e_clear_pxe_mode(hw);
err = i40e_get_capabilities(pf);
if (err)
goto err_adminq_setup;
......@@ -7801,6 +7846,8 @@ static void i40e_remove(struct pci_dev *pdev)
i40e_dbg_pf_exit(pf);
i40e_ptp_stop(pf);
if (pf->flags & I40E_FLAG_SRIOV_ENABLED) {
i40e_free_vfs(pf);
pf->flags &= ~I40E_FLAG_SRIOV_ENABLED;
......
......@@ -244,6 +244,7 @@ i40e_status i40e_read_nvm_buffer(struct i40e_hw *hw, u16 offset,
/**
* i40e_calc_nvm_checksum - Calculates and returns the checksum
* @hw: pointer to hardware structure
* @checksum: pointer to the checksum
*
* This function calculate SW Checksum that covers the whole 64kB shadow RAM
* except the VPD and PCIe ALT Auto-load modules. The structure and size of VPD
......
This diff is collapsed.
......@@ -892,6 +892,10 @@ static inline void i40e_rx_checksum(struct i40e_vsi *vsi,
rx_status & (1 << I40E_RX_DESC_STATUS_L3L4P_SHIFT)))
return;
/* likely incorrect csum if alternate IP extention headers found */
if (rx_status & (1 << I40E_RX_DESC_STATUS_IPV6EXADD_SHIFT))
return;
/* IP or L4 or outmost IP checksum error */
if (rx_error & ((1 << I40E_RX_DESC_ERROR_IPE_SHIFT) |
(1 << I40E_RX_DESC_ERROR_L4E_SHIFT) |
......@@ -1084,6 +1088,13 @@ static int i40e_clean_rx_irq(struct i40e_ring *rx_ring, int budget)
}
skb->rxhash = i40e_rx_hash(rx_ring, rx_desc);
if (unlikely(rx_status & I40E_RXD_QW1_STATUS_TSYNVALID_MASK)) {
i40e_ptp_rx_hwtstamp(vsi->back, skb, (rx_status &
I40E_RXD_QW1_STATUS_TSYNINDX_MASK) >>
I40E_RXD_QW1_STATUS_TSYNINDX_SHIFT);
rx_ring->last_rx_timestamp = jiffies;
}
/* probably a little skewed due to removing CRC */
total_rx_bytes += skb->len;
total_rx_packets++;
......@@ -1421,6 +1432,46 @@ static int i40e_tso(struct i40e_ring *tx_ring, struct sk_buff *skb,
return 1;
}
/**
* i40e_tsyn - set up the tsyn context descriptor
* @tx_ring: ptr to the ring to send
* @skb: ptr to the skb we're sending
* @tx_flags: the collected send information
*
* Returns 0 if no Tx timestamp can happen and 1 if the timestamp will happen
**/
static int i40e_tsyn(struct i40e_ring *tx_ring, struct sk_buff *skb,
u32 tx_flags, u64 *cd_type_cmd_tso_mss)
{
struct i40e_pf *pf;
if (likely(!(skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP)))
return 0;
/* Tx timestamps cannot be sampled when doing TSO */
if (tx_flags & I40E_TX_FLAGS_TSO)
return 0;
/* only timestamp the outbound packet if the user has requested it and
* we are not already transmitting a packet to be timestamped
*/
pf = i40e_netdev_to_pf(tx_ring->netdev);
if (pf->ptp_tx && !pf->ptp_tx_skb) {
skb_shinfo(skb)->tx_flags |= SKBTX_IN_PROGRESS;
pf->ptp_tx_skb = skb_get(skb);
} else {
return 0;
}
*cd_type_cmd_tso_mss |= (u64)I40E_TX_CTX_DESC_TSYN <<
I40E_TXD_CTX_QW1_CMD_SHIFT;
pf->ptp_tx_start = jiffies;
schedule_work(&pf->ptp_tx_work);
return 1;
}
/**
* i40e_tx_enable_csum - Enable Tx checksum offloads
* @skb: send buffer
......@@ -1797,6 +1848,7 @@ static netdev_tx_t i40e_xmit_frame_ring(struct sk_buff *skb,
__be16 protocol;
u32 td_cmd = 0;
u8 hdr_len = 0;
int tsyn;
int tso;
if (0 == i40e_xmit_descriptor_count(skb, tx_ring))
return NETDEV_TX_BUSY;
......@@ -1827,6 +1879,11 @@ static netdev_tx_t i40e_xmit_frame_ring(struct sk_buff *skb,
skb_tx_timestamp(skb);
tsyn = i40e_tsyn(tx_ring, skb, tx_flags, &cd_type_cmd_tso_mss);
if (tsyn)
tx_flags |= I40E_TX_FLAGS_TSYN;
/* always enable CRC insertion offload */
td_cmd |= I40E_TX_DESC_CMD_ICRC;
......
......@@ -29,9 +29,8 @@
/* Interrupt Throttling and Rate Limiting (storm control) Goodies */
#define I40E_MAX_ITR 0x07FF
#define I40E_MIN_ITR 0x0001
#define I40E_ITR_USEC_RESOLUTION 2
#define I40E_MAX_ITR 0x0FF0 /* reg uses 2 usec resolution */
#define I40E_MIN_ITR 0x0004 /* reg uses 2 usec resolution */
#define I40E_MAX_IRATE 0x03F
#define I40E_MIN_IRATE 0x001
#define I40E_IRATE_USEC_RESOLUTION 4
......@@ -137,6 +136,7 @@ enum i40e_dyn_idx_t {
#define I40E_TX_FLAGS_IPV6 (u32)(1 << 5)
#define I40E_TX_FLAGS_FCCRC (u32)(1 << 6)
#define I40E_TX_FLAGS_FSO (u32)(1 << 7)
#define I40E_TX_FLAGS_TSYN (u32)(1 << 8)
#define I40E_TX_FLAGS_VLAN_MASK 0xffff0000
#define I40E_TX_FLAGS_VLAN_PRIO_MASK 0xe0000000
#define I40E_TX_FLAGS_VLAN_PRIO_SHIFT 29
......@@ -249,6 +249,8 @@ struct i40e_ring {
u8 atr_sample_rate;
u8 atr_count;
unsigned long last_rx_timestamp;
bool ring_active; /* is ring online or not */
/* stats structs */
......
......@@ -60,15 +60,6 @@
/* Max default timeout in ms, */
#define I40E_MAX_NVM_TIMEOUT 18000
/* Check whether address is multicast. This is little-endian specific check.*/
#define I40E_IS_MULTICAST(address) \
(bool)(((u8 *)(address))[0] & ((u8)0x01))
/* Check whether an address is broadcast. */
#define I40E_IS_BROADCAST(address) \
((((u8 *)(address))[0] == ((u8)0xff)) && \
(((u8 *)(address))[1] == ((u8)0xff)))
/* Switch from mc to the 2usec global time (this is the GTIME resolution) */
#define I40E_MS_TO_GTIME(time) (((time) * 1000) / 2)
......@@ -508,7 +499,9 @@ enum i40e_rx_desc_status_bits {
I40E_RX_DESC_STATUS_FLM_SHIFT = 11,
I40E_RX_DESC_STATUS_FLTSTAT_SHIFT = 12, /* 2 BITS */
I40E_RX_DESC_STATUS_LPBK_SHIFT = 14,
I40E_RX_DESC_STATUS_UDP_0_SHIFT = 16
I40E_RX_DESC_STATUS_IPV6EXADD_SHIFT = 15,
I40E_RX_DESC_STATUS_RESERVED_SHIFT = 16, /* 2 BITS */
I40E_RX_DESC_STATUS_UDP_0_SHIFT = 18
};
#define I40E_RXD_QW1_STATUS_TSYNINDX_SHIFT I40E_RX_DESC_STATUS_TSYNINDX_SHIFT
......
......@@ -1525,10 +1525,14 @@ static int i40e_vc_del_mac_addr_msg(struct i40e_vf *vf, u8 *msg, u16 msglen)
}
for (i = 0; i < al->num_elements; i++) {
ret = i40e_check_vf_permission(vf, al->list[i].addr);
if (ret)
if (is_broadcast_ether_addr(al->list[i].addr) ||
is_zero_ether_addr(al->list[i].addr)) {
dev_err(&pf->pdev->dev, "invalid VF MAC addr %pM\n",
al->list[i].addr);
ret = I40E_ERR_INVALID_MAC_ADDR;
goto error_param;
}
}
vsi = pf->vsi[vsi_id];
/* delete addresses from the list */
......
......@@ -21,6 +21,8 @@
*
******************************************************************************/
#include <linux/prefetch.h>
#include "i40evf.h"
static inline __le64 build_ctob(u32 td_cmd, u32 td_offset, unsigned int size,
......
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