xref: /openbmc/linux/drivers/net/ethernet/sfc/siena/efx_common.c (revision 7ae9fb1b7ecbb5d85d07857943f677fd1a559b18)
16e173d3bSMartin Habets // SPDX-License-Identifier: GPL-2.0-only
26e173d3bSMartin Habets /****************************************************************************
36e173d3bSMartin Habets  * Driver for Solarflare network controllers and boards
46e173d3bSMartin Habets  * Copyright 2018 Solarflare Communications Inc.
56e173d3bSMartin Habets  *
66e173d3bSMartin Habets  * This program is free software; you can redistribute it and/or modify it
76e173d3bSMartin Habets  * under the terms of the GNU General Public License version 2 as published
86e173d3bSMartin Habets  * by the Free Software Foundation, incorporated herein by reference.
96e173d3bSMartin Habets  */
106e173d3bSMartin Habets 
116e173d3bSMartin Habets #include "net_driver.h"
126e173d3bSMartin Habets #include <linux/filter.h>
136e173d3bSMartin Habets #include <linux/module.h>
146e173d3bSMartin Habets #include <linux/netdevice.h>
156e173d3bSMartin Habets #include <net/gre.h>
166e173d3bSMartin Habets #include "efx_common.h"
176e173d3bSMartin Habets #include "efx_channels.h"
186e173d3bSMartin Habets #include "efx.h"
196e173d3bSMartin Habets #include "mcdi.h"
206e173d3bSMartin Habets #include "selftest.h"
216e173d3bSMartin Habets #include "rx_common.h"
226e173d3bSMartin Habets #include "tx_common.h"
236e173d3bSMartin Habets #include "nic.h"
246e173d3bSMartin Habets #include "mcdi_port_common.h"
256e173d3bSMartin Habets #include "io.h"
266e173d3bSMartin Habets #include "mcdi_pcol.h"
276e173d3bSMartin Habets 
286e173d3bSMartin Habets static unsigned int debug = (NETIF_MSG_DRV | NETIF_MSG_PROBE |
296e173d3bSMartin Habets 			     NETIF_MSG_LINK | NETIF_MSG_IFDOWN |
306e173d3bSMartin Habets 			     NETIF_MSG_IFUP | NETIF_MSG_RX_ERR |
316e173d3bSMartin Habets 			     NETIF_MSG_TX_ERR | NETIF_MSG_HW);
326e173d3bSMartin Habets module_param(debug, uint, 0);
336e173d3bSMartin Habets MODULE_PARM_DESC(debug, "Bitmapped debugging message enable value");
346e173d3bSMartin Habets 
356e173d3bSMartin Habets /* This is the time (in jiffies) between invocations of the hardware
366e173d3bSMartin Habets  * monitor.
376e173d3bSMartin Habets  * On Falcon-based NICs, this will:
386e173d3bSMartin Habets  * - Check the on-board hardware monitor;
396e173d3bSMartin Habets  * - Poll the link state and reconfigure the hardware as necessary.
406e173d3bSMartin Habets  * On Siena-based NICs for power systems with EEH support, this will give EEH a
416e173d3bSMartin Habets  * chance to start.
426e173d3bSMartin Habets  */
436e173d3bSMartin Habets static unsigned int efx_monitor_interval = 1 * HZ;
446e173d3bSMartin Habets 
456e173d3bSMartin Habets /* How often and how many times to poll for a reset while waiting for a
466e173d3bSMartin Habets  * BIST that another function started to complete.
476e173d3bSMartin Habets  */
486e173d3bSMartin Habets #define BIST_WAIT_DELAY_MS	100
496e173d3bSMartin Habets #define BIST_WAIT_DELAY_COUNT	100
506e173d3bSMartin Habets 
516e173d3bSMartin Habets /* Default stats update time */
526e173d3bSMartin Habets #define STATS_PERIOD_MS_DEFAULT 1000
536e173d3bSMartin Habets 
546e173d3bSMartin Habets static const unsigned int efx_reset_type_max = RESET_TYPE_MAX;
556e173d3bSMartin Habets static const char *const efx_reset_type_names[] = {
566e173d3bSMartin Habets 	[RESET_TYPE_INVISIBLE]          = "INVISIBLE",
576e173d3bSMartin Habets 	[RESET_TYPE_ALL]                = "ALL",
586e173d3bSMartin Habets 	[RESET_TYPE_RECOVER_OR_ALL]     = "RECOVER_OR_ALL",
596e173d3bSMartin Habets 	[RESET_TYPE_WORLD]              = "WORLD",
606e173d3bSMartin Habets 	[RESET_TYPE_RECOVER_OR_DISABLE] = "RECOVER_OR_DISABLE",
616e173d3bSMartin Habets 	[RESET_TYPE_DATAPATH]           = "DATAPATH",
626e173d3bSMartin Habets 	[RESET_TYPE_MC_BIST]		= "MC_BIST",
636e173d3bSMartin Habets 	[RESET_TYPE_DISABLE]            = "DISABLE",
646e173d3bSMartin Habets 	[RESET_TYPE_TX_WATCHDOG]        = "TX_WATCHDOG",
656e173d3bSMartin Habets 	[RESET_TYPE_INT_ERROR]          = "INT_ERROR",
666e173d3bSMartin Habets 	[RESET_TYPE_DMA_ERROR]          = "DMA_ERROR",
676e173d3bSMartin Habets 	[RESET_TYPE_TX_SKIP]            = "TX_SKIP",
686e173d3bSMartin Habets 	[RESET_TYPE_MC_FAILURE]         = "MC_FAILURE",
696e173d3bSMartin Habets 	[RESET_TYPE_MCDI_TIMEOUT]	= "MCDI_TIMEOUT (FLR)",
706e173d3bSMartin Habets };
716e173d3bSMartin Habets 
726e173d3bSMartin Habets #define RESET_TYPE(type) \
736e173d3bSMartin Habets 	STRING_TABLE_LOOKUP(type, efx_reset_type)
746e173d3bSMartin Habets 
756e173d3bSMartin Habets /* Loopback mode names (see LOOPBACK_MODE()) */
7695e96f77SMartin Habets const unsigned int efx_siena_loopback_mode_max = LOOPBACK_MAX;
7795e96f77SMartin Habets const char *const efx_siena_loopback_mode_names[] = {
786e173d3bSMartin Habets 	[LOOPBACK_NONE]		= "NONE",
796e173d3bSMartin Habets 	[LOOPBACK_DATA]		= "DATAPATH",
806e173d3bSMartin Habets 	[LOOPBACK_GMAC]		= "GMAC",
816e173d3bSMartin Habets 	[LOOPBACK_XGMII]	= "XGMII",
826e173d3bSMartin Habets 	[LOOPBACK_XGXS]		= "XGXS",
836e173d3bSMartin Habets 	[LOOPBACK_XAUI]		= "XAUI",
846e173d3bSMartin Habets 	[LOOPBACK_GMII]		= "GMII",
856e173d3bSMartin Habets 	[LOOPBACK_SGMII]	= "SGMII",
866e173d3bSMartin Habets 	[LOOPBACK_XGBR]		= "XGBR",
876e173d3bSMartin Habets 	[LOOPBACK_XFI]		= "XFI",
886e173d3bSMartin Habets 	[LOOPBACK_XAUI_FAR]	= "XAUI_FAR",
896e173d3bSMartin Habets 	[LOOPBACK_GMII_FAR]	= "GMII_FAR",
906e173d3bSMartin Habets 	[LOOPBACK_SGMII_FAR]	= "SGMII_FAR",
916e173d3bSMartin Habets 	[LOOPBACK_XFI_FAR]	= "XFI_FAR",
926e173d3bSMartin Habets 	[LOOPBACK_GPHY]		= "GPHY",
936e173d3bSMartin Habets 	[LOOPBACK_PHYXS]	= "PHYXS",
946e173d3bSMartin Habets 	[LOOPBACK_PCS]		= "PCS",
956e173d3bSMartin Habets 	[LOOPBACK_PMAPMD]	= "PMA/PMD",
966e173d3bSMartin Habets 	[LOOPBACK_XPORT]	= "XPORT",
976e173d3bSMartin Habets 	[LOOPBACK_XGMII_WS]	= "XGMII_WS",
986e173d3bSMartin Habets 	[LOOPBACK_XAUI_WS]	= "XAUI_WS",
996e173d3bSMartin Habets 	[LOOPBACK_XAUI_WS_FAR]  = "XAUI_WS_FAR",
1006e173d3bSMartin Habets 	[LOOPBACK_XAUI_WS_NEAR] = "XAUI_WS_NEAR",
1016e173d3bSMartin Habets 	[LOOPBACK_GMII_WS]	= "GMII_WS",
1026e173d3bSMartin Habets 	[LOOPBACK_XFI_WS]	= "XFI_WS",
1036e173d3bSMartin Habets 	[LOOPBACK_XFI_WS_FAR]	= "XFI_WS_FAR",
1046e173d3bSMartin Habets 	[LOOPBACK_PHYXS_WS]	= "PHYXS_WS",
1056e173d3bSMartin Habets };
1066e173d3bSMartin Habets 
1076e173d3bSMartin Habets /* Reset workqueue. If any NIC has a hardware failure then a reset will be
1086e173d3bSMartin Habets  * queued onto this work queue. This is not a per-nic work queue, because
1096e173d3bSMartin Habets  * efx_reset_work() acquires the rtnl lock, so resets are naturally serialised.
1106e173d3bSMartin Habets  */
1116e173d3bSMartin Habets static struct workqueue_struct *reset_workqueue;
1126e173d3bSMartin Habets 
efx_siena_create_reset_workqueue(void)11371ad88f6SMartin Habets int efx_siena_create_reset_workqueue(void)
1146e173d3bSMartin Habets {
115ef9b5770SMartin Habets 	reset_workqueue = create_singlethread_workqueue("sfc_siena_reset");
1166e173d3bSMartin Habets 	if (!reset_workqueue) {
1176e173d3bSMartin Habets 		printk(KERN_ERR "Failed to create reset workqueue\n");
1186e173d3bSMartin Habets 		return -ENOMEM;
1196e173d3bSMartin Habets 	}
1206e173d3bSMartin Habets 
1216e173d3bSMartin Habets 	return 0;
1226e173d3bSMartin Habets }
1236e173d3bSMartin Habets 
efx_siena_queue_reset_work(struct efx_nic * efx)12471ad88f6SMartin Habets void efx_siena_queue_reset_work(struct efx_nic *efx)
1256e173d3bSMartin Habets {
1266e173d3bSMartin Habets 	queue_work(reset_workqueue, &efx->reset_work);
1276e173d3bSMartin Habets }
1286e173d3bSMartin Habets 
efx_siena_flush_reset_workqueue(struct efx_nic * efx)12971ad88f6SMartin Habets void efx_siena_flush_reset_workqueue(struct efx_nic *efx)
1306e173d3bSMartin Habets {
1316e173d3bSMartin Habets 	cancel_work_sync(&efx->reset_work);
1326e173d3bSMartin Habets }
1336e173d3bSMartin Habets 
efx_siena_destroy_reset_workqueue(void)13471ad88f6SMartin Habets void efx_siena_destroy_reset_workqueue(void)
1356e173d3bSMartin Habets {
1366e173d3bSMartin Habets 	if (reset_workqueue) {
1376e173d3bSMartin Habets 		destroy_workqueue(reset_workqueue);
1386e173d3bSMartin Habets 		reset_workqueue = NULL;
1396e173d3bSMartin Habets 	}
1406e173d3bSMartin Habets }
1416e173d3bSMartin Habets 
1426e173d3bSMartin Habets /* We assume that efx->type->reconfigure_mac will always try to sync RX
1436e173d3bSMartin Habets  * filters and therefore needs to read-lock the filter table against freeing
1446e173d3bSMartin Habets  */
efx_siena_mac_reconfigure(struct efx_nic * efx,bool mtu_only)14571ad88f6SMartin Habets void efx_siena_mac_reconfigure(struct efx_nic *efx, bool mtu_only)
1466e173d3bSMartin Habets {
1476e173d3bSMartin Habets 	if (efx->type->reconfigure_mac) {
1486e173d3bSMartin Habets 		down_read(&efx->filter_sem);
1496e173d3bSMartin Habets 		efx->type->reconfigure_mac(efx, mtu_only);
1506e173d3bSMartin Habets 		up_read(&efx->filter_sem);
1516e173d3bSMartin Habets 	}
1526e173d3bSMartin Habets }
1536e173d3bSMartin Habets 
1546e173d3bSMartin Habets /* Asynchronous work item for changing MAC promiscuity and multicast
1556e173d3bSMartin Habets  * hash.  Avoid a drain/rx_ingress enable by reconfiguring the current
1566e173d3bSMartin Habets  * MAC directly.
1576e173d3bSMartin Habets  */
efx_mac_work(struct work_struct * data)1586e173d3bSMartin Habets static void efx_mac_work(struct work_struct *data)
1596e173d3bSMartin Habets {
1606e173d3bSMartin Habets 	struct efx_nic *efx = container_of(data, struct efx_nic, mac_work);
1616e173d3bSMartin Habets 
1626e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
1636e173d3bSMartin Habets 	if (efx->port_enabled)
16471ad88f6SMartin Habets 		efx_siena_mac_reconfigure(efx, false);
1656e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
1666e173d3bSMartin Habets }
1676e173d3bSMartin Habets 
efx_siena_set_mac_address(struct net_device * net_dev,void * data)16871ad88f6SMartin Habets int efx_siena_set_mac_address(struct net_device *net_dev, void *data)
1696e173d3bSMartin Habets {
1706e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
1716e173d3bSMartin Habets 	struct sockaddr *addr = data;
1726e173d3bSMartin Habets 	u8 *new_addr = addr->sa_data;
1736e173d3bSMartin Habets 	u8 old_addr[6];
1746e173d3bSMartin Habets 	int rc;
1756e173d3bSMartin Habets 
1766e173d3bSMartin Habets 	if (!is_valid_ether_addr(new_addr)) {
1776e173d3bSMartin Habets 		netif_err(efx, drv, efx->net_dev,
1786e173d3bSMartin Habets 			  "invalid ethernet MAC address requested: %pM\n",
1796e173d3bSMartin Habets 			  new_addr);
1806e173d3bSMartin Habets 		return -EADDRNOTAVAIL;
1816e173d3bSMartin Habets 	}
1826e173d3bSMartin Habets 
1836e173d3bSMartin Habets 	/* save old address */
1846e173d3bSMartin Habets 	ether_addr_copy(old_addr, net_dev->dev_addr);
1856e173d3bSMartin Habets 	eth_hw_addr_set(net_dev, new_addr);
1866e173d3bSMartin Habets 	if (efx->type->set_mac_address) {
1876e173d3bSMartin Habets 		rc = efx->type->set_mac_address(efx);
1886e173d3bSMartin Habets 		if (rc) {
1896e173d3bSMartin Habets 			eth_hw_addr_set(net_dev, old_addr);
1906e173d3bSMartin Habets 			return rc;
1916e173d3bSMartin Habets 		}
1926e173d3bSMartin Habets 	}
1936e173d3bSMartin Habets 
1946e173d3bSMartin Habets 	/* Reconfigure the MAC */
1956e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
19671ad88f6SMartin Habets 	efx_siena_mac_reconfigure(efx, false);
1976e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
1986e173d3bSMartin Habets 
1996e173d3bSMartin Habets 	return 0;
2006e173d3bSMartin Habets }
2016e173d3bSMartin Habets 
2026e173d3bSMartin Habets /* Context: netif_addr_lock held, BHs disabled. */
efx_siena_set_rx_mode(struct net_device * net_dev)20371ad88f6SMartin Habets void efx_siena_set_rx_mode(struct net_device *net_dev)
2046e173d3bSMartin Habets {
2056e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
2066e173d3bSMartin Habets 
2076e173d3bSMartin Habets 	if (efx->port_enabled)
2086e173d3bSMartin Habets 		queue_work(efx->workqueue, &efx->mac_work);
2096e173d3bSMartin Habets 	/* Otherwise efx_start_port() will do this */
2106e173d3bSMartin Habets }
2116e173d3bSMartin Habets 
efx_siena_set_features(struct net_device * net_dev,netdev_features_t data)21271ad88f6SMartin Habets int efx_siena_set_features(struct net_device *net_dev, netdev_features_t data)
2136e173d3bSMartin Habets {
2146e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
2156e173d3bSMartin Habets 	int rc;
2166e173d3bSMartin Habets 
2176e173d3bSMartin Habets 	/* If disabling RX n-tuple filtering, clear existing filters */
2186e173d3bSMartin Habets 	if (net_dev->features & ~data & NETIF_F_NTUPLE) {
2196e173d3bSMartin Habets 		rc = efx->type->filter_clear_rx(efx, EFX_FILTER_PRI_MANUAL);
2206e173d3bSMartin Habets 		if (rc)
2216e173d3bSMartin Habets 			return rc;
2226e173d3bSMartin Habets 	}
2236e173d3bSMartin Habets 
2246e173d3bSMartin Habets 	/* If Rx VLAN filter is changed, update filters via mac_reconfigure.
2256e173d3bSMartin Habets 	 * If rx-fcs is changed, mac_reconfigure updates that too.
2266e173d3bSMartin Habets 	 */
2276e173d3bSMartin Habets 	if ((net_dev->features ^ data) & (NETIF_F_HW_VLAN_CTAG_FILTER |
2286e173d3bSMartin Habets 					  NETIF_F_RXFCS)) {
22971ad88f6SMartin Habets 		/* efx_siena_set_rx_mode() will schedule MAC work to update filters
2306e173d3bSMartin Habets 		 * when a new features are finally set in net_dev.
2316e173d3bSMartin Habets 		 */
23271ad88f6SMartin Habets 		efx_siena_set_rx_mode(net_dev);
2336e173d3bSMartin Habets 	}
2346e173d3bSMartin Habets 
2356e173d3bSMartin Habets 	return 0;
2366e173d3bSMartin Habets }
2376e173d3bSMartin Habets 
2386e173d3bSMartin Habets /* This ensures that the kernel is kept informed (via
2396e173d3bSMartin Habets  * netif_carrier_on/off) of the link status, and also maintains the
2406e173d3bSMartin Habets  * link status's stop on the port's TX queue.
2416e173d3bSMartin Habets  */
efx_siena_link_status_changed(struct efx_nic * efx)24271ad88f6SMartin Habets void efx_siena_link_status_changed(struct efx_nic *efx)
2436e173d3bSMartin Habets {
2446e173d3bSMartin Habets 	struct efx_link_state *link_state = &efx->link_state;
2456e173d3bSMartin Habets 
2466e173d3bSMartin Habets 	/* SFC Bug 5356: A net_dev notifier is registered, so we must ensure
2476e173d3bSMartin Habets 	 * that no events are triggered between unregister_netdev() and the
2486e173d3bSMartin Habets 	 * driver unloading. A more general condition is that NETDEV_CHANGE
2496e173d3bSMartin Habets 	 * can only be generated between NETDEV_UP and NETDEV_DOWN
2506e173d3bSMartin Habets 	 */
2516e173d3bSMartin Habets 	if (!netif_running(efx->net_dev))
2526e173d3bSMartin Habets 		return;
2536e173d3bSMartin Habets 
2546e173d3bSMartin Habets 	if (link_state->up != netif_carrier_ok(efx->net_dev)) {
2556e173d3bSMartin Habets 		efx->n_link_state_changes++;
2566e173d3bSMartin Habets 
2576e173d3bSMartin Habets 		if (link_state->up)
2586e173d3bSMartin Habets 			netif_carrier_on(efx->net_dev);
2596e173d3bSMartin Habets 		else
2606e173d3bSMartin Habets 			netif_carrier_off(efx->net_dev);
2616e173d3bSMartin Habets 	}
2626e173d3bSMartin Habets 
2636e173d3bSMartin Habets 	/* Status message for kernel log */
2646e173d3bSMartin Habets 	if (link_state->up)
2656e173d3bSMartin Habets 		netif_info(efx, link, efx->net_dev,
2666e173d3bSMartin Habets 			   "link up at %uMbps %s-duplex (MTU %d)\n",
2676e173d3bSMartin Habets 			   link_state->speed, link_state->fd ? "full" : "half",
2686e173d3bSMartin Habets 			   efx->net_dev->mtu);
2696e173d3bSMartin Habets 	else
2706e173d3bSMartin Habets 		netif_info(efx, link, efx->net_dev, "link down\n");
2716e173d3bSMartin Habets }
2726e173d3bSMartin Habets 
efx_siena_xdp_max_mtu(struct efx_nic * efx)27371ad88f6SMartin Habets unsigned int efx_siena_xdp_max_mtu(struct efx_nic *efx)
2746e173d3bSMartin Habets {
2756e173d3bSMartin Habets 	/* The maximum MTU that we can fit in a single page, allowing for
2766e173d3bSMartin Habets 	 * framing, overhead and XDP headroom + tailroom.
2776e173d3bSMartin Habets 	 */
2786e173d3bSMartin Habets 	int overhead = EFX_MAX_FRAME_LEN(0) + sizeof(struct efx_rx_page_state) +
2796e173d3bSMartin Habets 		       efx->rx_prefix_size + efx->type->rx_buffer_padding +
2806e173d3bSMartin Habets 		       efx->rx_ip_align + EFX_XDP_HEADROOM + EFX_XDP_TAILROOM;
2816e173d3bSMartin Habets 
2826e173d3bSMartin Habets 	return PAGE_SIZE - overhead;
2836e173d3bSMartin Habets }
2846e173d3bSMartin Habets 
2856e173d3bSMartin Habets /* Context: process, rtnl_lock() held. */
efx_siena_change_mtu(struct net_device * net_dev,int new_mtu)28671ad88f6SMartin Habets int efx_siena_change_mtu(struct net_device *net_dev, int new_mtu)
2876e173d3bSMartin Habets {
2886e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
2896e173d3bSMartin Habets 	int rc;
2906e173d3bSMartin Habets 
2916e173d3bSMartin Habets 	rc = efx_check_disabled(efx);
2926e173d3bSMartin Habets 	if (rc)
2936e173d3bSMartin Habets 		return rc;
2946e173d3bSMartin Habets 
2956e173d3bSMartin Habets 	if (rtnl_dereference(efx->xdp_prog) &&
29671ad88f6SMartin Habets 	    new_mtu > efx_siena_xdp_max_mtu(efx)) {
2976e173d3bSMartin Habets 		netif_err(efx, drv, efx->net_dev,
2986e173d3bSMartin Habets 			  "Requested MTU of %d too big for XDP (max: %d)\n",
29971ad88f6SMartin Habets 			  new_mtu, efx_siena_xdp_max_mtu(efx));
3006e173d3bSMartin Habets 		return -EINVAL;
3016e173d3bSMartin Habets 	}
3026e173d3bSMartin Habets 
3036e173d3bSMartin Habets 	netif_dbg(efx, drv, efx->net_dev, "changing MTU to %d\n", new_mtu);
3046e173d3bSMartin Habets 
3056e173d3bSMartin Habets 	efx_device_detach_sync(efx);
30671ad88f6SMartin Habets 	efx_siena_stop_all(efx);
3076e173d3bSMartin Habets 
3086e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
3096e173d3bSMartin Habets 	net_dev->mtu = new_mtu;
31071ad88f6SMartin Habets 	efx_siena_mac_reconfigure(efx, true);
3116e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
3126e173d3bSMartin Habets 
31371ad88f6SMartin Habets 	efx_siena_start_all(efx);
3146e173d3bSMartin Habets 	efx_device_attach_if_not_resetting(efx);
3156e173d3bSMartin Habets 	return 0;
3166e173d3bSMartin Habets }
3176e173d3bSMartin Habets 
3186e173d3bSMartin Habets /**************************************************************************
3196e173d3bSMartin Habets  *
3206e173d3bSMartin Habets  * Hardware monitor
3216e173d3bSMartin Habets  *
3226e173d3bSMartin Habets  **************************************************************************/
3236e173d3bSMartin Habets 
3246e173d3bSMartin Habets /* Run periodically off the general workqueue */
efx_monitor(struct work_struct * data)3256e173d3bSMartin Habets static void efx_monitor(struct work_struct *data)
3266e173d3bSMartin Habets {
3276e173d3bSMartin Habets 	struct efx_nic *efx = container_of(data, struct efx_nic,
3286e173d3bSMartin Habets 					   monitor_work.work);
3296e173d3bSMartin Habets 
3306e173d3bSMartin Habets 	netif_vdbg(efx, timer, efx->net_dev,
3316e173d3bSMartin Habets 		   "hardware monitor executing on CPU %d\n",
3326e173d3bSMartin Habets 		   raw_smp_processor_id());
3336e173d3bSMartin Habets 	BUG_ON(efx->type->monitor == NULL);
3346e173d3bSMartin Habets 
3356e173d3bSMartin Habets 	/* If the mac_lock is already held then it is likely a port
3366e173d3bSMartin Habets 	 * reconfiguration is already in place, which will likely do
3376e173d3bSMartin Habets 	 * most of the work of monitor() anyway.
3386e173d3bSMartin Habets 	 */
3396e173d3bSMartin Habets 	if (mutex_trylock(&efx->mac_lock)) {
3406e173d3bSMartin Habets 		if (efx->port_enabled && efx->type->monitor)
3416e173d3bSMartin Habets 			efx->type->monitor(efx);
3426e173d3bSMartin Habets 		mutex_unlock(&efx->mac_lock);
3436e173d3bSMartin Habets 	}
3446e173d3bSMartin Habets 
34571ad88f6SMartin Habets 	efx_siena_start_monitor(efx);
3466e173d3bSMartin Habets }
3476e173d3bSMartin Habets 
efx_siena_start_monitor(struct efx_nic * efx)34871ad88f6SMartin Habets void efx_siena_start_monitor(struct efx_nic *efx)
3496e173d3bSMartin Habets {
3506e173d3bSMartin Habets 	if (efx->type->monitor)
3516e173d3bSMartin Habets 		queue_delayed_work(efx->workqueue, &efx->monitor_work,
3526e173d3bSMartin Habets 				   efx_monitor_interval);
3536e173d3bSMartin Habets }
3546e173d3bSMartin Habets 
3556e173d3bSMartin Habets /**************************************************************************
3566e173d3bSMartin Habets  *
3576e173d3bSMartin Habets  * Event queue processing
3586e173d3bSMartin Habets  *
3596e173d3bSMartin Habets  *************************************************************************/
3606e173d3bSMartin Habets 
3616e173d3bSMartin Habets /* Channels are shutdown and reinitialised whilst the NIC is running
3626e173d3bSMartin Habets  * to propagate configuration changes (mtu, checksum offload), or
3636e173d3bSMartin Habets  * to clear hardware error conditions
3646e173d3bSMartin Habets  */
efx_start_datapath(struct efx_nic * efx)3656e173d3bSMartin Habets static void efx_start_datapath(struct efx_nic *efx)
3666e173d3bSMartin Habets {
3676e173d3bSMartin Habets 	netdev_features_t old_features = efx->net_dev->features;
3686e173d3bSMartin Habets 	bool old_rx_scatter = efx->rx_scatter;
3696e173d3bSMartin Habets 	size_t rx_buf_len;
3706e173d3bSMartin Habets 
3716e173d3bSMartin Habets 	/* Calculate the rx buffer allocation parameters required to
3726e173d3bSMartin Habets 	 * support the current MTU, including padding for header
3736e173d3bSMartin Habets 	 * alignment and overruns.
3746e173d3bSMartin Habets 	 */
3756e173d3bSMartin Habets 	efx->rx_dma_len = (efx->rx_prefix_size +
3766e173d3bSMartin Habets 			   EFX_MAX_FRAME_LEN(efx->net_dev->mtu) +
3776e173d3bSMartin Habets 			   efx->type->rx_buffer_padding);
3786e173d3bSMartin Habets 	rx_buf_len = (sizeof(struct efx_rx_page_state)   + EFX_XDP_HEADROOM +
3796e173d3bSMartin Habets 		      efx->rx_ip_align + efx->rx_dma_len + EFX_XDP_TAILROOM);
3806e173d3bSMartin Habets 
3816e173d3bSMartin Habets 	if (rx_buf_len <= PAGE_SIZE) {
3826e173d3bSMartin Habets 		efx->rx_scatter = efx->type->always_rx_scatter;
3836e173d3bSMartin Habets 		efx->rx_buffer_order = 0;
3846e173d3bSMartin Habets 	} else if (efx->type->can_rx_scatter) {
3856e173d3bSMartin Habets 		BUILD_BUG_ON(EFX_RX_USR_BUF_SIZE % L1_CACHE_BYTES);
3866e173d3bSMartin Habets 		BUILD_BUG_ON(sizeof(struct efx_rx_page_state) +
3876e173d3bSMartin Habets 			     2 * ALIGN(NET_IP_ALIGN + EFX_RX_USR_BUF_SIZE,
3886e173d3bSMartin Habets 				       EFX_RX_BUF_ALIGNMENT) >
3896e173d3bSMartin Habets 			     PAGE_SIZE);
3906e173d3bSMartin Habets 		efx->rx_scatter = true;
3916e173d3bSMartin Habets 		efx->rx_dma_len = EFX_RX_USR_BUF_SIZE;
3926e173d3bSMartin Habets 		efx->rx_buffer_order = 0;
3936e173d3bSMartin Habets 	} else {
3946e173d3bSMartin Habets 		efx->rx_scatter = false;
3956e173d3bSMartin Habets 		efx->rx_buffer_order = get_order(rx_buf_len);
3966e173d3bSMartin Habets 	}
3976e173d3bSMartin Habets 
3987f9e4b2aSMartin Habets 	efx_siena_rx_config_page_split(efx);
3996e173d3bSMartin Habets 	if (efx->rx_buffer_order)
4006e173d3bSMartin Habets 		netif_dbg(efx, drv, efx->net_dev,
4016e173d3bSMartin Habets 			  "RX buf len=%u; page order=%u batch=%u\n",
4026e173d3bSMartin Habets 			  efx->rx_dma_len, efx->rx_buffer_order,
4036e173d3bSMartin Habets 			  efx->rx_pages_per_batch);
4046e173d3bSMartin Habets 	else
4056e173d3bSMartin Habets 		netif_dbg(efx, drv, efx->net_dev,
4066e173d3bSMartin Habets 			  "RX buf len=%u step=%u bpp=%u; page batch=%u\n",
4076e173d3bSMartin Habets 			  efx->rx_dma_len, efx->rx_page_buf_step,
4086e173d3bSMartin Habets 			  efx->rx_bufs_per_page, efx->rx_pages_per_batch);
4096e173d3bSMartin Habets 
4106e173d3bSMartin Habets 	/* Restore previously fixed features in hw_features and remove
4116e173d3bSMartin Habets 	 * features which are fixed now
4126e173d3bSMartin Habets 	 */
4136e173d3bSMartin Habets 	efx->net_dev->hw_features |= efx->net_dev->features;
4146e173d3bSMartin Habets 	efx->net_dev->hw_features &= ~efx->fixed_features;
4156e173d3bSMartin Habets 	efx->net_dev->features |= efx->fixed_features;
4166e173d3bSMartin Habets 	if (efx->net_dev->features != old_features)
4176e173d3bSMartin Habets 		netdev_features_change(efx->net_dev);
4186e173d3bSMartin Habets 
4196e173d3bSMartin Habets 	/* RX filters may also have scatter-enabled flags */
4206e173d3bSMartin Habets 	if ((efx->rx_scatter != old_rx_scatter) &&
4216e173d3bSMartin Habets 	    efx->type->filter_update_rx_scatter)
4226e173d3bSMartin Habets 		efx->type->filter_update_rx_scatter(efx);
4236e173d3bSMartin Habets 
4246e173d3bSMartin Habets 	/* We must keep at least one descriptor in a TX ring empty.
4256e173d3bSMartin Habets 	 * We could avoid this when the queue size does not exactly
4266e173d3bSMartin Habets 	 * match the hardware ring size, but it's not that important.
4276e173d3bSMartin Habets 	 * Therefore we stop the queue when one more skb might fill
4286e173d3bSMartin Habets 	 * the ring completely.  We wake it when half way back to
4296e173d3bSMartin Habets 	 * empty.
4306e173d3bSMartin Habets 	 */
4317f9e4b2aSMartin Habets 	efx->txq_stop_thresh = efx->txq_entries - efx_siena_tx_max_skb_descs(efx);
4326e173d3bSMartin Habets 	efx->txq_wake_thresh = efx->txq_stop_thresh / 2;
4336e173d3bSMartin Habets 
4346e173d3bSMartin Habets 	/* Initialise the channels */
43571ad88f6SMartin Habets 	efx_siena_start_channels(efx);
4366e173d3bSMartin Habets 
43795e96f77SMartin Habets 	efx_siena_ptp_start_datapath(efx);
4386e173d3bSMartin Habets 
4396e173d3bSMartin Habets 	if (netif_device_present(efx->net_dev))
4406e173d3bSMartin Habets 		netif_tx_wake_all_queues(efx->net_dev);
4416e173d3bSMartin Habets }
4426e173d3bSMartin Habets 
efx_stop_datapath(struct efx_nic * efx)4436e173d3bSMartin Habets static void efx_stop_datapath(struct efx_nic *efx)
4446e173d3bSMartin Habets {
4456e173d3bSMartin Habets 	EFX_ASSERT_RESET_SERIALISED(efx);
4466e173d3bSMartin Habets 	BUG_ON(efx->port_enabled);
4476e173d3bSMartin Habets 
44895e96f77SMartin Habets 	efx_siena_ptp_stop_datapath(efx);
4496e173d3bSMartin Habets 
45071ad88f6SMartin Habets 	efx_siena_stop_channels(efx);
4516e173d3bSMartin Habets }
4526e173d3bSMartin Habets 
4536e173d3bSMartin Habets /**************************************************************************
4546e173d3bSMartin Habets  *
4556e173d3bSMartin Habets  * Port handling
4566e173d3bSMartin Habets  *
4576e173d3bSMartin Habets  **************************************************************************/
4586e173d3bSMartin Habets 
4594d49e5cdSMartin Habets /* Equivalent to efx_siena_link_set_advertising with all-zeroes, except does not
4606e173d3bSMartin Habets  * force the Autoneg bit on.
4616e173d3bSMartin Habets  */
efx_siena_link_clear_advertising(struct efx_nic * efx)46271ad88f6SMartin Habets void efx_siena_link_clear_advertising(struct efx_nic *efx)
4636e173d3bSMartin Habets {
4646e173d3bSMartin Habets 	bitmap_zero(efx->link_advertising, __ETHTOOL_LINK_MODE_MASK_NBITS);
4656e173d3bSMartin Habets 	efx->wanted_fc &= ~(EFX_FC_TX | EFX_FC_RX);
4666e173d3bSMartin Habets }
4676e173d3bSMartin Habets 
efx_siena_link_set_wanted_fc(struct efx_nic * efx,u8 wanted_fc)46871ad88f6SMartin Habets void efx_siena_link_set_wanted_fc(struct efx_nic *efx, u8 wanted_fc)
4696e173d3bSMartin Habets {
4706e173d3bSMartin Habets 	efx->wanted_fc = wanted_fc;
4716e173d3bSMartin Habets 	if (efx->link_advertising[0]) {
4726e173d3bSMartin Habets 		if (wanted_fc & EFX_FC_RX)
4736e173d3bSMartin Habets 			efx->link_advertising[0] |= (ADVERTISED_Pause |
4746e173d3bSMartin Habets 						     ADVERTISED_Asym_Pause);
4756e173d3bSMartin Habets 		else
4766e173d3bSMartin Habets 			efx->link_advertising[0] &= ~(ADVERTISED_Pause |
4776e173d3bSMartin Habets 						      ADVERTISED_Asym_Pause);
4786e173d3bSMartin Habets 		if (wanted_fc & EFX_FC_TX)
4796e173d3bSMartin Habets 			efx->link_advertising[0] ^= ADVERTISED_Asym_Pause;
4806e173d3bSMartin Habets 	}
4816e173d3bSMartin Habets }
4826e173d3bSMartin Habets 
efx_start_port(struct efx_nic * efx)4836e173d3bSMartin Habets static void efx_start_port(struct efx_nic *efx)
4846e173d3bSMartin Habets {
4856e173d3bSMartin Habets 	netif_dbg(efx, ifup, efx->net_dev, "start port\n");
4866e173d3bSMartin Habets 	BUG_ON(efx->port_enabled);
4876e173d3bSMartin Habets 
4886e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
4896e173d3bSMartin Habets 	efx->port_enabled = true;
4906e173d3bSMartin Habets 
4916e173d3bSMartin Habets 	/* Ensure MAC ingress/egress is enabled */
49271ad88f6SMartin Habets 	efx_siena_mac_reconfigure(efx, false);
4936e173d3bSMartin Habets 
4946e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
4956e173d3bSMartin Habets }
4966e173d3bSMartin Habets 
4976e173d3bSMartin Habets /* Cancel work for MAC reconfiguration, periodic hardware monitoring
4986e173d3bSMartin Habets  * and the async self-test, wait for them to finish and prevent them
4996e173d3bSMartin Habets  * being scheduled again.  This doesn't cover online resets, which
5006e173d3bSMartin Habets  * should only be cancelled when removing the device.
5016e173d3bSMartin Habets  */
efx_stop_port(struct efx_nic * efx)5026e173d3bSMartin Habets static void efx_stop_port(struct efx_nic *efx)
5036e173d3bSMartin Habets {
5046e173d3bSMartin Habets 	netif_dbg(efx, ifdown, efx->net_dev, "stop port\n");
5056e173d3bSMartin Habets 
5066e173d3bSMartin Habets 	EFX_ASSERT_RESET_SERIALISED(efx);
5076e173d3bSMartin Habets 
5086e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
5096e173d3bSMartin Habets 	efx->port_enabled = false;
5106e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
5116e173d3bSMartin Habets 
5126e173d3bSMartin Habets 	/* Serialise against efx_set_multicast_list() */
5136e173d3bSMartin Habets 	netif_addr_lock_bh(efx->net_dev);
5146e173d3bSMartin Habets 	netif_addr_unlock_bh(efx->net_dev);
5156e173d3bSMartin Habets 
5166e173d3bSMartin Habets 	cancel_delayed_work_sync(&efx->monitor_work);
51795e96f77SMartin Habets 	efx_siena_selftest_async_cancel(efx);
5186e173d3bSMartin Habets 	cancel_work_sync(&efx->mac_work);
5196e173d3bSMartin Habets }
5206e173d3bSMartin Habets 
5216e173d3bSMartin Habets /* If the interface is supposed to be running but is not, start
5226e173d3bSMartin Habets  * the hardware and software data path, regular activity for the port
5236e173d3bSMartin Habets  * (MAC statistics, link polling, etc.) and schedule the port to be
5246e173d3bSMartin Habets  * reconfigured.  Interrupts must already be enabled.  This function
5256e173d3bSMartin Habets  * is safe to call multiple times, so long as the NIC is not disabled.
5266e173d3bSMartin Habets  * Requires the RTNL lock.
5276e173d3bSMartin Habets  */
efx_siena_start_all(struct efx_nic * efx)52871ad88f6SMartin Habets void efx_siena_start_all(struct efx_nic *efx)
5296e173d3bSMartin Habets {
5306e173d3bSMartin Habets 	EFX_ASSERT_RESET_SERIALISED(efx);
5316e173d3bSMartin Habets 	BUG_ON(efx->state == STATE_DISABLED);
5326e173d3bSMartin Habets 
5336e173d3bSMartin Habets 	/* Check that it is appropriate to restart the interface. All
5346e173d3bSMartin Habets 	 * of these flags are safe to read under just the rtnl lock
5356e173d3bSMartin Habets 	 */
5366e173d3bSMartin Habets 	if (efx->port_enabled || !netif_running(efx->net_dev) ||
5376e173d3bSMartin Habets 	    efx->reset_pending)
5386e173d3bSMartin Habets 		return;
5396e173d3bSMartin Habets 
5406e173d3bSMartin Habets 	efx_start_port(efx);
5416e173d3bSMartin Habets 	efx_start_datapath(efx);
5426e173d3bSMartin Habets 
5436e173d3bSMartin Habets 	/* Start the hardware monitor if there is one */
54471ad88f6SMartin Habets 	efx_siena_start_monitor(efx);
5456e173d3bSMartin Habets 
5466e173d3bSMartin Habets 	/* Link state detection is normally event-driven; we have
5476e173d3bSMartin Habets 	 * to poll now because we could have missed a change
5486e173d3bSMartin Habets 	 */
5496e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
5504d49e5cdSMartin Habets 	if (efx_siena_mcdi_phy_poll(efx))
55171ad88f6SMartin Habets 		efx_siena_link_status_changed(efx);
5526e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
5536e173d3bSMartin Habets 
5546e173d3bSMartin Habets 	if (efx->type->start_stats) {
5556e173d3bSMartin Habets 		efx->type->start_stats(efx);
5566e173d3bSMartin Habets 		efx->type->pull_stats(efx);
5576e173d3bSMartin Habets 		spin_lock_bh(&efx->stats_lock);
5586e173d3bSMartin Habets 		efx->type->update_stats(efx, NULL, NULL);
5596e173d3bSMartin Habets 		spin_unlock_bh(&efx->stats_lock);
5606e173d3bSMartin Habets 	}
5616e173d3bSMartin Habets }
5626e173d3bSMartin Habets 
5636e173d3bSMartin Habets /* Quiesce the hardware and software data path, and regular activity
5646e173d3bSMartin Habets  * for the port without bringing the link down.  Safe to call multiple
5656e173d3bSMartin Habets  * times with the NIC in almost any state, but interrupts should be
5666e173d3bSMartin Habets  * enabled.  Requires the RTNL lock.
5676e173d3bSMartin Habets  */
efx_siena_stop_all(struct efx_nic * efx)56871ad88f6SMartin Habets void efx_siena_stop_all(struct efx_nic *efx)
5696e173d3bSMartin Habets {
5706e173d3bSMartin Habets 	EFX_ASSERT_RESET_SERIALISED(efx);
5716e173d3bSMartin Habets 
5726e173d3bSMartin Habets 	/* port_enabled can be read safely under the rtnl lock */
5736e173d3bSMartin Habets 	if (!efx->port_enabled)
5746e173d3bSMartin Habets 		return;
5756e173d3bSMartin Habets 
5766e173d3bSMartin Habets 	if (efx->type->update_stats) {
5776e173d3bSMartin Habets 		/* update stats before we go down so we can accurately count
5786e173d3bSMartin Habets 		 * rx_nodesc_drops
5796e173d3bSMartin Habets 		 */
5806e173d3bSMartin Habets 		efx->type->pull_stats(efx);
5816e173d3bSMartin Habets 		spin_lock_bh(&efx->stats_lock);
5826e173d3bSMartin Habets 		efx->type->update_stats(efx, NULL, NULL);
5836e173d3bSMartin Habets 		spin_unlock_bh(&efx->stats_lock);
5846e173d3bSMartin Habets 		efx->type->stop_stats(efx);
5856e173d3bSMartin Habets 	}
5866e173d3bSMartin Habets 
5876e173d3bSMartin Habets 	efx_stop_port(efx);
5886e173d3bSMartin Habets 
5896e173d3bSMartin Habets 	/* Stop the kernel transmit interface.  This is only valid if
5906e173d3bSMartin Habets 	 * the device is stopped or detached; otherwise the watchdog
5916e173d3bSMartin Habets 	 * may fire immediately.
5926e173d3bSMartin Habets 	 */
5936e173d3bSMartin Habets 	WARN_ON(netif_running(efx->net_dev) &&
5946e173d3bSMartin Habets 		netif_device_present(efx->net_dev));
5956e173d3bSMartin Habets 	netif_tx_disable(efx->net_dev);
5966e173d3bSMartin Habets 
5976e173d3bSMartin Habets 	efx_stop_datapath(efx);
5986e173d3bSMartin Habets }
5996e173d3bSMartin Habets 
efx_siena_update_stats_atomic(struct efx_nic * efx,u64 * full_stats,struct rtnl_link_stats64 * core_stats)600c8443b69SMartin Habets static size_t efx_siena_update_stats_atomic(struct efx_nic *efx, u64 *full_stats,
601c8443b69SMartin Habets 					    struct rtnl_link_stats64 *core_stats)
602c8443b69SMartin Habets {
603c8443b69SMartin Habets 	if (efx->type->update_stats_atomic)
604c8443b69SMartin Habets 		return efx->type->update_stats_atomic(efx, full_stats, core_stats);
605c8443b69SMartin Habets 	return efx->type->update_stats(efx, full_stats, core_stats);
606c8443b69SMartin Habets }
607c8443b69SMartin Habets 
6086e173d3bSMartin Habets /* Context: process, dev_base_lock or RTNL held, non-blocking. */
efx_siena_net_stats(struct net_device * net_dev,struct rtnl_link_stats64 * stats)60971ad88f6SMartin Habets void efx_siena_net_stats(struct net_device *net_dev,
61071ad88f6SMartin Habets 			 struct rtnl_link_stats64 *stats)
6116e173d3bSMartin Habets {
6126e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
6136e173d3bSMartin Habets 
6146e173d3bSMartin Habets 	spin_lock_bh(&efx->stats_lock);
615c8443b69SMartin Habets 	efx_siena_update_stats_atomic(efx, NULL, stats);
6166e173d3bSMartin Habets 	spin_unlock_bh(&efx->stats_lock);
6176e173d3bSMartin Habets }
6186e173d3bSMartin Habets 
6196e173d3bSMartin Habets /* Push loopback/power/transmit disable settings to the PHY, and reconfigure
6206e173d3bSMartin Habets  * the MAC appropriately. All other PHY configuration changes are pushed
6216e173d3bSMartin Habets  * through phy_op->set_settings(), and pushed asynchronously to the MAC
6226e173d3bSMartin Habets  * through efx_monitor().
6236e173d3bSMartin Habets  *
6246e173d3bSMartin Habets  * Callers must hold the mac_lock
6256e173d3bSMartin Habets  */
__efx_siena_reconfigure_port(struct efx_nic * efx)62671ad88f6SMartin Habets int __efx_siena_reconfigure_port(struct efx_nic *efx)
6276e173d3bSMartin Habets {
6286e173d3bSMartin Habets 	enum efx_phy_mode phy_mode;
6296e173d3bSMartin Habets 	int rc = 0;
6306e173d3bSMartin Habets 
6316e173d3bSMartin Habets 	WARN_ON(!mutex_is_locked(&efx->mac_lock));
6326e173d3bSMartin Habets 
6336e173d3bSMartin Habets 	/* Disable PHY transmit in mac level loopbacks */
6346e173d3bSMartin Habets 	phy_mode = efx->phy_mode;
6356e173d3bSMartin Habets 	if (LOOPBACK_INTERNAL(efx))
6366e173d3bSMartin Habets 		efx->phy_mode |= PHY_MODE_TX_DISABLED;
6376e173d3bSMartin Habets 	else
6386e173d3bSMartin Habets 		efx->phy_mode &= ~PHY_MODE_TX_DISABLED;
6396e173d3bSMartin Habets 
6406e173d3bSMartin Habets 	if (efx->type->reconfigure_port)
6416e173d3bSMartin Habets 		rc = efx->type->reconfigure_port(efx);
6426e173d3bSMartin Habets 
6436e173d3bSMartin Habets 	if (rc)
6446e173d3bSMartin Habets 		efx->phy_mode = phy_mode;
6456e173d3bSMartin Habets 
6466e173d3bSMartin Habets 	return rc;
6476e173d3bSMartin Habets }
6486e173d3bSMartin Habets 
6496e173d3bSMartin Habets /* Reinitialise the MAC to pick up new PHY settings, even if the port is
6506e173d3bSMartin Habets  * disabled.
6516e173d3bSMartin Habets  */
efx_siena_reconfigure_port(struct efx_nic * efx)65271ad88f6SMartin Habets int efx_siena_reconfigure_port(struct efx_nic *efx)
6536e173d3bSMartin Habets {
6546e173d3bSMartin Habets 	int rc;
6556e173d3bSMartin Habets 
6566e173d3bSMartin Habets 	EFX_ASSERT_RESET_SERIALISED(efx);
6576e173d3bSMartin Habets 
6586e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
65971ad88f6SMartin Habets 	rc = __efx_siena_reconfigure_port(efx);
6606e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
6616e173d3bSMartin Habets 
6626e173d3bSMartin Habets 	return rc;
6636e173d3bSMartin Habets }
6646e173d3bSMartin Habets 
6656e173d3bSMartin Habets /**************************************************************************
6666e173d3bSMartin Habets  *
6676e173d3bSMartin Habets  * Device reset and suspend
6686e173d3bSMartin Habets  *
6696e173d3bSMartin Habets  **************************************************************************/
6706e173d3bSMartin Habets 
efx_wait_for_bist_end(struct efx_nic * efx)6716e173d3bSMartin Habets static void efx_wait_for_bist_end(struct efx_nic *efx)
6726e173d3bSMartin Habets {
6736e173d3bSMartin Habets 	int i;
6746e173d3bSMartin Habets 
6756e173d3bSMartin Habets 	for (i = 0; i < BIST_WAIT_DELAY_COUNT; ++i) {
6764d49e5cdSMartin Habets 		if (efx_siena_mcdi_poll_reboot(efx))
6776e173d3bSMartin Habets 			goto out;
6786e173d3bSMartin Habets 		msleep(BIST_WAIT_DELAY_MS);
6796e173d3bSMartin Habets 	}
6806e173d3bSMartin Habets 
6816e173d3bSMartin Habets 	netif_err(efx, drv, efx->net_dev, "Warning: No MC reboot after BIST mode\n");
6826e173d3bSMartin Habets out:
6836e173d3bSMartin Habets 	/* Either way unset the BIST flag. If we found no reboot we probably
6846e173d3bSMartin Habets 	 * won't recover, but we should try.
6856e173d3bSMartin Habets 	 */
6866e173d3bSMartin Habets 	efx->mc_bist_for_other_fn = false;
6876e173d3bSMartin Habets }
6886e173d3bSMartin Habets 
6896e173d3bSMartin Habets /* Try recovery mechanisms.
6906e173d3bSMartin Habets  * For now only EEH is supported.
6916e173d3bSMartin Habets  * Returns 0 if the recovery mechanisms are unsuccessful.
6926e173d3bSMartin Habets  * Returns a non-zero value otherwise.
6936e173d3bSMartin Habets  */
efx_siena_try_recovery(struct efx_nic * efx)69471ad88f6SMartin Habets int efx_siena_try_recovery(struct efx_nic *efx)
6956e173d3bSMartin Habets {
6966e173d3bSMartin Habets #ifdef CONFIG_EEH
6976e173d3bSMartin Habets 	/* A PCI error can occur and not be seen by EEH because nothing
6986e173d3bSMartin Habets 	 * happens on the PCI bus. In this case the driver may fail and
6996e173d3bSMartin Habets 	 * schedule a 'recover or reset', leading to this recovery handler.
7006e173d3bSMartin Habets 	 * Manually call the eeh failure check function.
7016e173d3bSMartin Habets 	 */
7026e173d3bSMartin Habets 	struct eeh_dev *eehdev = pci_dev_to_eeh_dev(efx->pci_dev);
7036e173d3bSMartin Habets 	if (eeh_dev_check_failure(eehdev)) {
7046e173d3bSMartin Habets 		/* The EEH mechanisms will handle the error and reset the
7056e173d3bSMartin Habets 		 * device if necessary.
7066e173d3bSMartin Habets 		 */
7076e173d3bSMartin Habets 		return 1;
7086e173d3bSMartin Habets 	}
7096e173d3bSMartin Habets #endif
7106e173d3bSMartin Habets 	return 0;
7116e173d3bSMartin Habets }
7126e173d3bSMartin Habets 
7136e173d3bSMartin Habets /* Tears down the entire software state and most of the hardware state
7146e173d3bSMartin Habets  * before reset.
7156e173d3bSMartin Habets  */
efx_siena_reset_down(struct efx_nic * efx,enum reset_type method)71671ad88f6SMartin Habets void efx_siena_reset_down(struct efx_nic *efx, enum reset_type method)
7176e173d3bSMartin Habets {
7186e173d3bSMartin Habets 	EFX_ASSERT_RESET_SERIALISED(efx);
7196e173d3bSMartin Habets 
7206e173d3bSMartin Habets 	if (method == RESET_TYPE_MCDI_TIMEOUT)
7216e173d3bSMartin Habets 		efx->type->prepare_flr(efx);
7226e173d3bSMartin Habets 
72371ad88f6SMartin Habets 	efx_siena_stop_all(efx);
72471ad88f6SMartin Habets 	efx_siena_disable_interrupts(efx);
7256e173d3bSMartin Habets 
7266e173d3bSMartin Habets 	mutex_lock(&efx->mac_lock);
7276e173d3bSMartin Habets 	down_write(&efx->filter_sem);
7286e173d3bSMartin Habets 	mutex_lock(&efx->rss_lock);
7296e173d3bSMartin Habets 	efx->type->fini(efx);
7306e173d3bSMartin Habets }
7316e173d3bSMartin Habets 
7326e173d3bSMartin Habets /* Context: netif_tx_lock held, BHs disabled. */
efx_siena_watchdog(struct net_device * net_dev,unsigned int txqueue)73371ad88f6SMartin Habets void efx_siena_watchdog(struct net_device *net_dev, unsigned int txqueue)
7346e173d3bSMartin Habets {
7356e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
7366e173d3bSMartin Habets 
7376e173d3bSMartin Habets 	netif_err(efx, tx_err, efx->net_dev,
7386e173d3bSMartin Habets 		  "TX stuck with port_enabled=%d: resetting channels\n",
7396e173d3bSMartin Habets 		  efx->port_enabled);
7406e173d3bSMartin Habets 
74171ad88f6SMartin Habets 	efx_siena_schedule_reset(efx, RESET_TYPE_TX_WATCHDOG);
7426e173d3bSMartin Habets }
7436e173d3bSMartin Habets 
7446e173d3bSMartin Habets /* This function will always ensure that the locks acquired in
74571ad88f6SMartin Habets  * efx_siena_reset_down() are released. A failure return code indicates
7466e173d3bSMartin Habets  * that we were unable to reinitialise the hardware, and the
7476e173d3bSMartin Habets  * driver should be disabled. If ok is false, then the rx and tx
7486e173d3bSMartin Habets  * engines are not restarted, pending a RESET_DISABLE.
7496e173d3bSMartin Habets  */
efx_siena_reset_up(struct efx_nic * efx,enum reset_type method,bool ok)75071ad88f6SMartin Habets int efx_siena_reset_up(struct efx_nic *efx, enum reset_type method, bool ok)
7516e173d3bSMartin Habets {
7526e173d3bSMartin Habets 	int rc;
7536e173d3bSMartin Habets 
7546e173d3bSMartin Habets 	EFX_ASSERT_RESET_SERIALISED(efx);
7556e173d3bSMartin Habets 
7566e173d3bSMartin Habets 	if (method == RESET_TYPE_MCDI_TIMEOUT)
7576e173d3bSMartin Habets 		efx->type->finish_flr(efx);
7586e173d3bSMartin Habets 
7596e173d3bSMartin Habets 	/* Ensure that SRAM is initialised even if we're disabling the device */
7606e173d3bSMartin Habets 	rc = efx->type->init(efx);
7616e173d3bSMartin Habets 	if (rc) {
7626e173d3bSMartin Habets 		netif_err(efx, drv, efx->net_dev, "failed to initialise NIC\n");
7636e173d3bSMartin Habets 		goto fail;
7646e173d3bSMartin Habets 	}
7656e173d3bSMartin Habets 
7666e173d3bSMartin Habets 	if (!ok)
7676e173d3bSMartin Habets 		goto fail;
7686e173d3bSMartin Habets 
7696e173d3bSMartin Habets 	if (efx->port_initialized && method != RESET_TYPE_INVISIBLE &&
7706e173d3bSMartin Habets 	    method != RESET_TYPE_DATAPATH) {
7714d49e5cdSMartin Habets 		rc = efx_siena_mcdi_port_reconfigure(efx);
7726e173d3bSMartin Habets 		if (rc && rc != -EPERM)
7736e173d3bSMartin Habets 			netif_err(efx, drv, efx->net_dev,
7746e173d3bSMartin Habets 				  "could not restore PHY settings\n");
7756e173d3bSMartin Habets 	}
7766e173d3bSMartin Habets 
77771ad88f6SMartin Habets 	rc = efx_siena_enable_interrupts(efx);
7786e173d3bSMartin Habets 	if (rc)
7796e173d3bSMartin Habets 		goto fail;
7806e173d3bSMartin Habets 
781dfb1cfbdSMartin Habets #ifdef CONFIG_SFC_SIENA_SRIOV
7826e173d3bSMartin Habets 	rc = efx->type->vswitching_restore(efx);
7836e173d3bSMartin Habets 	if (rc) /* not fatal; the PF will still work fine */
7846e173d3bSMartin Habets 		netif_warn(efx, probe, efx->net_dev,
7856e173d3bSMartin Habets 			   "failed to restore vswitching rc=%d;"
7866e173d3bSMartin Habets 			   " VFs may not function\n", rc);
7876e173d3bSMartin Habets #endif
7886e173d3bSMartin Habets 
7896e173d3bSMartin Habets 	if (efx->type->rx_restore_rss_contexts)
7906e173d3bSMartin Habets 		efx->type->rx_restore_rss_contexts(efx);
7916e173d3bSMartin Habets 	mutex_unlock(&efx->rss_lock);
7926e173d3bSMartin Habets 	efx->type->filter_table_restore(efx);
7936e173d3bSMartin Habets 	up_write(&efx->filter_sem);
7946e173d3bSMartin Habets 	if (efx->type->sriov_reset)
7956e173d3bSMartin Habets 		efx->type->sriov_reset(efx);
7966e173d3bSMartin Habets 
7976e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
7986e173d3bSMartin Habets 
79971ad88f6SMartin Habets 	efx_siena_start_all(efx);
8006e173d3bSMartin Habets 
8016e173d3bSMartin Habets 	if (efx->type->udp_tnl_push_ports)
8026e173d3bSMartin Habets 		efx->type->udp_tnl_push_ports(efx);
8036e173d3bSMartin Habets 
8046e173d3bSMartin Habets 	return 0;
8056e173d3bSMartin Habets 
8066e173d3bSMartin Habets fail:
8076e173d3bSMartin Habets 	efx->port_initialized = false;
8086e173d3bSMartin Habets 
8096e173d3bSMartin Habets 	mutex_unlock(&efx->rss_lock);
8106e173d3bSMartin Habets 	up_write(&efx->filter_sem);
8116e173d3bSMartin Habets 	mutex_unlock(&efx->mac_lock);
8126e173d3bSMartin Habets 
8136e173d3bSMartin Habets 	return rc;
8146e173d3bSMartin Habets }
8156e173d3bSMartin Habets 
8166e173d3bSMartin Habets /* Reset the NIC using the specified method.  Note that the reset may
8176e173d3bSMartin Habets  * fail, in which case the card will be left in an unusable state.
8186e173d3bSMartin Habets  *
8196e173d3bSMartin Habets  * Caller must hold the rtnl_lock.
8206e173d3bSMartin Habets  */
efx_siena_reset(struct efx_nic * efx,enum reset_type method)82171ad88f6SMartin Habets int efx_siena_reset(struct efx_nic *efx, enum reset_type method)
8226e173d3bSMartin Habets {
8236e173d3bSMartin Habets 	int rc, rc2 = 0;
8246e173d3bSMartin Habets 	bool disabled;
8256e173d3bSMartin Habets 
8266e173d3bSMartin Habets 	netif_info(efx, drv, efx->net_dev, "resetting (%s)\n",
8276e173d3bSMartin Habets 		   RESET_TYPE(method));
8286e173d3bSMartin Habets 
8296e173d3bSMartin Habets 	efx_device_detach_sync(efx);
83071ad88f6SMartin Habets 	/* efx_siena_reset_down() grabs locks that prevent recovery on EF100.
8316e173d3bSMartin Habets 	 * EF100 reset is handled in the efx_nic_type callback below.
8326e173d3bSMartin Habets 	 */
8336e173d3bSMartin Habets 	if (efx_nic_rev(efx) != EFX_REV_EF100)
83471ad88f6SMartin Habets 		efx_siena_reset_down(efx, method);
8356e173d3bSMartin Habets 
8366e173d3bSMartin Habets 	rc = efx->type->reset(efx, method);
8376e173d3bSMartin Habets 	if (rc) {
8386e173d3bSMartin Habets 		netif_err(efx, drv, efx->net_dev, "failed to reset hardware\n");
8396e173d3bSMartin Habets 		goto out;
8406e173d3bSMartin Habets 	}
8416e173d3bSMartin Habets 
8426e173d3bSMartin Habets 	/* Clear flags for the scopes we covered.  We assume the NIC and
8436e173d3bSMartin Habets 	 * driver are now quiescent so that there is no race here.
8446e173d3bSMartin Habets 	 */
8456e173d3bSMartin Habets 	if (method < RESET_TYPE_MAX_METHOD)
8466e173d3bSMartin Habets 		efx->reset_pending &= -(1 << (method + 1));
8476e173d3bSMartin Habets 	else /* it doesn't fit into the well-ordered scope hierarchy */
8486e173d3bSMartin Habets 		__clear_bit(method, &efx->reset_pending);
8496e173d3bSMartin Habets 
8506e173d3bSMartin Habets 	/* Reinitialise bus-mastering, which may have been turned off before
8516e173d3bSMartin Habets 	 * the reset was scheduled. This is still appropriate, even in the
8526e173d3bSMartin Habets 	 * RESET_TYPE_DISABLE since this driver generally assumes the hardware
8536e173d3bSMartin Habets 	 * can respond to requests.
8546e173d3bSMartin Habets 	 */
8556e173d3bSMartin Habets 	pci_set_master(efx->pci_dev);
8566e173d3bSMartin Habets 
8576e173d3bSMartin Habets out:
8586e173d3bSMartin Habets 	/* Leave device stopped if necessary */
8596e173d3bSMartin Habets 	disabled = rc ||
8606e173d3bSMartin Habets 		method == RESET_TYPE_DISABLE ||
8616e173d3bSMartin Habets 		method == RESET_TYPE_RECOVER_OR_DISABLE;
8626e173d3bSMartin Habets 	if (efx_nic_rev(efx) != EFX_REV_EF100)
86371ad88f6SMartin Habets 		rc2 = efx_siena_reset_up(efx, method, !disabled);
8646e173d3bSMartin Habets 	if (rc2) {
8656e173d3bSMartin Habets 		disabled = true;
8666e173d3bSMartin Habets 		if (!rc)
8676e173d3bSMartin Habets 			rc = rc2;
8686e173d3bSMartin Habets 	}
8696e173d3bSMartin Habets 
8706e173d3bSMartin Habets 	if (disabled) {
8716e173d3bSMartin Habets 		dev_close(efx->net_dev);
8726e173d3bSMartin Habets 		netif_err(efx, drv, efx->net_dev, "has been disabled\n");
8736e173d3bSMartin Habets 		efx->state = STATE_DISABLED;
8746e173d3bSMartin Habets 	} else {
8756e173d3bSMartin Habets 		netif_dbg(efx, drv, efx->net_dev, "reset complete\n");
8766e173d3bSMartin Habets 		efx_device_attach_if_not_resetting(efx);
8776e173d3bSMartin Habets 	}
8786e173d3bSMartin Habets 	return rc;
8796e173d3bSMartin Habets }
8806e173d3bSMartin Habets 
8816e173d3bSMartin Habets /* The worker thread exists so that code that cannot sleep can
8826e173d3bSMartin Habets  * schedule a reset for later.
8836e173d3bSMartin Habets  */
efx_reset_work(struct work_struct * data)8846e173d3bSMartin Habets static void efx_reset_work(struct work_struct *data)
8856e173d3bSMartin Habets {
8866e173d3bSMartin Habets 	struct efx_nic *efx = container_of(data, struct efx_nic, reset_work);
8876e173d3bSMartin Habets 	unsigned long pending;
8886e173d3bSMartin Habets 	enum reset_type method;
8896e173d3bSMartin Habets 
8906e173d3bSMartin Habets 	pending = READ_ONCE(efx->reset_pending);
8916e173d3bSMartin Habets 	method = fls(pending) - 1;
8926e173d3bSMartin Habets 
8936e173d3bSMartin Habets 	if (method == RESET_TYPE_MC_BIST)
8946e173d3bSMartin Habets 		efx_wait_for_bist_end(efx);
8956e173d3bSMartin Habets 
8966e173d3bSMartin Habets 	if ((method == RESET_TYPE_RECOVER_OR_DISABLE ||
8976e173d3bSMartin Habets 	     method == RESET_TYPE_RECOVER_OR_ALL) &&
89871ad88f6SMartin Habets 	    efx_siena_try_recovery(efx))
8996e173d3bSMartin Habets 		return;
9006e173d3bSMartin Habets 
9016e173d3bSMartin Habets 	if (!pending)
9026e173d3bSMartin Habets 		return;
9036e173d3bSMartin Habets 
9046e173d3bSMartin Habets 	rtnl_lock();
9056e173d3bSMartin Habets 
90671ad88f6SMartin Habets 	/* We checked the state in efx_siena_schedule_reset() but it may
9076e173d3bSMartin Habets 	 * have changed by now.  Now that we have the RTNL lock,
9086e173d3bSMartin Habets 	 * it cannot change again.
9096e173d3bSMartin Habets 	 */
9106e173d3bSMartin Habets 	if (efx->state == STATE_READY)
91171ad88f6SMartin Habets 		(void)efx_siena_reset(efx, method);
9126e173d3bSMartin Habets 
9136e173d3bSMartin Habets 	rtnl_unlock();
9146e173d3bSMartin Habets }
9156e173d3bSMartin Habets 
efx_siena_schedule_reset(struct efx_nic * efx,enum reset_type type)91671ad88f6SMartin Habets void efx_siena_schedule_reset(struct efx_nic *efx, enum reset_type type)
9176e173d3bSMartin Habets {
9186e173d3bSMartin Habets 	enum reset_type method;
9196e173d3bSMartin Habets 
9206e173d3bSMartin Habets 	if (efx->state == STATE_RECOVERY) {
9216e173d3bSMartin Habets 		netif_dbg(efx, drv, efx->net_dev,
9226e173d3bSMartin Habets 			  "recovering: skip scheduling %s reset\n",
9236e173d3bSMartin Habets 			  RESET_TYPE(type));
9246e173d3bSMartin Habets 		return;
9256e173d3bSMartin Habets 	}
9266e173d3bSMartin Habets 
9276e173d3bSMartin Habets 	switch (type) {
9286e173d3bSMartin Habets 	case RESET_TYPE_INVISIBLE:
9296e173d3bSMartin Habets 	case RESET_TYPE_ALL:
9306e173d3bSMartin Habets 	case RESET_TYPE_RECOVER_OR_ALL:
9316e173d3bSMartin Habets 	case RESET_TYPE_WORLD:
9326e173d3bSMartin Habets 	case RESET_TYPE_DISABLE:
9336e173d3bSMartin Habets 	case RESET_TYPE_RECOVER_OR_DISABLE:
9346e173d3bSMartin Habets 	case RESET_TYPE_DATAPATH:
9356e173d3bSMartin Habets 	case RESET_TYPE_MC_BIST:
9366e173d3bSMartin Habets 	case RESET_TYPE_MCDI_TIMEOUT:
9376e173d3bSMartin Habets 		method = type;
9386e173d3bSMartin Habets 		netif_dbg(efx, drv, efx->net_dev, "scheduling %s reset\n",
9396e173d3bSMartin Habets 			  RESET_TYPE(method));
9406e173d3bSMartin Habets 		break;
9416e173d3bSMartin Habets 	default:
9426e173d3bSMartin Habets 		method = efx->type->map_reset_reason(type);
9436e173d3bSMartin Habets 		netif_dbg(efx, drv, efx->net_dev,
9446e173d3bSMartin Habets 			  "scheduling %s reset for %s\n",
9456e173d3bSMartin Habets 			  RESET_TYPE(method), RESET_TYPE(type));
9466e173d3bSMartin Habets 		break;
9476e173d3bSMartin Habets 	}
9486e173d3bSMartin Habets 
9496e173d3bSMartin Habets 	set_bit(method, &efx->reset_pending);
9506e173d3bSMartin Habets 	smp_mb(); /* ensure we change reset_pending before checking state */
9516e173d3bSMartin Habets 
9526e173d3bSMartin Habets 	/* If we're not READY then just leave the flags set as the cue
9536e173d3bSMartin Habets 	 * to abort probing or reschedule the reset later.
9546e173d3bSMartin Habets 	 */
9556e173d3bSMartin Habets 	if (READ_ONCE(efx->state) != STATE_READY)
9566e173d3bSMartin Habets 		return;
9576e173d3bSMartin Habets 
9586e173d3bSMartin Habets 	/* efx_process_channel() will no longer read events once a
9596e173d3bSMartin Habets 	 * reset is scheduled. So switch back to poll'd MCDI completions.
9606e173d3bSMartin Habets 	 */
9614d49e5cdSMartin Habets 	efx_siena_mcdi_mode_poll(efx);
9626e173d3bSMartin Habets 
96371ad88f6SMartin Habets 	efx_siena_queue_reset_work(efx);
9646e173d3bSMartin Habets }
9656e173d3bSMartin Habets 
9666e173d3bSMartin Habets /**************************************************************************
9676e173d3bSMartin Habets  *
9686e173d3bSMartin Habets  * Dummy NIC operations
9696e173d3bSMartin Habets  *
9706e173d3bSMartin Habets  * Can be used for some unimplemented operations
9716e173d3bSMartin Habets  * Needed so all function pointers are valid and do not have to be tested
9726e173d3bSMartin Habets  * before use
9736e173d3bSMartin Habets  *
9746e173d3bSMartin Habets  **************************************************************************/
efx_siena_port_dummy_op_int(struct efx_nic * efx)97571ad88f6SMartin Habets int efx_siena_port_dummy_op_int(struct efx_nic *efx)
9766e173d3bSMartin Habets {
9776e173d3bSMartin Habets 	return 0;
9786e173d3bSMartin Habets }
97971ad88f6SMartin Habets 
efx_siena_port_dummy_op_void(struct efx_nic * efx)98071ad88f6SMartin Habets void efx_siena_port_dummy_op_void(struct efx_nic *efx) {}
9816e173d3bSMartin Habets 
9826e173d3bSMartin Habets /**************************************************************************
9836e173d3bSMartin Habets  *
9846e173d3bSMartin Habets  * Data housekeeping
9856e173d3bSMartin Habets  *
9866e173d3bSMartin Habets  **************************************************************************/
9876e173d3bSMartin Habets 
9886e173d3bSMartin Habets /* This zeroes out and then fills in the invariants in a struct
9896e173d3bSMartin Habets  * efx_nic (including all sub-structures).
9906e173d3bSMartin Habets  */
efx_siena_init_struct(struct efx_nic * efx,struct pci_dev * pci_dev,struct net_device * net_dev)99171ad88f6SMartin Habets int efx_siena_init_struct(struct efx_nic *efx,
9926e173d3bSMartin Habets 			  struct pci_dev *pci_dev, struct net_device *net_dev)
9936e173d3bSMartin Habets {
9946e173d3bSMartin Habets 	int rc = -ENOMEM;
9956e173d3bSMartin Habets 
9966e173d3bSMartin Habets 	/* Initialise common structures */
9976e173d3bSMartin Habets 	INIT_LIST_HEAD(&efx->node);
9986e173d3bSMartin Habets 	INIT_LIST_HEAD(&efx->secondary_list);
9996e173d3bSMartin Habets 	spin_lock_init(&efx->biu_lock);
100065d4b471SMartin Habets #ifdef CONFIG_SFC_SIENA_MTD
10016e173d3bSMartin Habets 	INIT_LIST_HEAD(&efx->mtd_list);
10026e173d3bSMartin Habets #endif
10036e173d3bSMartin Habets 	INIT_WORK(&efx->reset_work, efx_reset_work);
10046e173d3bSMartin Habets 	INIT_DELAYED_WORK(&efx->monitor_work, efx_monitor);
100595e96f77SMartin Habets 	efx_siena_selftest_async_init(efx);
10066e173d3bSMartin Habets 	efx->pci_dev = pci_dev;
10076e173d3bSMartin Habets 	efx->msg_enable = debug;
10086e173d3bSMartin Habets 	efx->state = STATE_UNINIT;
1009f029c781SWolfram Sang 	strscpy(efx->name, pci_name(pci_dev), sizeof(efx->name));
10106e173d3bSMartin Habets 
10116e173d3bSMartin Habets 	efx->net_dev = net_dev;
10126e173d3bSMartin Habets 	efx->rx_prefix_size = efx->type->rx_prefix_size;
10136e173d3bSMartin Habets 	efx->rx_ip_align =
10146e173d3bSMartin Habets 		NET_IP_ALIGN ? (efx->rx_prefix_size + NET_IP_ALIGN) % 4 : 0;
10156e173d3bSMartin Habets 	efx->rx_packet_hash_offset =
10166e173d3bSMartin Habets 		efx->type->rx_hash_offset - efx->type->rx_prefix_size;
10176e173d3bSMartin Habets 	efx->rx_packet_ts_offset =
10186e173d3bSMartin Habets 		efx->type->rx_ts_offset - efx->type->rx_prefix_size;
10196e173d3bSMartin Habets 	INIT_LIST_HEAD(&efx->rss_context.list);
10206e173d3bSMartin Habets 	efx->rss_context.context_id = EFX_MCDI_RSS_CONTEXT_INVALID;
10216e173d3bSMartin Habets 	mutex_init(&efx->rss_lock);
10226e173d3bSMartin Habets 	efx->vport_id = EVB_PORT_ID_ASSIGNED;
10236e173d3bSMartin Habets 	spin_lock_init(&efx->stats_lock);
10246e173d3bSMartin Habets 	efx->vi_stride = EFX_DEFAULT_VI_STRIDE;
10256e173d3bSMartin Habets 	efx->num_mac_stats = MC_CMD_MAC_NSTATS;
10266e173d3bSMartin Habets 	BUILD_BUG_ON(MC_CMD_MAC_NSTATS - 1 != MC_CMD_MAC_GENERATION_END);
10276e173d3bSMartin Habets 	mutex_init(&efx->mac_lock);
10286e173d3bSMartin Habets 	init_rwsem(&efx->filter_sem);
10296e173d3bSMartin Habets #ifdef CONFIG_RFS_ACCEL
10306e173d3bSMartin Habets 	mutex_init(&efx->rps_mutex);
10316e173d3bSMartin Habets 	spin_lock_init(&efx->rps_hash_lock);
10326e173d3bSMartin Habets 	/* Failure to allocate is not fatal, but may degrade ARFS performance */
10336e173d3bSMartin Habets 	efx->rps_hash_table = kcalloc(EFX_ARFS_HASH_TABLE_SIZE,
10346e173d3bSMartin Habets 				      sizeof(*efx->rps_hash_table), GFP_KERNEL);
10356e173d3bSMartin Habets #endif
10366e173d3bSMartin Habets 	efx->mdio.dev = net_dev;
10376e173d3bSMartin Habets 	INIT_WORK(&efx->mac_work, efx_mac_work);
10386e173d3bSMartin Habets 	init_waitqueue_head(&efx->flush_wq);
10396e173d3bSMartin Habets 
10406e173d3bSMartin Habets 	efx->tx_queues_per_channel = 1;
10416e173d3bSMartin Habets 	efx->rxq_entries = EFX_DEFAULT_DMAQ_SIZE;
10426e173d3bSMartin Habets 	efx->txq_entries = EFX_DEFAULT_DMAQ_SIZE;
10436e173d3bSMartin Habets 
10446e173d3bSMartin Habets 	efx->mem_bar = UINT_MAX;
10456e173d3bSMartin Habets 
104671ad88f6SMartin Habets 	rc = efx_siena_init_channels(efx);
10476e173d3bSMartin Habets 	if (rc)
10486e173d3bSMartin Habets 		goto fail;
10496e173d3bSMartin Habets 
10506e173d3bSMartin Habets 	/* Would be good to use the net_dev name, but we're too early */
10516e173d3bSMartin Habets 	snprintf(efx->workqueue_name, sizeof(efx->workqueue_name), "sfc%s",
10526e173d3bSMartin Habets 		 pci_name(pci_dev));
10536e173d3bSMartin Habets 	efx->workqueue = create_singlethread_workqueue(efx->workqueue_name);
10546e173d3bSMartin Habets 	if (!efx->workqueue) {
10556e173d3bSMartin Habets 		rc = -ENOMEM;
10566e173d3bSMartin Habets 		goto fail;
10576e173d3bSMartin Habets 	}
10586e173d3bSMartin Habets 
10596e173d3bSMartin Habets 	return 0;
10606e173d3bSMartin Habets 
10616e173d3bSMartin Habets fail:
106271ad88f6SMartin Habets 	efx_siena_fini_struct(efx);
10636e173d3bSMartin Habets 	return rc;
10646e173d3bSMartin Habets }
10656e173d3bSMartin Habets 
efx_siena_fini_struct(struct efx_nic * efx)106671ad88f6SMartin Habets void efx_siena_fini_struct(struct efx_nic *efx)
10676e173d3bSMartin Habets {
10686e173d3bSMartin Habets #ifdef CONFIG_RFS_ACCEL
10696e173d3bSMartin Habets 	kfree(efx->rps_hash_table);
10706e173d3bSMartin Habets #endif
10716e173d3bSMartin Habets 
107271ad88f6SMartin Habets 	efx_siena_fini_channels(efx);
10736e173d3bSMartin Habets 
10746e173d3bSMartin Habets 	kfree(efx->vpd_sn);
10756e173d3bSMartin Habets 
10766e173d3bSMartin Habets 	if (efx->workqueue) {
10776e173d3bSMartin Habets 		destroy_workqueue(efx->workqueue);
10786e173d3bSMartin Habets 		efx->workqueue = NULL;
10796e173d3bSMartin Habets 	}
10806e173d3bSMartin Habets }
10816e173d3bSMartin Habets 
10826e173d3bSMartin Habets /* This configures the PCI device to enable I/O and DMA. */
efx_siena_init_io(struct efx_nic * efx,int bar,dma_addr_t dma_mask,unsigned int mem_map_size)108371ad88f6SMartin Habets int efx_siena_init_io(struct efx_nic *efx, int bar, dma_addr_t dma_mask,
10846e173d3bSMartin Habets 		      unsigned int mem_map_size)
10856e173d3bSMartin Habets {
10866e173d3bSMartin Habets 	struct pci_dev *pci_dev = efx->pci_dev;
10876e173d3bSMartin Habets 	int rc;
10886e173d3bSMartin Habets 
10896e173d3bSMartin Habets 	efx->mem_bar = UINT_MAX;
10906e173d3bSMartin Habets 
10916e173d3bSMartin Habets 	netif_dbg(efx, probe, efx->net_dev, "initialising I/O bar=%d\n", bar);
10926e173d3bSMartin Habets 
10936e173d3bSMartin Habets 	rc = pci_enable_device(pci_dev);
10946e173d3bSMartin Habets 	if (rc) {
10956e173d3bSMartin Habets 		netif_err(efx, probe, efx->net_dev,
10966e173d3bSMartin Habets 			  "failed to enable PCI device\n");
10976e173d3bSMartin Habets 		goto fail1;
10986e173d3bSMartin Habets 	}
10996e173d3bSMartin Habets 
11006e173d3bSMartin Habets 	pci_set_master(pci_dev);
11016e173d3bSMartin Habets 
11026e173d3bSMartin Habets 	rc = dma_set_mask_and_coherent(&pci_dev->dev, dma_mask);
11036e173d3bSMartin Habets 	if (rc) {
11046e173d3bSMartin Habets 		netif_err(efx, probe, efx->net_dev,
11056e173d3bSMartin Habets 			  "could not find a suitable DMA mask\n");
11066e173d3bSMartin Habets 		goto fail2;
11076e173d3bSMartin Habets 	}
11086e173d3bSMartin Habets 	netif_dbg(efx, probe, efx->net_dev,
11096e173d3bSMartin Habets 		  "using DMA mask %llx\n", (unsigned long long)dma_mask);
11106e173d3bSMartin Habets 
11116e173d3bSMartin Habets 	efx->membase_phys = pci_resource_start(efx->pci_dev, bar);
11126e173d3bSMartin Habets 	if (!efx->membase_phys) {
11136e173d3bSMartin Habets 		netif_err(efx, probe, efx->net_dev,
11146e173d3bSMartin Habets 			  "ERROR: No BAR%d mapping from the BIOS. "
11156e173d3bSMartin Habets 			  "Try pci=realloc on the kernel command line\n", bar);
11166e173d3bSMartin Habets 		rc = -ENODEV;
11176e173d3bSMartin Habets 		goto fail3;
11186e173d3bSMartin Habets 	}
11196e173d3bSMartin Habets 
11206e173d3bSMartin Habets 	rc = pci_request_region(pci_dev, bar, "sfc");
11216e173d3bSMartin Habets 	if (rc) {
11226e173d3bSMartin Habets 		netif_err(efx, probe, efx->net_dev,
11236e173d3bSMartin Habets 			  "request for memory BAR[%d] failed\n", bar);
11246e173d3bSMartin Habets 		rc = -EIO;
11256e173d3bSMartin Habets 		goto fail3;
11266e173d3bSMartin Habets 	}
11276e173d3bSMartin Habets 	efx->mem_bar = bar;
11286e173d3bSMartin Habets 	efx->membase = ioremap(efx->membase_phys, mem_map_size);
11296e173d3bSMartin Habets 	if (!efx->membase) {
11306e173d3bSMartin Habets 		netif_err(efx, probe, efx->net_dev,
11316e173d3bSMartin Habets 			  "could not map memory BAR[%d] at %llx+%x\n", bar,
11326e173d3bSMartin Habets 			  (unsigned long long)efx->membase_phys, mem_map_size);
11336e173d3bSMartin Habets 		rc = -ENOMEM;
11346e173d3bSMartin Habets 		goto fail4;
11356e173d3bSMartin Habets 	}
11366e173d3bSMartin Habets 	netif_dbg(efx, probe, efx->net_dev,
11376e173d3bSMartin Habets 		  "memory BAR[%d] at %llx+%x (virtual %p)\n", bar,
11386e173d3bSMartin Habets 		  (unsigned long long)efx->membase_phys, mem_map_size,
11396e173d3bSMartin Habets 		  efx->membase);
11406e173d3bSMartin Habets 
11416e173d3bSMartin Habets 	return 0;
11426e173d3bSMartin Habets 
11436e173d3bSMartin Habets fail4:
11446e173d3bSMartin Habets 	pci_release_region(efx->pci_dev, bar);
11456e173d3bSMartin Habets fail3:
11466e173d3bSMartin Habets 	efx->membase_phys = 0;
11476e173d3bSMartin Habets fail2:
11486e173d3bSMartin Habets 	pci_disable_device(efx->pci_dev);
11496e173d3bSMartin Habets fail1:
11506e173d3bSMartin Habets 	return rc;
11516e173d3bSMartin Habets }
11526e173d3bSMartin Habets 
efx_siena_fini_io(struct efx_nic * efx)115371ad88f6SMartin Habets void efx_siena_fini_io(struct efx_nic *efx)
11546e173d3bSMartin Habets {
11556e173d3bSMartin Habets 	netif_dbg(efx, drv, efx->net_dev, "shutting down I/O\n");
11566e173d3bSMartin Habets 
11576e173d3bSMartin Habets 	if (efx->membase) {
11586e173d3bSMartin Habets 		iounmap(efx->membase);
11596e173d3bSMartin Habets 		efx->membase = NULL;
11606e173d3bSMartin Habets 	}
11616e173d3bSMartin Habets 
11626e173d3bSMartin Habets 	if (efx->membase_phys) {
11636e173d3bSMartin Habets 		pci_release_region(efx->pci_dev, efx->mem_bar);
11646e173d3bSMartin Habets 		efx->membase_phys = 0;
11656e173d3bSMartin Habets 		efx->mem_bar = UINT_MAX;
11666e173d3bSMartin Habets 	}
11676e173d3bSMartin Habets 
11686e173d3bSMartin Habets 	/* Don't disable bus-mastering if VFs are assigned */
11696e173d3bSMartin Habets 	if (!pci_vfs_assigned(efx->pci_dev))
11706e173d3bSMartin Habets 		pci_disable_device(efx->pci_dev);
11716e173d3bSMartin Habets }
11726e173d3bSMartin Habets 
117358b6b3d5SMartin Habets #ifdef CONFIG_SFC_SIENA_MCDI_LOGGING
mcdi_logging_show(struct device * dev,struct device_attribute * attr,char * buf)11746e173d3bSMartin Habets static ssize_t mcdi_logging_show(struct device *dev,
11756e173d3bSMartin Habets 				 struct device_attribute *attr,
11766e173d3bSMartin Habets 				 char *buf)
11776e173d3bSMartin Habets {
11786e173d3bSMartin Habets 	struct efx_nic *efx = dev_get_drvdata(dev);
11796e173d3bSMartin Habets 	struct efx_mcdi_iface *mcdi = efx_mcdi(efx);
11806e173d3bSMartin Habets 
1181*1ab586f5Sye xingchen 	return sysfs_emit(buf, "%d\n", mcdi->logging_enabled);
11826e173d3bSMartin Habets }
11836e173d3bSMartin Habets 
mcdi_logging_store(struct device * dev,struct device_attribute * attr,const char * buf,size_t count)11846e173d3bSMartin Habets static ssize_t mcdi_logging_store(struct device *dev,
11856e173d3bSMartin Habets 				  struct device_attribute *attr,
11866e173d3bSMartin Habets 				  const char *buf, size_t count)
11876e173d3bSMartin Habets {
11886e173d3bSMartin Habets 	struct efx_nic *efx = dev_get_drvdata(dev);
11896e173d3bSMartin Habets 	struct efx_mcdi_iface *mcdi = efx_mcdi(efx);
11906e173d3bSMartin Habets 	bool enable = count > 0 && *buf != '0';
11916e173d3bSMartin Habets 
11926e173d3bSMartin Habets 	mcdi->logging_enabled = enable;
11936e173d3bSMartin Habets 	return count;
11946e173d3bSMartin Habets }
11956e173d3bSMartin Habets 
11966e173d3bSMartin Habets static DEVICE_ATTR_RW(mcdi_logging);
11976e173d3bSMartin Habets 
efx_siena_init_mcdi_logging(struct efx_nic * efx)119871ad88f6SMartin Habets void efx_siena_init_mcdi_logging(struct efx_nic *efx)
11996e173d3bSMartin Habets {
12006e173d3bSMartin Habets 	int rc = device_create_file(&efx->pci_dev->dev, &dev_attr_mcdi_logging);
12016e173d3bSMartin Habets 
12026e173d3bSMartin Habets 	if (rc) {
12036e173d3bSMartin Habets 		netif_warn(efx, drv, efx->net_dev,
12046e173d3bSMartin Habets 			   "failed to init net dev attributes\n");
12056e173d3bSMartin Habets 	}
12066e173d3bSMartin Habets }
12076e173d3bSMartin Habets 
efx_siena_fini_mcdi_logging(struct efx_nic * efx)120871ad88f6SMartin Habets void efx_siena_fini_mcdi_logging(struct efx_nic *efx)
12096e173d3bSMartin Habets {
12106e173d3bSMartin Habets 	device_remove_file(&efx->pci_dev->dev, &dev_attr_mcdi_logging);
12116e173d3bSMartin Habets }
12126e173d3bSMartin Habets #endif
12136e173d3bSMartin Habets 
12146e173d3bSMartin Habets /* A PCI error affecting this device was detected.
12156e173d3bSMartin Habets  * At this point MMIO and DMA may be disabled.
12166e173d3bSMartin Habets  * Stop the software path and request a slot reset.
12176e173d3bSMartin Habets  */
efx_io_error_detected(struct pci_dev * pdev,pci_channel_state_t state)12186e173d3bSMartin Habets static pci_ers_result_t efx_io_error_detected(struct pci_dev *pdev,
12196e173d3bSMartin Habets 					      pci_channel_state_t state)
12206e173d3bSMartin Habets {
12216e173d3bSMartin Habets 	pci_ers_result_t status = PCI_ERS_RESULT_RECOVERED;
12226e173d3bSMartin Habets 	struct efx_nic *efx = pci_get_drvdata(pdev);
12236e173d3bSMartin Habets 
12246e173d3bSMartin Habets 	if (state == pci_channel_io_perm_failure)
12256e173d3bSMartin Habets 		return PCI_ERS_RESULT_DISCONNECT;
12266e173d3bSMartin Habets 
12276e173d3bSMartin Habets 	rtnl_lock();
12286e173d3bSMartin Habets 
12296e173d3bSMartin Habets 	if (efx->state != STATE_DISABLED) {
12306e173d3bSMartin Habets 		efx->state = STATE_RECOVERY;
12316e173d3bSMartin Habets 		efx->reset_pending = 0;
12326e173d3bSMartin Habets 
12336e173d3bSMartin Habets 		efx_device_detach_sync(efx);
12346e173d3bSMartin Habets 
123571ad88f6SMartin Habets 		efx_siena_stop_all(efx);
123671ad88f6SMartin Habets 		efx_siena_disable_interrupts(efx);
12376e173d3bSMartin Habets 
12386e173d3bSMartin Habets 		status = PCI_ERS_RESULT_NEED_RESET;
12396e173d3bSMartin Habets 	} else {
12406e173d3bSMartin Habets 		/* If the interface is disabled we don't want to do anything
12416e173d3bSMartin Habets 		 * with it.
12426e173d3bSMartin Habets 		 */
12436e173d3bSMartin Habets 		status = PCI_ERS_RESULT_RECOVERED;
12446e173d3bSMartin Habets 	}
12456e173d3bSMartin Habets 
12466e173d3bSMartin Habets 	rtnl_unlock();
12476e173d3bSMartin Habets 
12486e173d3bSMartin Habets 	pci_disable_device(pdev);
12496e173d3bSMartin Habets 
12506e173d3bSMartin Habets 	return status;
12516e173d3bSMartin Habets }
12526e173d3bSMartin Habets 
12536e173d3bSMartin Habets /* Fake a successful reset, which will be performed later in efx_io_resume. */
efx_io_slot_reset(struct pci_dev * pdev)12546e173d3bSMartin Habets static pci_ers_result_t efx_io_slot_reset(struct pci_dev *pdev)
12556e173d3bSMartin Habets {
12566e173d3bSMartin Habets 	struct efx_nic *efx = pci_get_drvdata(pdev);
12576e173d3bSMartin Habets 	pci_ers_result_t status = PCI_ERS_RESULT_RECOVERED;
12586e173d3bSMartin Habets 
12596e173d3bSMartin Habets 	if (pci_enable_device(pdev)) {
12606e173d3bSMartin Habets 		netif_err(efx, hw, efx->net_dev,
12616e173d3bSMartin Habets 			  "Cannot re-enable PCI device after reset.\n");
12626e173d3bSMartin Habets 		status =  PCI_ERS_RESULT_DISCONNECT;
12636e173d3bSMartin Habets 	}
12646e173d3bSMartin Habets 
12656e173d3bSMartin Habets 	return status;
12666e173d3bSMartin Habets }
12676e173d3bSMartin Habets 
12686e173d3bSMartin Habets /* Perform the actual reset and resume I/O operations. */
efx_io_resume(struct pci_dev * pdev)12696e173d3bSMartin Habets static void efx_io_resume(struct pci_dev *pdev)
12706e173d3bSMartin Habets {
12716e173d3bSMartin Habets 	struct efx_nic *efx = pci_get_drvdata(pdev);
12726e173d3bSMartin Habets 	int rc;
12736e173d3bSMartin Habets 
12746e173d3bSMartin Habets 	rtnl_lock();
12756e173d3bSMartin Habets 
12766e173d3bSMartin Habets 	if (efx->state == STATE_DISABLED)
12776e173d3bSMartin Habets 		goto out;
12786e173d3bSMartin Habets 
127971ad88f6SMartin Habets 	rc = efx_siena_reset(efx, RESET_TYPE_ALL);
12806e173d3bSMartin Habets 	if (rc) {
12816e173d3bSMartin Habets 		netif_err(efx, hw, efx->net_dev,
128271ad88f6SMartin Habets 			  "efx_siena_reset failed after PCI error (%d)\n", rc);
12836e173d3bSMartin Habets 	} else {
12846e173d3bSMartin Habets 		efx->state = STATE_READY;
12856e173d3bSMartin Habets 		netif_dbg(efx, hw, efx->net_dev,
12866e173d3bSMartin Habets 			  "Done resetting and resuming IO after PCI error.\n");
12876e173d3bSMartin Habets 	}
12886e173d3bSMartin Habets 
12896e173d3bSMartin Habets out:
12906e173d3bSMartin Habets 	rtnl_unlock();
12916e173d3bSMartin Habets }
12926e173d3bSMartin Habets 
12936e173d3bSMartin Habets /* For simplicity and reliability, we always require a slot reset and try to
12946e173d3bSMartin Habets  * reset the hardware when a pci error affecting the device is detected.
12956e173d3bSMartin Habets  * We leave both the link_reset and mmio_enabled callback unimplemented:
12966e173d3bSMartin Habets  * with our request for slot reset the mmio_enabled callback will never be
12976e173d3bSMartin Habets  * called, and the link_reset callback is not used by AER or EEH mechanisms.
12986e173d3bSMartin Habets  */
129971ad88f6SMartin Habets const struct pci_error_handlers efx_siena_err_handlers = {
13006e173d3bSMartin Habets 	.error_detected = efx_io_error_detected,
13016e173d3bSMartin Habets 	.slot_reset	= efx_io_slot_reset,
13026e173d3bSMartin Habets 	.resume		= efx_io_resume,
13036e173d3bSMartin Habets };
13046e173d3bSMartin Habets 
13056e173d3bSMartin Habets /* Determine whether the NIC will be able to handle TX offloads for a given
13066e173d3bSMartin Habets  * encapsulated packet.
13076e173d3bSMartin Habets  */
efx_can_encap_offloads(struct efx_nic * efx,struct sk_buff * skb)13086e173d3bSMartin Habets static bool efx_can_encap_offloads(struct efx_nic *efx, struct sk_buff *skb)
13096e173d3bSMartin Habets {
13106e173d3bSMartin Habets 	struct gre_base_hdr *greh;
13116e173d3bSMartin Habets 	__be16 dst_port;
13126e173d3bSMartin Habets 	u8 ipproto;
13136e173d3bSMartin Habets 
13146e173d3bSMartin Habets 	/* Does the NIC support encap offloads?
13156e173d3bSMartin Habets 	 * If not, we should never get here, because we shouldn't have
13166e173d3bSMartin Habets 	 * advertised encap offload feature flags in the first place.
13176e173d3bSMartin Habets 	 */
13186e173d3bSMartin Habets 	if (WARN_ON_ONCE(!efx->type->udp_tnl_has_port))
13196e173d3bSMartin Habets 		return false;
13206e173d3bSMartin Habets 
13216e173d3bSMartin Habets 	/* Determine encapsulation protocol in use */
13226e173d3bSMartin Habets 	switch (skb->protocol) {
13236e173d3bSMartin Habets 	case htons(ETH_P_IP):
13246e173d3bSMartin Habets 		ipproto = ip_hdr(skb)->protocol;
13256e173d3bSMartin Habets 		break;
13266e173d3bSMartin Habets 	case htons(ETH_P_IPV6):
13276e173d3bSMartin Habets 		/* If there are extension headers, this will cause us to
13286e173d3bSMartin Habets 		 * think we can't offload something that we maybe could have.
13296e173d3bSMartin Habets 		 */
13306e173d3bSMartin Habets 		ipproto = ipv6_hdr(skb)->nexthdr;
13316e173d3bSMartin Habets 		break;
13326e173d3bSMartin Habets 	default:
13336e173d3bSMartin Habets 		/* Not IP, so can't offload it */
13346e173d3bSMartin Habets 		return false;
13356e173d3bSMartin Habets 	}
13366e173d3bSMartin Habets 	switch (ipproto) {
13376e173d3bSMartin Habets 	case IPPROTO_GRE:
13386e173d3bSMartin Habets 		/* We support NVGRE but not IP over GRE or random gretaps.
13396e173d3bSMartin Habets 		 * Specifically, the NIC will accept GRE as encapsulated if
13406e173d3bSMartin Habets 		 * the inner protocol is Ethernet, but only handle it
13416e173d3bSMartin Habets 		 * correctly if the GRE header is 8 bytes long.  Moreover,
13426e173d3bSMartin Habets 		 * it will not update the Checksum or Sequence Number fields
13436e173d3bSMartin Habets 		 * if they are present.  (The Routing Present flag,
13446e173d3bSMartin Habets 		 * GRE_ROUTING, cannot be set else the header would be more
13456e173d3bSMartin Habets 		 * than 8 bytes long; so we don't have to worry about it.)
13466e173d3bSMartin Habets 		 */
13476e173d3bSMartin Habets 		if (skb->inner_protocol_type != ENCAP_TYPE_ETHER)
13486e173d3bSMartin Habets 			return false;
13496e173d3bSMartin Habets 		if (ntohs(skb->inner_protocol) != ETH_P_TEB)
13506e173d3bSMartin Habets 			return false;
13516e173d3bSMartin Habets 		if (skb_inner_mac_header(skb) - skb_transport_header(skb) != 8)
13526e173d3bSMartin Habets 			return false;
13536e173d3bSMartin Habets 		greh = (struct gre_base_hdr *)skb_transport_header(skb);
13546e173d3bSMartin Habets 		return !(greh->flags & (GRE_CSUM | GRE_SEQ));
13556e173d3bSMartin Habets 	case IPPROTO_UDP:
13566e173d3bSMartin Habets 		/* If the port is registered for a UDP tunnel, we assume the
13576e173d3bSMartin Habets 		 * packet is for that tunnel, and the NIC will handle it as
13586e173d3bSMartin Habets 		 * such.  If not, the NIC won't know what to do with it.
13596e173d3bSMartin Habets 		 */
13606e173d3bSMartin Habets 		dst_port = udp_hdr(skb)->dest;
13616e173d3bSMartin Habets 		return efx->type->udp_tnl_has_port(efx, dst_port);
13626e173d3bSMartin Habets 	default:
13636e173d3bSMartin Habets 		return false;
13646e173d3bSMartin Habets 	}
13656e173d3bSMartin Habets }
13666e173d3bSMartin Habets 
efx_siena_features_check(struct sk_buff * skb,struct net_device * dev,netdev_features_t features)136771ad88f6SMartin Habets netdev_features_t efx_siena_features_check(struct sk_buff *skb,
136871ad88f6SMartin Habets 					   struct net_device *dev,
13696e173d3bSMartin Habets 					   netdev_features_t features)
13706e173d3bSMartin Habets {
13716e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(dev);
13726e173d3bSMartin Habets 
13736e173d3bSMartin Habets 	if (skb->encapsulation) {
13746e173d3bSMartin Habets 		if (features & NETIF_F_GSO_MASK)
13756e173d3bSMartin Habets 			/* Hardware can only do TSO with at most 208 bytes
13766e173d3bSMartin Habets 			 * of headers.
13776e173d3bSMartin Habets 			 */
13786e173d3bSMartin Habets 			if (skb_inner_transport_offset(skb) >
13796e173d3bSMartin Habets 			    EFX_TSO2_MAX_HDRLEN)
13806e173d3bSMartin Habets 				features &= ~(NETIF_F_GSO_MASK);
13816e173d3bSMartin Habets 		if (features & (NETIF_F_GSO_MASK | NETIF_F_CSUM_MASK))
13826e173d3bSMartin Habets 			if (!efx_can_encap_offloads(efx, skb))
13836e173d3bSMartin Habets 				features &= ~(NETIF_F_GSO_MASK |
13846e173d3bSMartin Habets 					      NETIF_F_CSUM_MASK);
13856e173d3bSMartin Habets 	}
13866e173d3bSMartin Habets 	return features;
13876e173d3bSMartin Habets }
13886e173d3bSMartin Habets 
efx_siena_get_phys_port_id(struct net_device * net_dev,struct netdev_phys_item_id * ppid)138971ad88f6SMartin Habets int efx_siena_get_phys_port_id(struct net_device *net_dev,
13906e173d3bSMartin Habets 			       struct netdev_phys_item_id *ppid)
13916e173d3bSMartin Habets {
13926e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
13936e173d3bSMartin Habets 
13946e173d3bSMartin Habets 	if (efx->type->get_phys_port_id)
13956e173d3bSMartin Habets 		return efx->type->get_phys_port_id(efx, ppid);
13966e173d3bSMartin Habets 	else
13976e173d3bSMartin Habets 		return -EOPNOTSUPP;
13986e173d3bSMartin Habets }
13996e173d3bSMartin Habets 
efx_siena_get_phys_port_name(struct net_device * net_dev,char * name,size_t len)140071ad88f6SMartin Habets int efx_siena_get_phys_port_name(struct net_device *net_dev,
140171ad88f6SMartin Habets 				 char *name, size_t len)
14026e173d3bSMartin Habets {
14036e173d3bSMartin Habets 	struct efx_nic *efx = netdev_priv(net_dev);
14046e173d3bSMartin Habets 
14056e173d3bSMartin Habets 	if (snprintf(name, len, "p%u", efx->port_num) >= len)
14066e173d3bSMartin Habets 		return -EINVAL;
14076e173d3bSMartin Habets 	return 0;
14086e173d3bSMartin Habets }
1409