diff options
Diffstat (limited to 'drivers/net/sfc')
-rw-r--r-- | drivers/net/sfc/efx.c | 26 | ||||
-rw-r--r-- | drivers/net/sfc/ethtool.c | 106 | ||||
-rw-r--r-- | drivers/net/sfc/falcon.c | 4 | ||||
-rw-r--r-- | drivers/net/sfc/falcon_xmac.c | 2 | ||||
-rw-r--r-- | drivers/net/sfc/mac.h | 4 | ||||
-rw-r--r-- | drivers/net/sfc/mcdi_mac.c | 2 | ||||
-rw-r--r-- | drivers/net/sfc/mcdi_phy.c | 2 | ||||
-rw-r--r-- | drivers/net/sfc/net_driver.h | 8 | ||||
-rw-r--r-- | drivers/net/sfc/nic.c | 6 | ||||
-rw-r--r-- | drivers/net/sfc/nic.h | 6 | ||||
-rw-r--r-- | drivers/net/sfc/phy.h | 8 | ||||
-rw-r--r-- | drivers/net/sfc/qt202x_phy.c | 2 | ||||
-rw-r--r-- | drivers/net/sfc/rx.c | 3 | ||||
-rw-r--r-- | drivers/net/sfc/siena.c | 2 | ||||
-rw-r--r-- | drivers/net/sfc/tenxpress.c | 2 | ||||
-rw-r--r-- | drivers/net/sfc/txc43128_phy.c | 2 |
16 files changed, 64 insertions, 121 deletions
diff --git a/drivers/net/sfc/efx.c b/drivers/net/sfc/efx.c index a3c2aab53de8..38a55e9e89e4 100644 --- a/drivers/net/sfc/efx.c +++ b/drivers/net/sfc/efx.c @@ -1876,6 +1876,17 @@ static void efx_set_multicast_list(struct net_device *net_dev) /* Otherwise efx_start_port() will do this */ } +static int efx_set_features(struct net_device *net_dev, u32 data) +{ + struct efx_nic *efx = netdev_priv(net_dev); + + /* If disabling RX n-tuple filtering, clear existing filters */ + if (net_dev->features & ~data & NETIF_F_NTUPLE) + efx_filter_clear_rx(efx, EFX_FILTER_PRI_MANUAL); + + return 0; +} + static const struct net_device_ops efx_netdev_ops = { .ndo_open = efx_net_open, .ndo_stop = efx_net_stop, @@ -1887,6 +1898,7 @@ static const struct net_device_ops efx_netdev_ops = { .ndo_change_mtu = efx_change_mtu, .ndo_set_mac_address = efx_set_mac_address, .ndo_set_multicast_list = efx_set_multicast_list, + .ndo_set_features = efx_set_features, #ifdef CONFIG_NET_POLL_CONTROLLER .ndo_poll_controller = efx_netpoll, #endif @@ -2235,7 +2247,7 @@ static bool efx_port_dummy_op_poll(struct efx_nic *efx) return false; } -static struct efx_phy_operations efx_dummy_phy_operations = { +static const struct efx_phy_operations efx_dummy_phy_operations = { .init = efx_port_dummy_op_int, .reconfigure = efx_port_dummy_op_int, .poll = efx_port_dummy_op_poll, @@ -2251,7 +2263,7 @@ static struct efx_phy_operations efx_dummy_phy_operations = { /* This zeroes out and then fills in the invariants in a struct * efx_nic (including all sub-structures). */ -static int efx_init_struct(struct efx_nic *efx, struct efx_nic_type *type, +static int efx_init_struct(struct efx_nic *efx, const struct efx_nic_type *type, struct pci_dev *pci_dev, struct net_device *net_dev) { int i; @@ -2271,7 +2283,6 @@ static int efx_init_struct(struct efx_nic *efx, struct efx_nic_type *type, strlcpy(efx->name, pci_name(pci_dev), sizeof(efx->name)); efx->net_dev = net_dev; - efx->rx_checksum_enabled = true; spin_lock_init(&efx->stats_lock); mutex_init(&efx->mac_lock); efx->mac_op = type->default_mac_ops; @@ -2442,7 +2453,7 @@ static int efx_pci_probe_main(struct efx_nic *efx) static int __devinit efx_pci_probe(struct pci_dev *pci_dev, const struct pci_device_id *entry) { - struct efx_nic_type *type = (struct efx_nic_type *) entry->driver_data; + const struct efx_nic_type *type = (const struct efx_nic_type *) entry->driver_data; struct net_device *net_dev; struct efx_nic *efx; int i, rc; @@ -2454,12 +2465,15 @@ static int __devinit efx_pci_probe(struct pci_dev *pci_dev, return -ENOMEM; net_dev->features |= (type->offload_features | NETIF_F_SG | NETIF_F_HIGHDMA | NETIF_F_TSO | - NETIF_F_GRO); + NETIF_F_RXCSUM); if (type->offload_features & NETIF_F_V6_CSUM) net_dev->features |= NETIF_F_TSO6; /* Mask for features that also apply to VLAN devices */ net_dev->vlan_features |= (NETIF_F_ALL_CSUM | NETIF_F_SG | - NETIF_F_HIGHDMA | NETIF_F_TSO); + NETIF_F_HIGHDMA | NETIF_F_ALL_TSO | + NETIF_F_RXCSUM); + /* All offloads can be toggled */ + net_dev->hw_features = net_dev->features & ~NETIF_F_HIGHDMA; efx = netdev_priv(net_dev); pci_set_drvdata(pci_dev, efx); SET_NETDEV_DEV(net_dev, &pci_dev->dev); diff --git a/drivers/net/sfc/ethtool.c b/drivers/net/sfc/ethtool.c index 807178ef65ad..5d8468fc5804 100644 --- a/drivers/net/sfc/ethtool.c +++ b/drivers/net/sfc/ethtool.c @@ -178,19 +178,27 @@ static struct efx_ethtool_stat efx_ethtool_stats[] = { */ /* Identify device by flashing LEDs */ -static int efx_ethtool_phys_id(struct net_device *net_dev, u32 count) +static int efx_ethtool_phys_id(struct net_device *net_dev, + enum ethtool_phys_id_state state) { struct efx_nic *efx = netdev_priv(net_dev); + enum efx_led_mode mode = EFX_LED_DEFAULT; - do { - efx->type->set_id_led(efx, EFX_LED_ON); - schedule_timeout_interruptible(HZ / 2); - - efx->type->set_id_led(efx, EFX_LED_OFF); - schedule_timeout_interruptible(HZ / 2); - } while (!signal_pending(current) && --count != 0); + switch (state) { + case ETHTOOL_ID_ON: + mode = EFX_LED_ON; + break; + case ETHTOOL_ID_OFF: + mode = EFX_LED_OFF; + break; + case ETHTOOL_ID_INACTIVE: + mode = EFX_LED_DEFAULT; + break; + case ETHTOOL_ID_ACTIVE: + return 1; /* cycle on/off once per second */ + } - efx->type->set_id_led(efx, EFX_LED_DEFAULT); + efx->type->set_id_led(efx, mode); return 0; } @@ -518,72 +526,6 @@ static void efx_ethtool_get_stats(struct net_device *net_dev, } } -static int efx_ethtool_set_tso(struct net_device *net_dev, u32 enable) -{ - struct efx_nic *efx __attribute__ ((unused)) = netdev_priv(net_dev); - u32 features; - - features = NETIF_F_TSO; - if (efx->type->offload_features & NETIF_F_V6_CSUM) - features |= NETIF_F_TSO6; - - if (enable) - net_dev->features |= features; - else - net_dev->features &= ~features; - - return 0; -} - -static int efx_ethtool_set_tx_csum(struct net_device *net_dev, u32 enable) -{ - struct efx_nic *efx = netdev_priv(net_dev); - u32 features = efx->type->offload_features & NETIF_F_ALL_CSUM; - - if (enable) - net_dev->features |= features; - else - net_dev->features &= ~features; - - return 0; -} - -static int efx_ethtool_set_rx_csum(struct net_device *net_dev, u32 enable) -{ - struct efx_nic *efx = netdev_priv(net_dev); - - /* No way to stop the hardware doing the checks; we just - * ignore the result. - */ - efx->rx_checksum_enabled = !!enable; - - return 0; -} - -static u32 efx_ethtool_get_rx_csum(struct net_device *net_dev) -{ - struct efx_nic *efx = netdev_priv(net_dev); - - return efx->rx_checksum_enabled; -} - -static int efx_ethtool_set_flags(struct net_device *net_dev, u32 data) -{ - struct efx_nic *efx = netdev_priv(net_dev); - u32 supported = (efx->type->offload_features & - (ETH_FLAG_RXHASH | ETH_FLAG_NTUPLE)); - int rc; - - rc = ethtool_op_set_flags(net_dev, data, supported); - if (rc) - return rc; - - if (!(data & ETH_FLAG_NTUPLE)) - efx_filter_clear_rx(efx, EFX_FILTER_PRI_MANUAL); - - return 0; -} - static void efx_ethtool_self_test(struct net_device *net_dev, struct ethtool_test *test, u64 *data) { @@ -1070,22 +1012,10 @@ const struct ethtool_ops efx_ethtool_ops = { .set_ringparam = efx_ethtool_set_ringparam, .get_pauseparam = efx_ethtool_get_pauseparam, .set_pauseparam = efx_ethtool_set_pauseparam, - .get_rx_csum = efx_ethtool_get_rx_csum, - .set_rx_csum = efx_ethtool_set_rx_csum, - .get_tx_csum = ethtool_op_get_tx_csum, - /* Need to enable/disable IPv6 too */ - .set_tx_csum = efx_ethtool_set_tx_csum, - .get_sg = ethtool_op_get_sg, - .set_sg = ethtool_op_set_sg, - .get_tso = ethtool_op_get_tso, - /* Need to enable/disable TSO-IPv6 too */ - .set_tso = efx_ethtool_set_tso, - .get_flags = ethtool_op_get_flags, - .set_flags = efx_ethtool_set_flags, .get_sset_count = efx_ethtool_get_sset_count, .self_test = efx_ethtool_self_test, .get_strings = efx_ethtool_get_strings, - .phys_id = efx_ethtool_phys_id, + .set_phys_id = efx_ethtool_phys_id, .get_ethtool_stats = efx_ethtool_get_stats, .get_wol = efx_ethtool_get_wol, .set_wol = efx_ethtool_set_wol, diff --git a/drivers/net/sfc/falcon.c b/drivers/net/sfc/falcon.c index d96b23769bd1..60176e873d62 100644 --- a/drivers/net/sfc/falcon.c +++ b/drivers/net/sfc/falcon.c @@ -1703,7 +1703,7 @@ static int falcon_set_wol(struct efx_nic *efx, u32 type) ************************************************************************** */ -struct efx_nic_type falcon_a1_nic_type = { +const struct efx_nic_type falcon_a1_nic_type = { .probe = falcon_probe_nic, .remove = falcon_remove_nic, .init = falcon_init_nic, @@ -1744,7 +1744,7 @@ struct efx_nic_type falcon_a1_nic_type = { .reset_world_flags = ETH_RESET_IRQ, }; -struct efx_nic_type falcon_b0_nic_type = { +const struct efx_nic_type falcon_b0_nic_type = { .probe = falcon_probe_nic, .remove = falcon_remove_nic, .init = falcon_init_nic, diff --git a/drivers/net/sfc/falcon_xmac.c b/drivers/net/sfc/falcon_xmac.c index 2c9ee5db3bf7..9516452c079c 100644 --- a/drivers/net/sfc/falcon_xmac.c +++ b/drivers/net/sfc/falcon_xmac.c @@ -362,7 +362,7 @@ void falcon_poll_xmac(struct efx_nic *efx) falcon_ack_status_intr(efx); } -struct efx_mac_operations falcon_xmac_operations = { +const struct efx_mac_operations falcon_xmac_operations = { .reconfigure = falcon_reconfigure_xmac, .update_stats = falcon_update_stats_xmac, .check_fault = falcon_xmac_check_fault, diff --git a/drivers/net/sfc/mac.h b/drivers/net/sfc/mac.h index 6886cdf87c12..d6a255d0856b 100644 --- a/drivers/net/sfc/mac.h +++ b/drivers/net/sfc/mac.h @@ -13,8 +13,8 @@ #include "net_driver.h" -extern struct efx_mac_operations falcon_xmac_operations; -extern struct efx_mac_operations efx_mcdi_mac_operations; +extern const struct efx_mac_operations falcon_xmac_operations; +extern const struct efx_mac_operations efx_mcdi_mac_operations; extern int efx_mcdi_mac_stats(struct efx_nic *efx, dma_addr_t dma_addr, u32 dma_len, int enable, int clear); diff --git a/drivers/net/sfc/mcdi_mac.c b/drivers/net/sfc/mcdi_mac.c index 33f7294edb47..50c20777a564 100644 --- a/drivers/net/sfc/mcdi_mac.c +++ b/drivers/net/sfc/mcdi_mac.c @@ -138,7 +138,7 @@ static bool efx_mcdi_mac_check_fault(struct efx_nic *efx) } -struct efx_mac_operations efx_mcdi_mac_operations = { +const struct efx_mac_operations efx_mcdi_mac_operations = { .reconfigure = efx_mcdi_mac_reconfigure, .update_stats = efx_port_dummy_op_void, .check_fault = efx_mcdi_mac_check_fault, diff --git a/drivers/net/sfc/mcdi_phy.c b/drivers/net/sfc/mcdi_phy.c index 7e3c65b0c99f..1fcda2d82399 100644 --- a/drivers/net/sfc/mcdi_phy.c +++ b/drivers/net/sfc/mcdi_phy.c @@ -739,7 +739,7 @@ static const char *efx_mcdi_phy_test_name(struct efx_nic *efx, return NULL; } -struct efx_phy_operations efx_mcdi_phy_ops = { +const struct efx_phy_operations efx_mcdi_phy_ops = { .probe = efx_mcdi_phy_probe, .init = efx_port_dummy_op_int, .reconfigure = efx_mcdi_phy_reconfigure, diff --git a/drivers/net/sfc/net_driver.h b/drivers/net/sfc/net_driver.h index 191a311da2dc..5718260298c4 100644 --- a/drivers/net/sfc/net_driver.h +++ b/drivers/net/sfc/net_driver.h @@ -679,7 +679,6 @@ struct efx_filter_state; * @port_inhibited: If set, the netif_carrier is always off. Hold the mac_lock * @port_initialized: Port initialized? * @net_dev: Operating system network device. Consider holding the rtnl lock - * @rx_checksum_enabled: RX checksumming enabled * @stats_buffer: DMA buffer for statistics * @mac_op: MAC interface * @phy_type: PHY type @@ -769,14 +768,13 @@ struct efx_nic { bool port_initialized; struct net_device *net_dev; - bool rx_checksum_enabled; struct efx_buffer stats_buffer; - struct efx_mac_operations *mac_op; + const struct efx_mac_operations *mac_op; unsigned int phy_type; - struct efx_phy_operations *phy_op; + const struct efx_phy_operations *phy_op; void *phy_data; struct mdio_if_info mdio; unsigned int mdio_bus; @@ -897,7 +895,7 @@ struct efx_nic_type { void (*resume_wol)(struct efx_nic *efx); int (*test_registers)(struct efx_nic *efx); int (*test_nvram)(struct efx_nic *efx); - struct efx_mac_operations *default_mac_ops; + const struct efx_mac_operations *default_mac_ops; int revision; unsigned int mem_map_size; diff --git a/drivers/net/sfc/nic.c b/drivers/net/sfc/nic.c index 10f1cb79c147..5ac9fa2cd3bc 100644 --- a/drivers/net/sfc/nic.c +++ b/drivers/net/sfc/nic.c @@ -852,7 +852,6 @@ efx_handle_rx_event(struct efx_channel *channel, const efx_qword_t *event) unsigned expected_ptr; bool rx_ev_pkt_ok, discard = false, checksummed; struct efx_rx_queue *rx_queue; - struct efx_nic *efx = channel->efx; /* Basic packet information */ rx_ev_byte_cnt = EFX_QWORD_FIELD(*event, FSF_AZ_RX_EV_BYTE_CNT); @@ -875,9 +874,8 @@ efx_handle_rx_event(struct efx_channel *channel, const efx_qword_t *event) * UDP/IP, then we can rely on the hardware checksum. */ checksummed = - likely(efx->rx_checksum_enabled) && - (rx_ev_hdr_type == FSE_CZ_RX_EV_HDR_TYPE_IPV4V6_TCP || - rx_ev_hdr_type == FSE_CZ_RX_EV_HDR_TYPE_IPV4V6_UDP); + rx_ev_hdr_type == FSE_CZ_RX_EV_HDR_TYPE_IPV4V6_TCP || + rx_ev_hdr_type == FSE_CZ_RX_EV_HDR_TYPE_IPV4V6_UDP; } else { efx_handle_rx_not_ok(rx_queue, event, &rx_ev_pkt_ok, &discard); checksummed = false; diff --git a/drivers/net/sfc/nic.h b/drivers/net/sfc/nic.h index a42db6e35be3..7443f99c977f 100644 --- a/drivers/net/sfc/nic.h +++ b/drivers/net/sfc/nic.h @@ -150,9 +150,9 @@ struct siena_nic_data { int wol_filter_id; }; -extern struct efx_nic_type falcon_a1_nic_type; -extern struct efx_nic_type falcon_b0_nic_type; -extern struct efx_nic_type siena_a0_nic_type; +extern const struct efx_nic_type falcon_a1_nic_type; +extern const struct efx_nic_type falcon_b0_nic_type; +extern const struct efx_nic_type siena_a0_nic_type; /************************************************************************** * diff --git a/drivers/net/sfc/phy.h b/drivers/net/sfc/phy.h index b3b79472421e..11d148cd8441 100644 --- a/drivers/net/sfc/phy.h +++ b/drivers/net/sfc/phy.h @@ -13,14 +13,14 @@ /**************************************************************************** * 10Xpress (SFX7101) PHY */ -extern struct efx_phy_operations falcon_sfx7101_phy_ops; +extern const struct efx_phy_operations falcon_sfx7101_phy_ops; extern void tenxpress_set_id_led(struct efx_nic *efx, enum efx_led_mode mode); /**************************************************************************** * AMCC/Quake QT202x PHYs */ -extern struct efx_phy_operations falcon_qt202x_phy_ops; +extern const struct efx_phy_operations falcon_qt202x_phy_ops; /* These PHYs provide various H/W control states for LEDs */ #define QUAKE_LED_LINK_INVAL (0) @@ -39,7 +39,7 @@ extern void falcon_qt202x_set_led(struct efx_nic *p, int led, int state); /**************************************************************************** * Transwitch CX4 retimer */ -extern struct efx_phy_operations falcon_txc_phy_ops; +extern const struct efx_phy_operations falcon_txc_phy_ops; #define TXC_GPIO_DIR_INPUT 0 #define TXC_GPIO_DIR_OUTPUT 1 @@ -50,7 +50,7 @@ extern void falcon_txc_set_gpio_val(struct efx_nic *efx, int pin, int val); /**************************************************************************** * Siena managed PHYs */ -extern struct efx_phy_operations efx_mcdi_phy_ops; +extern const struct efx_phy_operations efx_mcdi_phy_ops; extern int efx_mcdi_mdio_read(struct efx_nic *efx, unsigned int bus, unsigned int prtad, unsigned int devad, diff --git a/drivers/net/sfc/qt202x_phy.c b/drivers/net/sfc/qt202x_phy.c index 55f90924247e..7ad97e397406 100644 --- a/drivers/net/sfc/qt202x_phy.c +++ b/drivers/net/sfc/qt202x_phy.c @@ -449,7 +449,7 @@ static void qt202x_phy_remove(struct efx_nic *efx) efx->phy_data = NULL; } -struct efx_phy_operations falcon_qt202x_phy_ops = { +const struct efx_phy_operations falcon_qt202x_phy_ops = { .probe = qt202x_phy_probe, .init = qt202x_phy_init, .reconfigure = qt202x_phy_reconfigure, diff --git a/drivers/net/sfc/rx.c b/drivers/net/sfc/rx.c index c0fdb59030fb..b7dc891b4461 100644 --- a/drivers/net/sfc/rx.c +++ b/drivers/net/sfc/rx.c @@ -605,6 +605,9 @@ void __efx_rx_packet(struct efx_channel *channel, skb_record_rx_queue(skb, channel->channel); } + if (unlikely(!(efx->net_dev->features & NETIF_F_RXCSUM))) + checksummed = false; + if (likely(checksummed || rx_buf->is_page)) { efx_rx_packet_gro(channel, rx_buf, eh, checksummed); return; diff --git a/drivers/net/sfc/siena.c b/drivers/net/sfc/siena.c index e4dd8986b1fe..ceac1c9907f0 100644 --- a/drivers/net/sfc/siena.c +++ b/drivers/net/sfc/siena.c @@ -581,7 +581,7 @@ static void siena_init_wol(struct efx_nic *efx) ************************************************************************** */ -struct efx_nic_type siena_a0_nic_type = { +const struct efx_nic_type siena_a0_nic_type = { .probe = siena_probe_nic, .remove = siena_remove_nic, .init = siena_init_nic, diff --git a/drivers/net/sfc/tenxpress.c b/drivers/net/sfc/tenxpress.c index efdceb35aaae..204ecdaac9ab 100644 --- a/drivers/net/sfc/tenxpress.c +++ b/drivers/net/sfc/tenxpress.c @@ -478,7 +478,7 @@ static void sfx7101_set_npage_adv(struct efx_nic *efx, u32 advertising) advertising & ADVERTISED_10000baseT_Full); } -struct efx_phy_operations falcon_sfx7101_phy_ops = { +const struct efx_phy_operations falcon_sfx7101_phy_ops = { .probe = tenxpress_phy_probe, .init = tenxpress_phy_init, .reconfigure = tenxpress_phy_reconfigure, diff --git a/drivers/net/sfc/txc43128_phy.c b/drivers/net/sfc/txc43128_phy.c index d9886addcc99..7c21b334a75b 100644 --- a/drivers/net/sfc/txc43128_phy.c +++ b/drivers/net/sfc/txc43128_phy.c @@ -545,7 +545,7 @@ static void txc43128_get_settings(struct efx_nic *efx, struct ethtool_cmd *ecmd) mdio45_ethtool_gset(&efx->mdio, ecmd); } -struct efx_phy_operations falcon_txc_phy_ops = { +const struct efx_phy_operations falcon_txc_phy_ops = { .probe = txc43128_phy_probe, .init = txc43128_phy_init, .reconfigure = txc43128_phy_reconfigure, |