Module Name: src Committed By: martin Date: Mon Jul 22 17:53:35 UTC 2019
Modified Files: src/sys/dev/pci/ixgbe [netbsd-8]: if_sriov.c ix_txrx.c ixgbe.c ixgbe.h ixgbe_82599.c ixgbe_api.c ixgbe_api.h ixgbe_common.c ixgbe_common.h ixgbe_features.h ixgbe_mbx.c ixgbe_mbx.h ixgbe_netbsd.c ixgbe_netbsd.h ixgbe_netmap.c ixgbe_phy.c ixgbe_type.h ixgbe_vf.c ixgbe_x550.c ixgbe_x550.h ixv.c Log Message: Pull up the following revisions (via patch), requested by msaitoh in ticket #1301: sys/dev/pci/ixgbe/if_sriov.c 1.5-1.6 sys/dev/pci/ixgbe/ix_txrx.c 1.53-1.54 sys/dev/pci/ixgbe/ixgbe_x550.h 1.5 sys/dev/pci/ixgbe/ixgbe.c 1.169-1.170,1.176,1.179,1.181,1.185-1.186,1.188-1.192 via patch sys/dev/pci/ixgbe/ixgbe.h 1.53,1.55 sys/dev/pci/ixgbe/ixgbe_82599.c 1.21 sys/dev/pci/ixgbe/ixgbe_api.c 1.22-1.23 sys/dev/pci/ixgbe/ixgbe_api.h 1.14-1.15 sys/dev/pci/ixgbe/ixgbe_x550.c 1.14-1.15 sys/dev/pci/ixgbe/ixgbe_common.c 1.23 sys/dev/pci/ixgbe/ixgbe_common.h 1.14 sys/dev/pci/ixgbe/ixgbe_mbx.c 1.11 sys/dev/pci/ixgbe/ixgbe_mbx.h 1.14 sys/dev/pci/ixgbe/ixgbe_netmap.c 1.2 sys/dev/pci/ixgbe/ixgbe_features.h 1.2 sys/dev/pci/ixgbe/ixgbe_netbsd.c 1.9 sys/dev/pci/ixgbe/ixgbe_netbsd.h 1.9-1.10 sys/dev/pci/ixgbe/ixgbe_phy.c 1.18 sys/dev/pci/ixgbe/ixgbe_type.h 1.37,1.39-1.40 sys/dev/pci/ixgbe/ixgbe_vf.c 1.18 sys/dev/pci/ixgbe/ixv.c 1.112-1.114,1.117,1.119 via patch Sync ixgbe up to 20190717 except ETHERCAP or ixv's VLAN stuff: - Add firmware recovery mode for X550, X550A(Xeon D) and X550EM(C3000). - Remove IXGBE_DEV_ID_82599_LS(0x154f) support again. - On X550EMU, use ixgbe_identify_sfp_module_X550em() instead of ixgbe_identify_module_generic(). ixgbe_identify_sfp_module_X550em() has extra check (e.g. exclude 1G copper). - It's not required to calculate unused queues' statistics. - Remove ETHERCAP_VLAN_HWFILTER's definition. - Match 82598_BX(0x1508), 82599_KR(0x1517), 82599_SFP_EM(0x1507), X550EM_X_XFI(0x15b0), X550EM_A_QSFP(0x15ca) and X550EM_A_QSFP_N(0x15cc) - Add missing XFI support into ixgbe_get_link_capabilities_X550em(). - Other than IXGBE_VF_RESET should wait ACK, so use ixgbevf_write_msg_read_ack() instead of write_posted() in ixgbe_update_mc_addr_list_vf(). - When ixv_check_link() failed in the watchdog function, reset the interface. - Remove RXCSUM register modification in ixv_initialize_receive_units(). It seems it's not required. - Remove some debug printf in ixv_print_debug_info(). - Calculate vector's bit location correctly when the vector >= 31 in ixgbe_allocate_msix(). - Fix hung queue check when the queue number >= 31. - On ENETRESET case, not continue and quit the ifflags_cb() function because if_init() will do the same thing. - Fix bugs in unused code. - Fix typo in comment. - Fix typo in unused code. - Whitespace fixes. KNF. To generate a diff of this commit: cvs rdiff -u -r1.1.4.4 -r1.1.4.5 src/sys/dev/pci/ixgbe/if_sriov.c cvs rdiff -u -r1.24.2.15 -r1.24.2.16 src/sys/dev/pci/ixgbe/ix_txrx.c cvs rdiff -u -r1.88.2.29 -r1.88.2.30 src/sys/dev/pci/ixgbe/ixgbe.c cvs rdiff -u -r1.24.6.16 -r1.24.6.17 src/sys/dev/pci/ixgbe/ixgbe.h cvs rdiff -u -r1.14.8.4 -r1.14.8.5 src/sys/dev/pci/ixgbe/ixgbe_82599.c cvs rdiff -u -r1.15.8.4 -r1.15.8.5 src/sys/dev/pci/ixgbe/ixgbe_api.c cvs rdiff -u -r1.9.8.3 -r1.9.8.4 src/sys/dev/pci/ixgbe/ixgbe_api.h cvs rdiff -u -r1.13.2.4 -r1.13.2.5 src/sys/dev/pci/ixgbe/ixgbe_common.c cvs rdiff -u -r1.7.8.4 -r1.7.8.5 src/sys/dev/pci/ixgbe/ixgbe_common.h cvs rdiff -u -r1.1.4.2 -r1.1.4.3 src/sys/dev/pci/ixgbe/ixgbe_features.h \ src/sys/dev/pci/ixgbe/ixgbe_netmap.c cvs rdiff -u -r1.6.8.2 -r1.6.8.3 src/sys/dev/pci/ixgbe/ixgbe_mbx.c cvs rdiff -u -r1.10.8.2 -r1.10.8.3 src/sys/dev/pci/ixgbe/ixgbe_mbx.h cvs rdiff -u -r1.6.2.2 -r1.6.2.3 src/sys/dev/pci/ixgbe/ixgbe_netbsd.c cvs rdiff -u -r1.7.6.1 -r1.7.6.2 src/sys/dev/pci/ixgbe/ixgbe_netbsd.h cvs rdiff -u -r1.11.6.3 -r1.11.6.4 src/sys/dev/pci/ixgbe/ixgbe_phy.c cvs rdiff -u -r1.22.2.8 -r1.22.2.9 src/sys/dev/pci/ixgbe/ixgbe_type.h cvs rdiff -u -r1.12.8.2 -r1.12.8.3 src/sys/dev/pci/ixgbe/ixgbe_vf.c cvs rdiff -u -r1.5.6.5 -r1.5.6.6 src/sys/dev/pci/ixgbe/ixgbe_x550.c cvs rdiff -u -r1.2.12.2 -r1.2.12.3 src/sys/dev/pci/ixgbe/ixgbe_x550.h cvs rdiff -u -r1.56.2.21 -r1.56.2.22 src/sys/dev/pci/ixgbe/ixv.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/dev/pci/ixgbe/if_sriov.c diff -u src/sys/dev/pci/ixgbe/if_sriov.c:1.1.4.4 src/sys/dev/pci/ixgbe/if_sriov.c:1.1.4.5 --- src/sys/dev/pci/ixgbe/if_sriov.c:1.1.4.4 Sat Apr 14 10:25:11 2018 +++ src/sys/dev/pci/ixgbe/if_sriov.c Mon Jul 22 17:53:35 2019 @@ -250,6 +250,20 @@ ixgbe_vf_set_default_vlan(struct adapter } /* ixgbe_vf_set_default_vlan */ +static void +ixgbe_clear_vfmbmem(struct ixgbe_hw *hw, struct ixgbe_vf *vf) +{ + uint32_t vf_index = IXGBE_VF_INDEX(vf->pool); + uint16_t mbx_size = hw->mbx.size; + uint16_t i; + + IXGBE_CORE_LOCK_ASSERT(adapter); + + for (i = 0; i < mbx_size; ++i) + IXGBE_WRITE_REG_ARRAY(hw, IXGBE_PFMBMEM(vf_index), i, 0x0); +} /* ixgbe_clear_vfmbmem */ + + static boolean_t ixgbe_vf_frame_size_compatible(struct adapter *adapter, struct ixgbe_vf *vf) { @@ -305,6 +319,8 @@ ixgbe_process_vf_reset(struct adapter *a // XXX clear multicast addresses ixgbe_clear_rar(&adapter->hw, vf->rar_index); + ixgbe_clear_vfmbmem(&adapter->hw, vf); + ixgbe_toggle_txdctl(&adapter->hw, IXGBE_VF_INDEX(vf->pool)); vf->api_ver = IXGBE_API_VER_UNKNOWN; } /* ixgbe_process_vf_reset */ Index: src/sys/dev/pci/ixgbe/ix_txrx.c diff -u src/sys/dev/pci/ixgbe/ix_txrx.c:1.24.2.15 src/sys/dev/pci/ixgbe/ix_txrx.c:1.24.2.16 --- src/sys/dev/pci/ixgbe/ix_txrx.c:1.24.2.15 Fri Mar 1 17:33:24 2019 +++ src/sys/dev/pci/ixgbe/ix_txrx.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ix_txrx.c,v 1.24.2.15 2019/03/01 17:33:24 martin Exp $ */ +/* $NetBSD: ix_txrx.c,v 1.24.2.16 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** @@ -233,7 +233,7 @@ ixgbe_mq_start(struct ifnet *ifp, struct i = (cpu_index(curcpu()) % ncpu) % adapter->num_queues; /* Check for a hung queue and pick alternative */ - if (((1 << i) & adapter->active_queues) == 0) + if (((1ULL << i) & adapter->active_queues) == 0) i = ffs64(adapter->active_queues); txr = &adapter->tx_rings[i]; @@ -694,7 +694,7 @@ ixgbe_setup_transmit_ring(struct tx_ring * netmap_idx_n2k() handles wraparounds properly. */ if ((adapter->feat_en & IXGBE_FEATURE_NETMAP) && slot) { - int si = netmap_idx_n2k(&na->tx_rings[txr->me], i); + int si = netmap_idx_n2k(na->tx_rings[txr->me], i); netmap_load_map(na, txr->txtag, txbuf->map, NMB(na, slot + si)); } @@ -1105,7 +1105,7 @@ ixgbe_txeof(struct tx_ring *txr) if ((adapter->feat_en & IXGBE_FEATURE_NETMAP) && (adapter->ifp->if_capenable & IFCAP_NETMAP)) { struct netmap_adapter *na = NA(adapter->ifp); - struct netmap_kring *kring = &na->tx_rings[txr->me]; + struct netmap_kring *kring = na->tx_rings[txr->me]; txd = txr->tx_base; bus_dmamap_sync(txr->txdma.dma_tag, txr->txdma.dma_map, BUS_DMASYNC_POSTREAD); @@ -1123,9 +1123,8 @@ ixgbe_txeof(struct tx_ring *txr) * - the driver ignores tx interrupts unless netmap_mitigate=0 * or the slot has the DD bit set. */ - if (!netmap_mitigate || - (kring->nr_kflags < kring->nkr_num_slots && - txd[kring->nr_kflags].wb.status & IXGBE_TXD_STAT_DD)) { + if (kring->nr_kflags < kring->nkr_num_slots && + txd[kring->nr_kflags].wb.status & IXGBE_TXD_STAT_DD) { netmap_tx_irq(ifp, txr->me); } return false; @@ -1405,7 +1404,7 @@ update: static int ixgbe_allocate_receive_buffers(struct rx_ring *rxr) { - struct adapter *adapter = rxr->adapter; + struct adapter *adapter = rxr->adapter; device_t dev = adapter->dev; struct ixgbe_rx_buf *rxbuf; int bsize, error; @@ -1530,7 +1529,7 @@ ixgbe_setup_receive_ring(struct rx_ring * an mbuf, so end the block with a continue; */ if ((adapter->feat_en & IXGBE_FEATURE_NETMAP) && slot) { - int sj = netmap_idx_n2k(&na->rx_rings[rxr->me], j); + int sj = netmap_idx_n2k(na->rx_rings[rxr->me], j); uint64_t paddr; void *addr; @@ -1827,7 +1826,7 @@ ixgbe_rxeof(struct ix_queue *que) u16 len; u16 vtag = 0; bool eop; - + /* Sync the ring. */ ixgbe_dmamap_sync(rxr->rxdma.dma_tag, rxr->rxdma.dma_map, BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE); @@ -2307,7 +2306,7 @@ ixgbe_allocate_queues(struct adapter *ad /* * Next the RX queues... - */ + */ rsize = roundup2(adapter->num_rx_desc * sizeof(union ixgbe_adv_rx_desc), DBA_ALIGN); for (int i = 0; i < adapter->num_queues; i++, rxconf++) { Index: src/sys/dev/pci/ixgbe/ixgbe.c diff -u src/sys/dev/pci/ixgbe/ixgbe.c:1.88.2.29 src/sys/dev/pci/ixgbe/ixgbe.c:1.88.2.30 --- src/sys/dev/pci/ixgbe/ixgbe.c:1.88.2.29 Mon Apr 1 12:35:38 2019 +++ src/sys/dev/pci/ixgbe/ixgbe.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe.c,v 1.88.2.29 2019/04/01 12:35:38 martin Exp $ */ +/* $NetBSD: ixgbe.c,v 1.88.2.30 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** @@ -81,7 +81,7 @@ * Driver version ************************************************************************/ static const char ixgbe_driver_version[] = "4.0.1-k"; - +/* XXX NetBSD: + 3.3.10 */ /************************************************************************ * PCI Device ID Table @@ -100,14 +100,17 @@ static const ixgbe_vendor_info_t ixgbe_v {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598AT, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598AT2, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598, 0, 0, 0}, + {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598_BX, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598_DA_DUAL_PORT, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598_CX4_DUAL_PORT, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598EB_XF_LR, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598_SR_DUAL_PORT_EM, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82598EB_SFP_LOM, 0, 0, 0}, + {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_KR, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_KX4, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_KX4_MEZZ, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_SFP, 0, 0, 0}, + {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_SFP_EM, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_XAUI_LOM, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_CX4, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_82599_T3_LOM, 0, 0, 0}, @@ -127,8 +130,11 @@ static const ixgbe_vendor_info_t ixgbe_v {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_X_10G_T, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_X_1G_T, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_X_SFP, 0, 0, 0}, + {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_X_XFI, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_A_KR, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_A_KR_L, 0, 0, 0}, + {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_A_QSFP, 0, 0, 0}, + {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_A_QSFP_N, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_A_SFP, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_A_SFP_N, 0, 0, 0}, {IXGBE_INTEL_VENDOR_ID, IXGBE_DEV_ID_X550EM_A_SGMII, 0, 0, 0}, @@ -152,38 +158,39 @@ static const char *ixgbe_strings[] = /************************************************************************ * Function prototypes ************************************************************************/ -static int ixgbe_probe(device_t, cfdata_t, void *); -static void ixgbe_attach(device_t, device_t, void *); -static int ixgbe_detach(device_t, int); +static int ixgbe_probe(device_t, cfdata_t, void *); +static void ixgbe_attach(device_t, device_t, void *); +static int ixgbe_detach(device_t, int); #if 0 -static int ixgbe_shutdown(device_t); +static int ixgbe_shutdown(device_t); #endif static bool ixgbe_suspend(device_t, const pmf_qual_t *); static bool ixgbe_resume(device_t, const pmf_qual_t *); static int ixgbe_ifflags_cb(struct ethercom *); -static int ixgbe_ioctl(struct ifnet *, u_long, void *); +static int ixgbe_ioctl(struct ifnet *, u_long, void *); static void ixgbe_ifstop(struct ifnet *, int); static int ixgbe_init(struct ifnet *); static void ixgbe_init_locked(struct adapter *); -static void ixgbe_stop(void *); -static void ixgbe_init_device_features(struct adapter *); -static void ixgbe_check_fan_failure(struct adapter *, u32, bool); +static void ixgbe_stop(void *); +static void ixgbe_init_device_features(struct adapter *); +static void ixgbe_check_fan_failure(struct adapter *, u32, bool); static void ixgbe_add_media_types(struct adapter *); -static void ixgbe_media_status(struct ifnet *, struct ifmediareq *); -static int ixgbe_media_change(struct ifnet *); -static int ixgbe_allocate_pci_resources(struct adapter *, +static void ixgbe_media_status(struct ifnet *, struct ifmediareq *); +static int ixgbe_media_change(struct ifnet *); +static int ixgbe_allocate_pci_resources(struct adapter *, const struct pci_attach_args *); -static void ixgbe_free_softint(struct adapter *); +static void ixgbe_free_softint(struct adapter *); static void ixgbe_get_slot_info(struct adapter *); -static int ixgbe_allocate_msix(struct adapter *, +static int ixgbe_allocate_msix(struct adapter *, const struct pci_attach_args *); -static int ixgbe_allocate_legacy(struct adapter *, +static int ixgbe_allocate_legacy(struct adapter *, const struct pci_attach_args *); -static int ixgbe_configure_interrupts(struct adapter *); +static int ixgbe_configure_interrupts(struct adapter *); static void ixgbe_free_pciintr_resources(struct adapter *); static void ixgbe_free_pci_resources(struct adapter *); static void ixgbe_local_timer(void *); static void ixgbe_local_timer1(void *); +static void ixgbe_recovery_mode_timer(void *); static int ixgbe_setup_interface(device_t, struct adapter *); static void ixgbe_config_gpie(struct adapter *); static void ixgbe_config_dmac(struct adapter *); @@ -193,18 +200,18 @@ static void ixgbe_check_wol_support(stru static int ixgbe_setup_low_power_mode(struct adapter *); static void ixgbe_rearm_queues(struct adapter *, u64); -static void ixgbe_initialize_transmit_units(struct adapter *); -static void ixgbe_initialize_receive_units(struct adapter *); +static void ixgbe_initialize_transmit_units(struct adapter *); +static void ixgbe_initialize_receive_units(struct adapter *); static void ixgbe_enable_rx_drop(struct adapter *); static void ixgbe_disable_rx_drop(struct adapter *); static void ixgbe_initialize_rss_mapping(struct adapter *); -static void ixgbe_enable_intr(struct adapter *); -static void ixgbe_disable_intr(struct adapter *); -static void ixgbe_update_stats_counters(struct adapter *); -static void ixgbe_set_promisc(struct adapter *); -static void ixgbe_set_multi(struct adapter *); -static void ixgbe_update_link_status(struct adapter *); +static void ixgbe_enable_intr(struct adapter *); +static void ixgbe_disable_intr(struct adapter *); +static void ixgbe_update_stats_counters(struct adapter *); +static void ixgbe_set_promisc(struct adapter *); +static void ixgbe_set_multi(struct adapter *); +static void ixgbe_update_link_status(struct adapter *); static void ixgbe_set_ivar(struct adapter *, u8, u8, s8); static void ixgbe_configure_ivars(struct adapter *); static u8 * ixgbe_mc_array_itr(struct ixgbe_hw *, u8 **, u32 *); @@ -217,18 +224,18 @@ static void ixgbe_unregister_vlan(void * #endif static void ixgbe_add_device_sysctls(struct adapter *); -static void ixgbe_add_hw_stats(struct adapter *); +static void ixgbe_add_hw_stats(struct adapter *); static void ixgbe_clear_evcnt(struct adapter *); static int ixgbe_set_flowcntl(struct adapter *, int); static int ixgbe_set_advertise(struct adapter *, int); -static int ixgbe_get_advertise(struct adapter *); +static int ixgbe_get_advertise(struct adapter *); /* Sysctl handlers */ static void ixgbe_set_sysctl_value(struct adapter *, const char *, const char *, int *, int); static int ixgbe_sysctl_flowcntl(SYSCTLFN_PROTO); static int ixgbe_sysctl_advertise(SYSCTLFN_PROTO); -static int ixgbe_sysctl_interrupt_rate_handler(SYSCTLFN_PROTO); +static int ixgbe_sysctl_interrupt_rate_handler(SYSCTLFN_PROTO); static int ixgbe_sysctl_dmac(SYSCTLFN_PROTO); static int ixgbe_sysctl_phy_temp(SYSCTLFN_PROTO); static int ixgbe_sysctl_phy_overtemp_occurred(SYSCTLFN_PROTO); @@ -236,12 +243,12 @@ static int ixgbe_sysctl_phy_overtemp_occ static int ixgbe_sysctl_power_state(SYSCTLFN_PROTO); static int ixgbe_sysctl_print_rss_config(SYSCTLFN_PROTO); #endif -static int ixgbe_sysctl_next_to_check_handler(SYSCTLFN_PROTO); -static int ixgbe_sysctl_rdh_handler(SYSCTLFN_PROTO); -static int ixgbe_sysctl_rdt_handler(SYSCTLFN_PROTO); -static int ixgbe_sysctl_tdt_handler(SYSCTLFN_PROTO); -static int ixgbe_sysctl_tdh_handler(SYSCTLFN_PROTO); -static int ixgbe_sysctl_eee_state(SYSCTLFN_PROTO); +static int ixgbe_sysctl_next_to_check_handler(SYSCTLFN_PROTO); +static int ixgbe_sysctl_rdh_handler(SYSCTLFN_PROTO); +static int ixgbe_sysctl_rdt_handler(SYSCTLFN_PROTO); +static int ixgbe_sysctl_tdt_handler(SYSCTLFN_PROTO); +static int ixgbe_sysctl_tdh_handler(SYSCTLFN_PROTO); +static int ixgbe_sysctl_eee_state(SYSCTLFN_PROTO); static int ixgbe_sysctl_debug(SYSCTLFN_PROTO); static int ixgbe_sysctl_wol_enable(SYSCTLFN_PROTO); static int ixgbe_sysctl_wufc(SYSCTLFN_PROTO); @@ -321,7 +328,7 @@ static int ixgbe_flow_control = ixgbe_fc SYSCTL_INT(_hw_ix, OID_AUTO, flow_control, CTLFLAG_RDTUN, &ixgbe_flow_control, 0, "Default flow control used for all adapters"); -/* Which pakcet processing uses workqueue or softint */ +/* Which packet processing uses workqueue or softint */ static bool ixgbe_txrx_workqueue = false; /* @@ -416,10 +423,10 @@ static void ixgbe_initialize_rss_mapping(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - u32 reta = 0, mrqc, rss_key[10]; - int queue_id, table_size, index_mult; - int i, j; - u32 rss_hash_config; + u32 reta = 0, mrqc, rss_key[10]; + int queue_id, table_size, index_mult; + int i, j; + u32 rss_hash_config; /* force use default RSS key. */ #ifdef __NetBSD__ @@ -496,11 +503,11 @@ ixgbe_initialize_rss_mapping(struct adap * traffic. */ rss_hash_config = RSS_HASHTYPE_RSS_IPV4 - | RSS_HASHTYPE_RSS_TCP_IPV4 - | RSS_HASHTYPE_RSS_IPV6 - | RSS_HASHTYPE_RSS_TCP_IPV6 - | RSS_HASHTYPE_RSS_IPV6_EX - | RSS_HASHTYPE_RSS_TCP_IPV6_EX; + | RSS_HASHTYPE_RSS_TCP_IPV4 + | RSS_HASHTYPE_RSS_IPV6 + | RSS_HASHTYPE_RSS_TCP_IPV6 + | RSS_HASHTYPE_RSS_IPV6_EX + | RSS_HASHTYPE_RSS_TCP_IPV6_EX; } mrqc = IXGBE_MRQC_RSSEN; @@ -530,14 +537,14 @@ ixgbe_initialize_rss_mapping(struct adap * ixgbe_initialize_receive_units - Setup receive registers and features. ************************************************************************/ #define BSIZEPKT_ROUNDUP ((1<<IXGBE_SRRCTL_BSIZEPKT_SHIFT)-1) - + static void ixgbe_initialize_receive_units(struct adapter *adapter) { struct rx_ring *rxr = adapter->rx_rings; struct ixgbe_hw *hw = &adapter->hw; - struct ifnet *ifp = adapter->ifp; - int i, j; + struct ifnet *ifp = adapter->ifp; + int i, j; u32 bufsz, fctrl, srrctl, rxcsum; u32 hlreg; @@ -630,9 +637,9 @@ ixgbe_initialize_receive_units(struct ad if (adapter->hw.mac.type != ixgbe_mac_82598EB) { u32 psrtype = IXGBE_PSRTYPE_TCPHDR - | IXGBE_PSRTYPE_UDPHDR - | IXGBE_PSRTYPE_IPV4HDR - | IXGBE_PSRTYPE_IPV6HDR; + | IXGBE_PSRTYPE_UDPHDR + | IXGBE_PSRTYPE_IPV4HDR + | IXGBE_PSRTYPE_IPV6HDR; IXGBE_WRITE_REG(hw, IXGBE_PSRTYPE(0), psrtype); } @@ -662,7 +669,7 @@ ixgbe_initialize_receive_units(struct ad static void ixgbe_initialize_transmit_units(struct adapter *adapter) { - struct tx_ring *txr = adapter->tx_rings; + struct tx_ring *txr = adapter->tx_rings; struct ixgbe_hw *hw = &adapter->hw; int i; @@ -760,9 +767,9 @@ ixgbe_initialize_transmit_units(struct a static void ixgbe_attach(device_t parent, device_t dev, void *aux) { - struct adapter *adapter; + struct adapter *adapter; struct ixgbe_hw *hw; - int error = -1; + int error = -1; u32 ctrl_ext; u16 high, low, nvmreg; pcireg_t id, subid; @@ -965,6 +972,7 @@ ixgbe_attach(device_t parent, device_t d aprint_normal("%s:", device_xname(dev)); /* NVM Image Version */ + high = low = 0; switch (hw->mac.type) { case ixgbe_mac_X540: case ixgbe_mac_X550EM_a: @@ -994,6 +1002,8 @@ ixgbe_attach(device_t parent, device_t d default: break; } + hw->eeprom.nvm_image_ver_high = high; + hw->eeprom.nvm_image_ver_low = low; /* PHY firmware revision */ switch (hw->mac.type) { @@ -1066,9 +1076,24 @@ ixgbe_attach(device_t parent, device_t d } } } + /* Recovery mode */ + switch (adapter->hw.mac.type) { + case ixgbe_mac_X550: + case ixgbe_mac_X550EM_x: + case ixgbe_mac_X550EM_a: + /* >= 2.00 */ + if (hw->eeprom.nvm_image_ver_high >= 2) { + adapter->feat_cap |= IXGBE_FEATURE_RECOVERY_MODE; + adapter->feat_en |= IXGBE_FEATURE_RECOVERY_MODE; + } + break; + default: + break; + } + if ((adapter->feat_en & IXGBE_FEATURE_MSIX) == 0) error = ixgbe_allocate_legacy(adapter, pa); - if (error) + if (error) goto err_late; /* Tasklets for Link, SFP, Multispeed Fiber and Flow Director */ @@ -1193,6 +1218,19 @@ ixgbe_attach(device_t parent, device_t d else aprint_error_dev(dev, "couldn't establish power handler\n"); + /* Init recovery mode timer and state variable */ + if (adapter->feat_en & IXGBE_FEATURE_RECOVERY_MODE) { + adapter->recovery_mode = 0; + + /* Set up the timer callout */ + callout_init(&adapter->recovery_mode_timer, + IXGBE_CALLOUT_FLAGS); + + /* Start the task */ + callout_reset(&adapter->recovery_mode_timer, hz, + ixgbe_recovery_mode_timer, adapter); + } + INIT_DEBUGOUT("ixgbe_attach: end"); adapter->osdep.attached = true; @@ -1228,7 +1266,7 @@ static void ixgbe_check_wol_support(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - u16 dev_caps = 0; + u16 dev_caps = 0; /* Find out WoL support for port */ adapter->wol_support = hw->wol_enabled = 0; @@ -1311,15 +1349,15 @@ ixgbe_setup_interface(device_t dev, stru /* Set capability flags */ ifp->if_capabilities |= IFCAP_RXCSUM - | IFCAP_TXCSUM - | IFCAP_TSOv4 - | IFCAP_TSOv6; + | IFCAP_TXCSUM + | IFCAP_TSOv4 + | IFCAP_TSOv6; ifp->if_capenable = 0; ec->ec_capabilities |= ETHERCAP_VLAN_HWTAGGING - | ETHERCAP_VLAN_HWCSUM - | ETHERCAP_JUMBO_MTU - | ETHERCAP_VLAN_MTU; + | ETHERCAP_VLAN_HWCSUM + | ETHERCAP_JUMBO_MTU + | ETHERCAP_VLAN_MTU; /* Enable the above capabilities by default */ ec->ec_capenable = ec->ec_capabilities; @@ -1359,8 +1397,8 @@ static void ixgbe_add_media_types(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - device_t dev = adapter->dev; - u64 layer; + device_t dev = adapter->dev; + u64 layer; layer = adapter->phy_layer; @@ -1440,7 +1478,7 @@ ixgbe_add_media_types(struct adapter *ad if (layer & IXGBE_PHYSICAL_LAYER_1000BASE_BX) device_printf(dev, "Media supported: 1000baseBX\n"); /* XXX no ifmedia_set? */ - + ADD(IFM_AUTO, 0); #undef ADD @@ -1482,12 +1520,12 @@ static void ixgbe_config_link(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - u32 autoneg, err = 0; - bool sfp, negotiate = false; + u32 autoneg, err = 0; + bool sfp, negotiate = false; sfp = ixgbe_is_sfp(hw); - if (sfp) { + if (sfp) { if (hw->phy.multispeed_fiber) { ixgbe_enable_tx_laser(hw); kpreempt_disable(); @@ -1498,7 +1536,7 @@ ixgbe_config_link(struct adapter *adapte softint_schedule(adapter->mod_si); kpreempt_enable(); } else { - struct ifmedia *ifm = &adapter->media; + struct ifmedia *ifm = &adapter->media; if (hw->mac.ops.check_link) err = ixgbe_check_link(hw, &adapter->link_speed, @@ -1513,12 +1551,12 @@ ixgbe_config_link(struct adapter *adapte autoneg = hw->phy.autoneg_advertised; if ((IFM_SUBTYPE(ifm->ifm_cur->ifm_media) != IFM_NONE) && ((!autoneg) && (hw->mac.ops.get_link_capabilities))) - err = hw->mac.ops.get_link_capabilities(hw, &autoneg, + err = hw->mac.ops.get_link_capabilities(hw, &autoneg, &negotiate); if (err) return; if (hw->mac.ops.setup_link) - err = hw->mac.ops.setup_link(hw, autoneg, + err = hw->mac.ops.setup_link(hw, autoneg, adapter->link_up); } @@ -1530,13 +1568,14 @@ ixgbe_config_link(struct adapter *adapte static void ixgbe_update_stats_counters(struct adapter *adapter) { - struct ifnet *ifp = adapter->ifp; - struct ixgbe_hw *hw = &adapter->hw; + struct ifnet *ifp = adapter->ifp; + struct ixgbe_hw *hw = &adapter->hw; struct ixgbe_hw_stats *stats = &adapter->stats.pf; - u32 missed_rx = 0, bprc, lxon, lxoff, total; - u64 total_missed_rx = 0; - uint64_t crcerrs, rlec; - int i, j; + u32 missed_rx = 0, bprc, lxon, lxoff, total; + u64 total_missed_rx = 0; + uint64_t crcerrs, rlec; + unsigned int queue_counters; + int i; crcerrs = IXGBE_READ_REG(hw, IXGBE_CRCERRS); stats->crcerrs.ev_count += crcerrs; @@ -1546,14 +1585,13 @@ ixgbe_update_stats_counters(struct adapt if (hw->mac.type == ixgbe_mac_X550) stats->mbsdc.ev_count += IXGBE_READ_REG(hw, IXGBE_MBSDC); - /* 16 registers */ - for (i = 0; i < __arraycount(stats->qprc); i++) { - j = i % adapter->num_queues; - - stats->qprc[j].ev_count += IXGBE_READ_REG(hw, IXGBE_QPRC(i)); - stats->qptc[j].ev_count += IXGBE_READ_REG(hw, IXGBE_QPTC(i)); + /* 16 registers exist */ + queue_counters = min(__arraycount(stats->qprc), adapter->num_queues); + for (i = 0; i < queue_counters; i++) { + stats->qprc[i].ev_count += IXGBE_READ_REG(hw, IXGBE_QPRC(i)); + stats->qptc[i].ev_count += IXGBE_READ_REG(hw, IXGBE_QPTC(i)); if (hw->mac.type >= ixgbe_mac_82599EB) { - stats->qprdc[j].ev_count + stats->qprdc[i].ev_count += IXGBE_READ_REG(hw, IXGBE_QPRDC(i)); } } @@ -2150,17 +2188,22 @@ ixgbe_clear_evcnt(struct adapter *adapte * * Retrieves the TDH value from the hardware ************************************************************************/ -static int +static int ixgbe_sysctl_tdh_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct tx_ring *txr = (struct tx_ring *)node.sysctl_data; + struct adapter *adapter; uint32_t val; if (!txr) return (0); - val = IXGBE_READ_REG(&txr->adapter->hw, IXGBE_TDH(txr->me)); + adapter = txr->adapter; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + + val = IXGBE_READ_REG(&adapter->hw, IXGBE_TDH(txr->me)); node.sysctl_data = &val; return sysctl_lookup(SYSCTLFN_CALL(&node)); } /* ixgbe_sysctl_tdh_handler */ @@ -2170,17 +2213,22 @@ ixgbe_sysctl_tdh_handler(SYSCTLFN_ARGS) * * Retrieves the TDT value from the hardware ************************************************************************/ -static int +static int ixgbe_sysctl_tdt_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct tx_ring *txr = (struct tx_ring *)node.sysctl_data; + struct adapter *adapter; uint32_t val; if (!txr) return (0); - val = IXGBE_READ_REG(&txr->adapter->hw, IXGBE_TDT(txr->me)); + adapter = txr->adapter; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + + val = IXGBE_READ_REG(&adapter->hw, IXGBE_TDT(txr->me)); node.sysctl_data = &val; return sysctl_lookup(SYSCTLFN_CALL(&node)); } /* ixgbe_sysctl_tdt_handler */ @@ -2191,16 +2239,21 @@ ixgbe_sysctl_tdt_handler(SYSCTLFN_ARGS) * * Retrieves the next_to_check value ************************************************************************/ -static int +static int ixgbe_sysctl_next_to_check_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct rx_ring *rxr = (struct rx_ring *)node.sysctl_data; + struct adapter *adapter; uint32_t val; if (!rxr) return (0); + adapter = rxr->adapter; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + val = rxr->next_to_check; node.sysctl_data = &val; return sysctl_lookup(SYSCTLFN_CALL(&node)); @@ -2211,17 +2264,22 @@ ixgbe_sysctl_next_to_check_handler(SYSCT * * Retrieves the RDH value from the hardware ************************************************************************/ -static int +static int ixgbe_sysctl_rdh_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct rx_ring *rxr = (struct rx_ring *)node.sysctl_data; + struct adapter *adapter; uint32_t val; if (!rxr) return (0); - val = IXGBE_READ_REG(&rxr->adapter->hw, IXGBE_RDH(rxr->me)); + adapter = rxr->adapter; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + + val = IXGBE_READ_REG(&adapter->hw, IXGBE_RDH(rxr->me)); node.sysctl_data = &val; return sysctl_lookup(SYSCTLFN_CALL(&node)); } /* ixgbe_sysctl_rdh_handler */ @@ -2231,17 +2289,22 @@ ixgbe_sysctl_rdh_handler(SYSCTLFN_ARGS) * * Retrieves the RDT value from the hardware ************************************************************************/ -static int +static int ixgbe_sysctl_rdt_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct rx_ring *rxr = (struct rx_ring *)node.sysctl_data; + struct adapter *adapter; uint32_t val; if (!rxr) return (0); - val = IXGBE_READ_REG(&rxr->adapter->hw, IXGBE_RDT(rxr->me)); + adapter = rxr->adapter; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + + val = IXGBE_READ_REG(&adapter->hw, IXGBE_RDT(rxr->me)); node.sysctl_data = &val; return sysctl_lookup(SYSCTLFN_CALL(&node)); } /* ixgbe_sysctl_rdt_handler */ @@ -2308,7 +2371,7 @@ ixgbe_setup_vlan_hw_support(struct adapt struct ethercom *ec = &adapter->osdep.ec; struct ixgbe_hw *hw = &adapter->hw; struct rx_ring *rxr; - int i; + int i; u32 ctrl; bool hwtagging; @@ -2374,9 +2437,9 @@ ixgbe_get_slot_info(struct adapter *adap { device_t dev = adapter->dev; struct ixgbe_hw *hw = &adapter->hw; - u32 offset; + u32 offset; u16 link; - int bus_info_valid = TRUE; + int bus_info_valid = TRUE; /* Some devices are behind an internal bridge */ switch (hw->device_id) { @@ -2437,9 +2500,9 @@ get_parent_info: display: device_printf(dev, "PCI Express Bus: Speed %s Width %s\n", - ((hw->bus.speed == ixgbe_bus_speed_8000) ? "8.0GT/s" : - (hw->bus.speed == ixgbe_bus_speed_5000) ? "5.0GT/s" : - (hw->bus.speed == ixgbe_bus_speed_2500) ? "2.5GT/s" : + ((hw->bus.speed == ixgbe_bus_speed_8000) ? "8.0GT/s" : + (hw->bus.speed == ixgbe_bus_speed_5000) ? "5.0GT/s" : + (hw->bus.speed == ixgbe_bus_speed_2500) ? "2.5GT/s" : "Unknown"), ((hw->bus.width == ixgbe_bus_width_pcie_x8) ? "x8" : (hw->bus.width == ixgbe_bus_width_pcie_x4) ? "x4" : @@ -2479,8 +2542,8 @@ ixgbe_enable_queue(struct adapter *adapt { struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que = &adapter->queues[vector]; - u64 queue = (u64)(1ULL << vector); - u32 mask; + u64 queue = (u64)(1ULL << vector); + u32 mask; mutex_enter(&que->dc_mtx); if (que->disabled_count > 0 && --que->disabled_count > 0) @@ -2509,8 +2572,8 @@ ixgbe_disable_queue_internal(struct adap { struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que = &adapter->queues[vector]; - u64 queue = (u64)(1ULL << vector); - u32 mask; + u64 queue = (u64)(1ULL << vector); + u32 mask; mutex_enter(&que->dc_mtx); @@ -2553,7 +2616,7 @@ static inline void ixgbe_sched_handle_que(struct adapter *adapter, struct ix_queue *que) { - if(que->txrx_use_workqueue) { + if (que->txrx_use_workqueue) { /* * adapter->que_wq is bound to each CPU instead of * each NIC queue to reduce workqueue kthread. As we @@ -2583,8 +2646,8 @@ static int ixgbe_msix_que(void *arg) { struct ix_queue *que = arg; - struct adapter *adapter = que->adapter; - struct ifnet *ifp = adapter->ifp; + struct adapter *adapter = que->adapter; + struct ifnet *ifp = adapter->ifp; struct tx_ring *txr = que->txr; struct rx_ring *rxr = que->rxr; bool more; @@ -2630,9 +2693,9 @@ ixgbe_msix_que(void *arg) que->eitr_setting = 0; /* Idle, do nothing */ - if ((txr->bytes == 0) && (rxr->bytes == 0)) - goto no_calc; - + if ((txr->bytes == 0) && (rxr->bytes == 0)) + goto no_calc; + if ((txr->bytes) && (txr->packets)) newitr = txr->bytes/txr->packets; if ((rxr->bytes) && (rxr->packets)) @@ -2660,8 +2723,8 @@ ixgbe_msix_que(void *arg) newitr = IXGBE_MIN_RSC_EITR_10G1G; } - /* save for next interrupt */ - que->eitr_setting = newitr; + /* save for next interrupt */ + que->eitr_setting = newitr; /* Reset state */ txr->bytes = 0; @@ -2843,9 +2906,9 @@ ixgbe_media_status(struct ifnet *ifp, st static int ixgbe_media_change(struct ifnet *ifp) { - struct adapter *adapter = ifp->if_softc; - struct ifmedia *ifm = &adapter->media; - struct ixgbe_hw *hw = &adapter->hw; + struct adapter *adapter = ifp->if_softc; + struct ifmedia *ifm = &adapter->media; + struct ixgbe_hw *hw = &adapter->hw; ixgbe_link_speed speed = 0; ixgbe_link_speed link_caps = 0; bool negotiate = false; @@ -2881,10 +2944,9 @@ ixgbe_media_change(struct ifnet *ifp) case IFM_10G_LRM: case IFM_10G_LR: case IFM_10G_TWINAX: -#ifndef IFM_ETH_XTYPE - case IFM_10G_SR: /* KR, too */ - case IFM_10G_CX4: /* KX4 */ -#else + case IFM_10G_SR: + case IFM_10G_CX4: +#ifdef IFM_ETH_XTYPE case IFM_10G_KR: case IFM_10G_KX4: #endif @@ -2950,8 +3012,8 @@ static void ixgbe_set_promisc(struct adapter *adapter) { struct ifnet *ifp = adapter->ifp; - int mcnt = 0; - u32 rctl; + int mcnt = 0; + u32 rctl; struct ether_multi *enm; struct ether_multistep step; struct ethercom *ec = &adapter->osdep.ec; @@ -2995,7 +3057,7 @@ ixgbe_msix_link(void *arg) struct adapter *adapter = arg; struct ixgbe_hw *hw = &adapter->hw; u32 eicr, eicr_mask; - s32 retval; + s32 retval; ++adapter->link_irq.ev_count; @@ -3104,7 +3166,7 @@ ixgbe_msix_link(void *arg) (eicr & IXGBE_EICR_GPI_SDP0_X540)) { IXGBE_WRITE_REG(hw, IXGBE_EICR, IXGBE_EICR_GPI_SDP0_X540); softint_schedule(adapter->phy_si); - } + } /* Re-enable other interrupts */ IXGBE_WRITE_REG(hw, IXGBE_EIMS, IXGBE_EIMS_OTHER); @@ -3114,11 +3176,11 @@ ixgbe_msix_link(void *arg) static void ixgbe_eitr_write(struct adapter *adapter, uint32_t index, uint32_t itr) { - - if (adapter->hw.mac.type == ixgbe_mac_82598EB) - itr |= itr << 16; - else - itr |= IXGBE_EITR_CNT_WDIS; + + if (adapter->hw.mac.type == ixgbe_mac_82598EB) + itr |= itr << 16; + else + itr |= IXGBE_EITR_CNT_WDIS; IXGBE_WRITE_REG(&adapter->hw, IXGBE_EITR(index), itr); } @@ -3132,13 +3194,18 @@ ixgbe_sysctl_interrupt_rate_handler(SYSC { struct sysctlnode node = *rnode; struct ix_queue *que = (struct ix_queue *)node.sysctl_data; - struct adapter *adapter = que->adapter; + struct adapter *adapter; uint32_t reg, usec, rate; int error; if (que == NULL) return 0; - reg = IXGBE_READ_REG(&que->adapter->hw, IXGBE_EITR(que->msix)); + + adapter = que->adapter; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + + reg = IXGBE_READ_REG(&adapter->hw, IXGBE_EITR(que->msix)); usec = ((reg & 0x0FF8) >> 3); if (usec > 0) rate = 500000 / usec; @@ -3205,8 +3272,8 @@ err: static void ixgbe_add_device_sysctls(struct adapter *adapter) { - device_t dev = adapter->dev; - struct ixgbe_hw *hw = &adapter->hw; + device_t dev = adapter->dev; + struct ixgbe_hw *hw = &adapter->hw; struct sysctllog **log; const struct sysctlnode *rnode, *cnode; @@ -3374,7 +3441,7 @@ ixgbe_allocate_pci_resources(struct adap case PCI_MAPREG_TYPE_MEM | PCI_MAPREG_MEM_TYPE_64BIT: adapter->osdep.mem_bus_space_tag = pa->pa_memt; if (pci_mapreg_info(pa->pa_pc, pa->pa_tag, PCI_BAR(0), - memtype, &addr, &adapter->osdep.mem_size, &flags) != 0) + memtype, &addr, &adapter->osdep.mem_size, &flags) != 0) goto map_err; if ((flags & BUS_SPACE_MAP_PREFETCHABLE) != 0) { aprint_normal_dev(dev, "clearing prefetchable bit\n"); @@ -3493,8 +3560,8 @@ ixgbe_detach(device_t dev, int flags) #if NVLAN > 0 /* Make sure VLANs are not using driver */ if (!VLAN_ATTACHED(&adapter->osdep.ec)) - ; /* nothing to do: no VLANs */ - else if ((flags & (DETACH_SHUTDOWN|DETACH_FORCE)) != 0) + ; /* nothing to do: no VLANs */ + else if ((flags & (DETACH_SHUTDOWN | DETACH_FORCE)) != 0) vlan_ifdetach(adapter->ifp); else { aprint_error_dev(dev, "VLANs in use, detach first\n"); @@ -3511,13 +3578,15 @@ ixgbe_detach(device_t dev, int flags) IXGBE_CORE_UNLOCK(adapter); ixgbe_free_softint(adapter); - + /* let hardware know driver is unloading */ ctrl_ext = IXGBE_READ_REG(&adapter->hw, IXGBE_CTRL_EXT); ctrl_ext &= ~IXGBE_CTRL_EXT_DRV_LOAD; IXGBE_WRITE_REG(&adapter->hw, IXGBE_CTRL_EXT, ctrl_ext); callout_halt(&adapter->timer, NULL); + if (adapter->feat_en & IXGBE_FEATURE_RECOVERY_MODE) + callout_halt(&adapter->recovery_mode_timer, NULL); if (adapter->feat_en & IXGBE_FEATURE_NETMAP) netmap_detach(adapter->ifp); @@ -3667,8 +3736,8 @@ static int ixgbe_setup_low_power_mode(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - device_t dev = adapter->dev; - s32 error = 0; + device_t dev = adapter->dev; + s32 error = 0; KASSERT(mutex_owned(&adapter->core_mtx)); @@ -3747,7 +3816,7 @@ static bool ixgbe_suspend(device_t dev, const pmf_qual_t *qual) { struct adapter *adapter = device_private(dev); - int error = 0; + int error = 0; INIT_DEBUGOUT("ixgbe_suspend: begin"); @@ -3768,10 +3837,10 @@ ixgbe_suspend(device_t dev, const pmf_qu static bool ixgbe_resume(device_t dev, const pmf_qual_t *qual) { - struct adapter *adapter = device_private(dev); - struct ifnet *ifp = adapter->ifp; + struct adapter *adapter = device_private(dev); + struct ifnet *ifp = adapter->ifp; struct ixgbe_hw *hw = &adapter->hw; - u32 wus; + u32 wus; INIT_DEBUGOUT("ixgbe_resume: begin"); @@ -3825,15 +3894,15 @@ static void ixgbe_init_locked(struct adapter *adapter) { struct ifnet *ifp = adapter->ifp; - device_t dev = adapter->dev; + device_t dev = adapter->dev; struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que; - struct tx_ring *txr; - struct rx_ring *rxr; + struct tx_ring *txr; + struct rx_ring *rxr; u32 txdctl, mhadd; u32 rxdctl, rxctrl; - u32 ctrl_ext; - int i, j, err; + u32 ctrl_ext; + int i, j, err; /* XXX check IFF_UP and IFF_RUNNING, power-saving state! */ @@ -3842,7 +3911,7 @@ ixgbe_init_locked(struct adapter *adapte hw->adapter_stopped = FALSE; ixgbe_stop_adapter(hw); - callout_stop(&adapter->timer); + callout_stop(&adapter->timer); for (i = 0, que = adapter->queues; i < adapter->num_queues; i++, que++) que->disabled_count = 0; @@ -3970,7 +4039,7 @@ ixgbe_init_locked(struct adapter *adapte if ((adapter->feat_en & IXGBE_FEATURE_NETMAP) && (ifp->if_capenable & IFCAP_NETMAP)) { struct netmap_adapter *na = NA(adapter->ifp); - struct netmap_kring *kring = &na->rx_rings[i]; + struct netmap_kring *kring = na->rx_rings[i]; int t = na->num_rx_desc - 1 - nm_kr_rxspace(kring); IXGBE_WRITE_REG(hw, IXGBE_RDT(rxr->me), t); @@ -4014,10 +4083,10 @@ ixgbe_init_locked(struct adapter *adapte if (hw->phy.type == ixgbe_phy_none) { err = hw->phy.ops.identify(hw); if (err == IXGBE_ERR_SFP_NOT_SUPPORTED) { - device_printf(dev, + device_printf(dev, "Unsupported SFP+ module type was detected.\n"); return; - } + } } /* Set moderation on the Link interrupt */ @@ -4035,7 +4104,7 @@ ixgbe_init_locked(struct adapter *adapte ixgbe_config_link(adapter); /* Hardware Packet Buffer & Flow Control setup */ - ixgbe_config_delay_values(adapter); + ixgbe_config_delay_values(adapter); /* Initialize the FC settings */ ixgbe_start_hw(hw); @@ -4140,7 +4209,7 @@ static void ixgbe_configure_ivars(struct adapter *adapter) { struct ix_queue *que = adapter->queues; - u32 newitr; + u32 newitr; if (ixgbe_max_interrupt_rate > 0) newitr = (4000000 / ixgbe_max_interrupt_rate) & 0x0FF8; @@ -4153,11 +4222,11 @@ ixgbe_configure_ivars(struct adapter *ad newitr = 0; } - for (int i = 0; i < adapter->num_queues; i++, que++) { + for (int i = 0; i < adapter->num_queues; i++, que++) { struct rx_ring *rxr = &adapter->rx_rings[i]; struct tx_ring *txr = &adapter->tx_rings[i]; /* First the RX queue entry */ - ixgbe_set_ivar(adapter, rxr->me, que->msix, 0); + ixgbe_set_ivar(adapter, rxr->me, que->msix, 0); /* ... and the TX */ ixgbe_set_ivar(adapter, txr->me, que->msix, 1); /* Set an Initial EITR value */ @@ -4172,7 +4241,7 @@ ixgbe_configure_ivars(struct adapter *ad } /* For the Link interrupt */ - ixgbe_set_ivar(adapter, 1, adapter->vector, -1); + ixgbe_set_ivar(adapter, 1, adapter->vector, -1); } /* ixgbe_configure_ivars */ /************************************************************************ @@ -4182,16 +4251,16 @@ static void ixgbe_config_gpie(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - u32 gpie; + u32 gpie; gpie = IXGBE_READ_REG(hw, IXGBE_GPIE); if (adapter->feat_en & IXGBE_FEATURE_MSIX) { /* Enable Enhanced MSI-X mode */ gpie |= IXGBE_GPIE_MSIX_MODE - | IXGBE_GPIE_EIAME - | IXGBE_GPIE_PBA_SUPPORT - | IXGBE_GPIE_OCD; + | IXGBE_GPIE_EIAME + | IXGBE_GPIE_PBA_SUPPORT + | IXGBE_GPIE_OCD; } /* Fan Failure Interrupt */ @@ -4228,7 +4297,7 @@ static void ixgbe_config_delay_values(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - u32 rxpb, frame, size, tmp; + u32 rxpb, frame, size, tmp; frame = adapter->max_frame_size; @@ -4386,7 +4455,7 @@ ixgbe_local_timer1(void *arg) v0 = v1 = v2 = v3 = v4 = v5 = v6 = v7 = 0; que = adapter->queues; for (i = 0; i < adapter->num_queues; i++, que++) { - struct tx_ring *txr = que->txr; + struct tx_ring *txr = que->txr; v0 += txr->q_efbig_tx_dma_setup; v1 += txr->q_mbuf_defrag_failed; @@ -4408,14 +4477,14 @@ ixgbe_local_timer1(void *arg) /* * Check the TX queues status - * - mark hung queues so we don't schedule on them - * - watchdog only if all queues show hung + * - mark hung queues so we don't schedule on them + * - watchdog only if all queues show hung */ que = adapter->queues; for (i = 0; i < adapter->num_queues; i++, que++) { /* Keep track of queues with work for soft irq */ if (que->txr->busy) - queues |= ((u64)1 << que->me); + queues |= 1ULL << que->me; /* * Each time txeof runs without cleaning, but there * are uncleaned descriptors it increments busy. If @@ -4424,12 +4493,12 @@ ixgbe_local_timer1(void *arg) if (que->busy == IXGBE_QUEUE_HUNG) { ++hung; /* Mark the queue as inactive */ - adapter->active_queues &= ~((u64)1 << que->me); + adapter->active_queues &= ~(1ULL << que->me); continue; } else { /* Check if we've come back from hung */ - if ((adapter->active_queues & ((u64)1 << que->me)) == 0) - adapter->active_queues |= ((u64)1 << que->me); + if ((adapter->active_queues & (1ULL << que->me)) == 0) + adapter->active_queues |= 1ULL << que->me; } if (que->busy >= IXGBE_MAX_TX_BUSY) { device_printf(dev, @@ -4467,6 +4536,32 @@ watchdog: } /* ixgbe_local_timer */ /************************************************************************ + * ixgbe_recovery_mode_timer - Recovery mode timer routine + ************************************************************************/ +static void +ixgbe_recovery_mode_timer(void *arg) +{ + struct adapter *adapter = arg; + struct ixgbe_hw *hw = &adapter->hw; + + IXGBE_CORE_LOCK(adapter); + if (ixgbe_fw_recovery_mode(hw)) { + if (atomic_cas_uint(&adapter->recovery_mode, 0, 1)) { + /* Firmware error detected, entering recovery mode */ + device_printf(adapter->dev, "Firmware recovery mode detected. Limiting functionality. Refer to the Intel(R) Ethernet Adapters and Devices User Guide for details on firmware recovery mode.\n"); + + if (hw->adapter_stopped == FALSE) + ixgbe_stop(adapter); + } + } else + atomic_cas_uint(&adapter->recovery_mode, 1, 0); + + callout_reset(&adapter->recovery_mode_timer, hz, + ixgbe_recovery_mode_timer, adapter); + IXGBE_CORE_UNLOCK(adapter); +} /* ixgbe_recovery_mode_timer */ + +/************************************************************************ * ixgbe_sfp_probe * * Determine if a port had optics inserted. @@ -4489,7 +4584,7 @@ ixgbe_sfp_probe(struct adapter *adapter) device_printf(dev,"Unsupported SFP+ module detected!"); device_printf(dev, "Reload driver with supported module.\n"); - goto out; + goto out; } else device_printf(dev, "SFP+ module detected!\n"); /* We now have supported optics */ @@ -4506,10 +4601,10 @@ out: static void ixgbe_handle_mod(void *context) { - struct adapter *adapter = context; + struct adapter *adapter = context; struct ixgbe_hw *hw = &adapter->hw; device_t dev = adapter->dev; - u32 err, cage_full = 0; + u32 err, cage_full = 0; ++adapter->mod_sicount.ev_count; if (adapter->hw.need_crosstalk_fix) { @@ -4558,11 +4653,12 @@ ixgbe_handle_mod(void *context) static void ixgbe_handle_msf(void *context) { - struct adapter *adapter = context; + struct adapter *adapter = context; struct ixgbe_hw *hw = &adapter->hw; - u32 autoneg; - bool negotiate; + u32 autoneg; + bool negotiate; + IXGBE_CORE_LOCK(adapter); ++adapter->msf_sicount.ev_count; /* get_supported_phy_layer will call hw->phy.ops.identify_sfp() */ adapter->phy_layer = ixgbe_get_supported_physical_layer(hw); @@ -4579,6 +4675,7 @@ ixgbe_handle_msf(void *context) ifmedia_removeall(&adapter->media); ixgbe_add_media_types(adapter); ifmedia_set(&adapter->media, IFM_ETHER | IFM_AUTO); + IXGBE_CORE_UNLOCK(adapter); } /* ixgbe_handle_msf */ /************************************************************************ @@ -4587,7 +4684,7 @@ ixgbe_handle_msf(void *context) static void ixgbe_handle_phy(void *context) { - struct adapter *adapter = context; + struct adapter *adapter = context; struct ixgbe_hw *hw = &adapter->hw; int error; @@ -4621,8 +4718,8 @@ ixgbe_ifstop(struct ifnet *ifp, int disa static void ixgbe_stop(void *arg) { - struct ifnet *ifp; - struct adapter *adapter = arg; + struct ifnet *ifp; + struct adapter *adapter = arg; struct ixgbe_hw *hw = &adapter->hw; ifp = adapter->ifp; @@ -4658,14 +4755,14 @@ ixgbe_stop(void *arg) * ixgbe_update_link_status - Update OS on link state * * Note: Only updates the OS on the cached link state. - * The real check of the hardware only happens with - * a link interrupt. + * The real check of the hardware only happens with + * a link interrupt. ************************************************************************/ static void ixgbe_update_link_status(struct adapter *adapter) { struct ifnet *ifp = adapter->ifp; - device_t dev = adapter->dev; + device_t dev = adapter->dev; struct ixgbe_hw *hw = &adapter->hw; KASSERT(mutex_owned(&adapter->core_mtx)); @@ -4734,7 +4831,7 @@ ixgbe_update_link_status(struct adapter /* * Do it when link active changes to DOWN. i.e. * a) LINK_STATE_UNKNOWN -> LINK_STATE_DOWN - * b) LINK_STATE_UP -> LINK_STATE_DOWN + * b) LINK_STATE_UP -> LINK_STATE_DOWN */ if (adapter->link_active != LINK_STATE_DOWN) { if (bootverbose) @@ -4851,8 +4948,8 @@ ixgbe_enable_intr(struct adapter *adapte * allow for handling the extended (beyond 32) MSI-X * vectors that can be used by 82599 */ - for (int i = 0; i < adapter->num_queues; i++, que++) - ixgbe_enable_queue(adapter, que->msix); + for (int i = 0; i < adapter->num_queues; i++, que++) + ixgbe_enable_queue(adapter, que->msix); IXGBE_WRITE_FLUSH(hw); @@ -4908,10 +5005,10 @@ ixgbe_legacy_irq(void *arg) struct ix_queue *que = arg; struct adapter *adapter = que->adapter; struct ixgbe_hw *hw = &adapter->hw; - struct ifnet *ifp = adapter->ifp; - struct tx_ring *txr = adapter->tx_rings; + struct ifnet *ifp = adapter->ifp; + struct tx_ring *txr = adapter->tx_rings; bool more = false; - u32 eicr, eicr_mask; + u32 eicr, eicr_mask; /* Silicon errata #26 on 82598 */ IXGBE_WRITE_REG(hw, IXGBE_EIMC, IXGBE_IRQ_CLEAR_MASK); @@ -5056,10 +5153,15 @@ static void ixgbe_set_sysctl_value(struct adapter *adapter, const char *name, const char *description, int *limit, int value) { - device_t dev = adapter->dev; + device_t dev = adapter->dev; struct sysctllog **log; const struct sysctlnode *rnode, *cnode; + /* + * It's not required to check recovery mode because this function never + * touches hardware. + */ + log = &adapter->sysctllog; if ((rnode = ixgbe_sysctl_instance(adapter)) == NULL) { aprint_error_dev(dev, "could not create sysctl root\n"); @@ -5085,6 +5187,9 @@ ixgbe_sysctl_flowcntl(SYSCTLFN_ARGS) struct adapter *adapter = (struct adapter *)node.sysctl_data; int error, fc; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + fc = adapter->hw.fc.current_mode; node.sysctl_data = &fc; error = sysctl_lookup(SYSCTLFN_CALL(&node)); @@ -5149,8 +5254,8 @@ static void ixgbe_enable_rx_drop(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - struct rx_ring *rxr; - u32 srrctl; + struct rx_ring *rxr; + u32 srrctl; for (int i = 0; i < adapter->num_queues; i++) { rxr = &adapter->rx_rings[i]; @@ -5174,14 +5279,14 @@ static void ixgbe_disable_rx_drop(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - struct rx_ring *rxr; - u32 srrctl; + struct rx_ring *rxr; + u32 srrctl; for (int i = 0; i < adapter->num_queues; i++) { rxr = &adapter->rx_rings[i]; - srrctl = IXGBE_READ_REG(hw, IXGBE_SRRCTL(rxr->me)); - srrctl &= ~IXGBE_SRRCTL_DROP_EN; - IXGBE_WRITE_REG(hw, IXGBE_SRRCTL(rxr->me), srrctl); + srrctl = IXGBE_READ_REG(hw, IXGBE_SRRCTL(rxr->me)); + srrctl &= ~IXGBE_SRRCTL_DROP_EN; + IXGBE_WRITE_REG(hw, IXGBE_SRRCTL(rxr->me), srrctl); } /* disable drop for each vf */ @@ -5201,7 +5306,10 @@ ixgbe_sysctl_advertise(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct adapter *adapter = (struct adapter *)node.sysctl_data; - int error = 0, advertise; + int error = 0, advertise; + + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); advertise = adapter->advertise; node.sysctl_data = &advertise; @@ -5227,12 +5335,12 @@ ixgbe_sysctl_advertise(SYSCTLFN_ARGS) static int ixgbe_set_advertise(struct adapter *adapter, int advertise) { - device_t dev; - struct ixgbe_hw *hw; + device_t dev; + struct ixgbe_hw *hw; ixgbe_link_speed speed = 0; ixgbe_link_speed link_caps = 0; - s32 err = IXGBE_NOT_IMPLEMENTED; - bool negotiate = FALSE; + s32 err = IXGBE_NOT_IMPLEMENTED; + bool negotiate = FALSE; /* Checks to validate new value */ if (adapter->advertise == advertise) /* no change */ @@ -5336,11 +5444,11 @@ ixgbe_set_advertise(struct adapter *adap static int ixgbe_get_advertise(struct adapter *adapter) { - struct ixgbe_hw *hw = &adapter->hw; - int speed; + struct ixgbe_hw *hw = &adapter->hw; + int speed; ixgbe_link_speed link_caps = 0; - s32 err; - bool negotiate = FALSE; + s32 err; + bool negotiate = FALSE; /* * Advertised speed means nothing unless it's copper or @@ -5382,8 +5490,11 @@ ixgbe_sysctl_dmac(SYSCTLFN_ARGS) struct sysctlnode node = *rnode; struct adapter *adapter = (struct adapter *)node.sysctl_data; struct ifnet *ifp = adapter->ifp; - int error; - int newval; + int error; + int newval; + + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); newval = adapter->dmac; node.sysctl_data = &newval; @@ -5440,7 +5551,10 @@ ixgbe_sysctl_power_state(SYSCTLFN_ARGS) struct sysctlnode node = *rnode; struct adapter *adapter = (struct adapter *)node.sysctl_data; device_t dev = adapter->dev; - int curr_ps, new_ps, error = 0; + int curr_ps, new_ps, error = 0; + + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); curr_ps = new_ps = pci_get_powerstate(dev); @@ -5481,11 +5595,15 @@ static int ixgbe_sysctl_wol_enable(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; - struct adapter *adapter = (struct adapter *)node.sysctl_data; + struct adapter *adapter = (struct adapter *)node.sysctl_data; struct ixgbe_hw *hw = &adapter->hw; - bool new_wol_enabled; - int error = 0; + bool new_wol_enabled; + int error = 0; + /* + * It's not required to check recovery mode because this function never + * touches hardware. + */ new_wol_enabled = hw->wol_enabled; node.sysctl_data = &new_wol_enabled; error = sysctl_lookup(SYSCTLFN_CALL(&node)); @@ -5527,6 +5645,10 @@ ixgbe_sysctl_wufc(SYSCTLFN_ARGS) int error = 0; u32 new_wufc; + /* + * It's not required to check recovery mode because this function never + * touches hardware. + */ new_wufc = adapter->wufc; node.sysctl_data = &new_wufc; error = sysctl_lookup(SYSCTLFN_CALL(&node)); @@ -5554,12 +5676,15 @@ ixgbe_sysctl_print_rss_config(SYSCTLFN_A { #ifdef notyet struct sysctlnode node = *rnode; - struct adapter *adapter = (struct adapter *)node.sysctl_data; + struct adapter *adapter = (struct adapter *)node.sysctl_data; struct ixgbe_hw *hw = &adapter->hw; - device_t dev = adapter->dev; - struct sbuf *buf; - int error = 0, reta_size; - u32 reg; + device_t dev = adapter->dev; + struct sbuf *buf; + int error = 0, reta_size; + u32 reg; + + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); buf = sbuf_new_for_sysctl(NULL, NULL, 128, req); if (!buf) { @@ -5619,6 +5744,9 @@ ixgbe_sysctl_phy_temp(SYSCTLFN_ARGS) u16 reg; int error; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + if (hw->device_id != IXGBE_DEV_ID_X550EM_X_10G_T) { device_printf(adapter->dev, "Device has no supported external thermal sensor.\n"); @@ -5659,6 +5787,9 @@ ixgbe_sysctl_phy_overtemp_occurred(SYSCT int val, error; u16 reg; + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); + if (hw->device_id != IXGBE_DEV_ID_X550EM_X_10G_T) { device_printf(adapter->dev, "Device has no supported external thermal sensor.\n"); @@ -5700,8 +5831,11 @@ ixgbe_sysctl_eee_state(SYSCTLFN_ARGS) struct adapter *adapter = (struct adapter *)node.sysctl_data; struct ifnet *ifp = adapter->ifp; device_t dev = adapter->dev; - int curr_eee, new_eee, error = 0; - s32 retval; + int curr_eee, new_eee, error = 0; + s32 retval; + + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); curr_eee = new_eee = !!(adapter->feat_en & IXGBE_FEATURE_EEE); node.sysctl_data = &new_eee; @@ -5765,8 +5899,8 @@ ixgbe_sysctl_eee_state(SYSCTLFN_ARGS) static void ixgbe_print_debug_info(struct adapter *adapter) { - device_t dev = adapter->dev; - struct ixgbe_hw *hw = &adapter->hw; + device_t dev = adapter->dev; + struct ixgbe_hw *hw = &adapter->hw; int table_size; int i; @@ -5780,7 +5914,7 @@ ixgbe_print_debug_info(struct adapter *a table_size = 32; break; } - + device_printf(dev, "[E]RETA:\n"); for (i = 0; i < table_size; i++) { if (i < 32) @@ -5818,7 +5952,7 @@ ixgbe_print_debug_info(struct adapter *a printf("%8d", adapter->queues[i].disabled_count); } printf("\n"); - + device_printf(dev, "EIMS:\t%08x\n", IXGBE_READ_REG(hw, IXGBE_EIMS)); if (hw->mac.type != ixgbe_mac_82598EB) { device_printf(dev, "EIMS_EX(0):\t%08x\n", @@ -5836,7 +5970,10 @@ ixgbe_sysctl_debug(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct adapter *adapter = (struct adapter *)node.sysctl_data; - int error, result = 0; + int error, result = 0; + + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); node.sysctl_data = &result; error = sysctl_lookup(SYSCTLFN_CALL(&node)); @@ -5857,11 +5994,11 @@ static void ixgbe_init_device_features(struct adapter *adapter) { adapter->feat_cap = IXGBE_FEATURE_NETMAP - | IXGBE_FEATURE_RSS - | IXGBE_FEATURE_MSI - | IXGBE_FEATURE_MSIX - | IXGBE_FEATURE_LEGACY_IRQ - | IXGBE_FEATURE_LEGACY_TX; + | IXGBE_FEATURE_RSS + | IXGBE_FEATURE_MSI + | IXGBE_FEATURE_MSIX + | IXGBE_FEATURE_LEGACY_IRQ + | IXGBE_FEATURE_LEGACY_TX; /* Set capabilities first... */ switch (adapter->hw.mac.type) { @@ -5877,17 +6014,29 @@ ixgbe_init_device_features(struct adapte adapter->feat_cap |= IXGBE_FEATURE_BYPASS; break; case ixgbe_mac_X550: + /* + * IXGBE_FEATURE_RECOVERY_MODE will be set after reading + * NVM Image version. + */ adapter->feat_cap |= IXGBE_FEATURE_TEMP_SENSOR; adapter->feat_cap |= IXGBE_FEATURE_SRIOV; adapter->feat_cap |= IXGBE_FEATURE_FDIR; break; case ixgbe_mac_X550EM_x: + /* + * IXGBE_FEATURE_RECOVERY_MODE will be set after reading + * NVM Image version. + */ adapter->feat_cap |= IXGBE_FEATURE_SRIOV; adapter->feat_cap |= IXGBE_FEATURE_FDIR; if (adapter->hw.device_id == IXGBE_DEV_ID_X550EM_X_KR) adapter->feat_cap |= IXGBE_FEATURE_EEE; break; case ixgbe_mac_X550EM_a: + /* + * IXGBE_FEATURE_RECOVERY_MODE will be set after reading + * NVM Image version. + */ adapter->feat_cap |= IXGBE_FEATURE_SRIOV; adapter->feat_cap |= IXGBE_FEATURE_FDIR; adapter->feat_cap &= ~IXGBE_FEATURE_LEGACY_IRQ; @@ -5923,6 +6072,11 @@ ixgbe_init_device_features(struct adapte /* Thermal Sensor */ if (adapter->feat_cap & IXGBE_FEATURE_TEMP_SENSOR) adapter->feat_en |= IXGBE_FEATURE_TEMP_SENSOR; + /* + * Recovery mode: + * NetBSD: IXGBE_FEATURE_RECOVERY_MODE will be controlled after reading + * NVM Image version. + */ /* Enabled via global sysctl... */ /* Flow Director */ @@ -6003,7 +6157,7 @@ ixgbe_ifflags_cb(struct ethercom *ec) { struct ifnet *ifp = &ec->ec_if; struct adapter *adapter = ifp->if_softc; - int change, rc = 0; + int change, rv = 0; IXGBE_CORE_LOCK(adapter); @@ -6011,17 +6165,19 @@ ixgbe_ifflags_cb(struct ethercom *ec) if (change != 0) adapter->if_flags = ifp->if_flags; - if ((change & ~(IFF_CANTCHANGE | IFF_DEBUG)) != 0) - rc = ENETRESET; - else if ((change & (IFF_PROMISC | IFF_ALLMULTI)) != 0) + if ((change & ~(IFF_CANTCHANGE | IFF_DEBUG)) != 0) { + rv = ENETRESET; + goto out; + } else if ((change & (IFF_PROMISC | IFF_ALLMULTI)) != 0) ixgbe_set_promisc(adapter); /* Set up VLAN support and filter */ ixgbe_setup_vlan_hw_support(adapter); +out: IXGBE_CORE_UNLOCK(adapter); - return rc; + return rv; } /************************************************************************ @@ -6038,10 +6194,13 @@ ixgbe_ioctl(struct ifnet * ifp, u_long c struct ixgbe_hw *hw = &adapter->hw; struct ifcapreq *ifcr = data; struct ifreq *ifr = data; - int error = 0; + int error = 0; int l4csum_en; - const int l4csum = IFCAP_CSUM_TCPv4_Rx|IFCAP_CSUM_UDPv4_Rx| - IFCAP_CSUM_TCPv6_Rx|IFCAP_CSUM_UDPv6_Rx; + const int l4csum = IFCAP_CSUM_TCPv4_Rx | IFCAP_CSUM_UDPv4_Rx | + IFCAP_CSUM_TCPv6_Rx | IFCAP_CSUM_UDPv6_Rx; + + if (ixgbe_fw_recovery_mode_swflag(adapter)) + return (EPERM); switch (command) { case SIOCSIFFLAGS: @@ -6188,9 +6347,9 @@ static void ixgbe_handle_que(void *context) { struct ix_queue *que = context; - struct adapter *adapter = que->adapter; - struct tx_ring *txr = que->txr; - struct ifnet *ifp = adapter->ifp; + struct adapter *adapter = que->adapter; + struct tx_ring *txr = que->txr; + struct ifnet *ifp = adapter->ifp; bool more = false; que->handleq.ev_count++; @@ -6246,12 +6405,12 @@ ixgbe_allocate_legacy(struct adapter *ad { device_t dev = adapter->dev; struct ix_queue *que = adapter->queues; - struct tx_ring *txr = adapter->tx_rings; + struct tx_ring *txr = adapter->tx_rings; int counts[PCI_INTR_TYPE_SIZE]; pci_intr_type_t intr_type, max_type; - char intrbuf[PCI_INTRSTR_LEN]; + char intrbuf[PCI_INTRSTR_LEN]; const char *intrstr = NULL; - + /* We allocate a single interrupt resource */ max_type = PCI_INTR_TYPE_MSI; counts[PCI_INTR_TYPE_MSIX] = 0; @@ -6322,7 +6481,7 @@ alloc_retry: if ((!(adapter->feat_en & IXGBE_FEATURE_LEGACY_TX) & (txr->txr_si == NULL)) || (que->que_si == NULL)) { aprint_error_dev(dev, - "could not establish software interrupts\n"); + "could not establish software interrupts\n"); return ENXIO; } @@ -6338,19 +6497,19 @@ alloc_retry: static int ixgbe_allocate_msix(struct adapter *adapter, const struct pci_attach_args *pa) { - device_t dev = adapter->dev; - struct ix_queue *que = adapter->queues; - struct tx_ring *txr = adapter->tx_rings; + device_t dev = adapter->dev; + struct ix_queue *que = adapter->queues; + struct tx_ring *txr = adapter->tx_rings; pci_chipset_tag_t pc; char intrbuf[PCI_INTRSTR_LEN]; char intr_xname[32]; char wqname[MAXCOMLEN]; const char *intrstr = NULL; - int error, vector = 0; + int error, vector = 0; int cpu_id = 0; kcpuset_t *affinity; #ifdef RSS - unsigned int rss_buckets = 0; + unsigned int rss_buckets = 0; kcpuset_t cpu_mask; #endif @@ -6406,7 +6565,7 @@ ixgbe_allocate_msix(struct adapter *adap goto err_out; } que->msix = vector; - adapter->active_queues |= (u64)(1 << que->msix); + adapter->active_queues |= 1ULL << que->msix; if (adapter->feat_en & IXGBE_FEATURE_RSS) { #ifdef RSS @@ -6465,7 +6624,7 @@ ixgbe_allocate_msix(struct adapter *adap ixgbe_handle_que, que); if (que->que_si == NULL) { aprint_error_dev(dev, - "couldn't establish software interrupt\n"); + "couldn't establish software interrupt\n"); error = ENXIO; goto err_out; } @@ -6527,7 +6686,7 @@ ixgbe_allocate_msix(struct adapter *adap ixgbe_handle_mbx, adapter); if (adapter->mbx_si == NULL) { aprint_error_dev(dev, - "could not establish software interrupts\n"); + "could not establish software interrupts\n"); error = ENXIO; goto err_out; @@ -6573,7 +6732,7 @@ ixgbe_configure_interrupts(struct adapte */ if (ncpu == 1) goto msi; - + /* First try MSI-X */ msgs = pci_msix_count(adapter->osdep.pc, adapter->osdep.tag); msgs = MIN(msgs, IXG_MAX_NINTR); @@ -6612,7 +6771,7 @@ ixgbe_configure_interrupts(struct adapte if (msgs >= want) msgs = want; else { - aprint_error_dev(dev, "MSI-X Configuration Problem, " + aprint_error_dev(dev, "MSI-X Configuration Problem, " "%d vectors but %d queues wanted!\n", msgs, want); goto msi; @@ -6633,7 +6792,7 @@ msi: adapter->feat_cap &= ~IXGBE_FEATURE_SRIOV; adapter->feat_en &= ~IXGBE_FEATURE_SRIOV; - msgs = pci_msi_count(adapter->osdep.pc, adapter->osdep.tag); + msgs = pci_msi_count(adapter->osdep.pc, adapter->osdep.tag); adapter->msix_mem = NULL; /* XXX */ if (msgs > 1) msgs = 1; @@ -6663,7 +6822,7 @@ msi: static void ixgbe_handle_link(void *context) { - struct adapter *adapter = context; + struct adapter *adapter = context; struct ixgbe_hw *hw = &adapter->hw; IXGBE_CORE_LOCK(adapter); Index: src/sys/dev/pci/ixgbe/ixgbe.h diff -u src/sys/dev/pci/ixgbe/ixgbe.h:1.24.6.16 src/sys/dev/pci/ixgbe/ixgbe.h:1.24.6.17 --- src/sys/dev/pci/ixgbe/ixgbe.h:1.24.6.16 Fri Mar 1 17:33:24 2019 +++ src/sys/dev/pci/ixgbe/ixgbe.h Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe.h,v 1.24.6.16 2019/03/01 17:33:24 martin Exp $ */ +/* $NetBSD: ixgbe.h,v 1.24.6.17 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -240,7 +240,7 @@ #endif /* - * Interrupt Moderation parameters + * Interrupt Moderation parameters */ #define IXGBE_LOW_LATENCY 128 #define IXGBE_AVE_LATENCY 400 @@ -348,7 +348,7 @@ struct ix_queue { * The transmit ring, one per queue */ struct tx_ring { - struct adapter *adapter; + struct adapter *adapter; kmutex_t tx_mtx; u32 me; u32 tail; @@ -396,7 +396,7 @@ struct tx_ring { * The Receive ring, one per rx queue */ struct rx_ring { - struct adapter *adapter; + struct adapter *adapter; kmutex_t rx_mtx; u32 me; u32 tail; @@ -408,8 +408,8 @@ struct rx_ring { bool lro_enabled; bool hw_rsc; bool vtag_strip; - u16 next_to_refresh; - u16 next_to_check; + u16 next_to_refresh; + u16 next_to_check; u16 num_desc; u16 mbuf_sz; #if 0 @@ -574,6 +574,10 @@ struct adapter { void (*init_locked)(struct adapter *); void (*stop_locked)(void *); + /* Firmware error check */ + u_int recovery_mode; + struct callout recovery_mode_timer; + /* Misc stats maintained by the driver */ struct evcnt efbig_tx_dma_setup; struct evcnt mbuf_defrag_failed; @@ -674,11 +678,11 @@ struct adapter { "\nControl advertised link speed using these flags:\n" \ "\t0x01 - advertise 100M\n" \ "\t0x02 - advertise 1G\n" \ - "\t0x04 - advertise 10G\n" \ - "\t0x08 - advertise 10M\n" \ - "\t0x10 - advertise 2.5G\n" \ - "\t0x20 - advertise 5G\n\n" \ - "\t5G, 2.5G, 100M and 10M are only supported on certain adapters." + "\t0x04 - advertise 10G\n" \ + "\t0x08 - advertise 10M\n" \ + "\t0x10 - advertise 2.5G\n" \ + "\t0x20 - advertise 5G\n\n" \ + "\t5G, 2.5G, 100M and 10M are only supported on certain adapters." #define IXGBE_SYSCTL_DESC_SET_FC \ "\nSet flow control mode using these values:\n" \ @@ -745,6 +749,18 @@ ixv_check_ether_addr(u8 *addr) return (status); } +/* + * This checks the adapter->recovery_mode software flag which is + * set by ixgbe_fw_recovery_mode(). + * + */ +static inline bool +ixgbe_fw_recovery_mode_swflag(struct adapter *adapter) +{ + return (adapter->feat_en & IXGBE_FEATURE_RECOVERY_MODE) && + atomic_load_acq_uint(&adapter->recovery_mode); +} + /* Shared Prototypes */ void ixgbe_legacy_start(struct ifnet *); int ixgbe_legacy_start_locked(struct ifnet *, struct tx_ring *); Index: src/sys/dev/pci/ixgbe/ixgbe_82599.c diff -u src/sys/dev/pci/ixgbe/ixgbe_82599.c:1.14.8.4 src/sys/dev/pci/ixgbe/ixgbe_82599.c:1.14.8.5 --- src/sys/dev/pci/ixgbe/ixgbe_82599.c:1.14.8.4 Thu Jul 26 23:21:54 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_82599.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_82599.c,v 1.14.8.4 2018/07/26 23:21:54 snj Exp $ */ +/* $NetBSD: ixgbe_82599.c,v 1.14.8.5 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -566,9 +566,6 @@ enum ixgbe_media_type ixgbe_get_media_ty case IXGBE_DEV_ID_82599_T3_LOM: media_type = ixgbe_media_type_copper; break; - case IXGBE_DEV_ID_82599_LS: - media_type = ixgbe_media_type_fiber_lco; - break; case IXGBE_DEV_ID_82599_QSFP_SF_QP: media_type = ixgbe_media_type_fiber_qsfp; break; Index: src/sys/dev/pci/ixgbe/ixgbe_api.c diff -u src/sys/dev/pci/ixgbe/ixgbe_api.c:1.15.8.4 src/sys/dev/pci/ixgbe/ixgbe_api.c:1.15.8.5 --- src/sys/dev/pci/ixgbe/ixgbe_api.c:1.15.8.4 Thu Jul 26 23:21:54 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_api.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_api.c,v 1.15.8.4 2018/07/26 23:21:54 snj Exp $ */ +/* $NetBSD: ixgbe_api.c,v 1.15.8.5 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -173,7 +173,6 @@ s32 ixgbe_set_mac_type(struct ixgbe_hw * case IXGBE_DEV_ID_82599_SFP_SF_QP: case IXGBE_DEV_ID_82599_QSFP_SF_QP: case IXGBE_DEV_ID_82599EN_SFP: - case IXGBE_DEV_ID_82599_LS: case IXGBE_DEV_ID_82599_CX4: case IXGBE_DEV_ID_82599_BYPASS: case IXGBE_DEV_ID_82599_T3_LOM: @@ -1107,6 +1106,19 @@ s32 ixgbe_set_vlvf(struct ixgbe_hw *hw, } /** + * ixgbe_toggle_txdctl - Toggle VF's queues + * @hw: pointer to hardware structure + * @vind: VMDq pool index + * + * Enable and disable each queue in VF. + */ +s32 ixgbe_toggle_txdctl(struct ixgbe_hw *hw, u32 vind) +{ + return ixgbe_call_func(hw, hw->mac.ops.toggle_txdctl, (hw, + vind), IXGBE_NOT_IMPLEMENTED); +} + +/** * ixgbe_fc_enable - Enable flow control * @hw: pointer to hardware structure * @@ -1310,6 +1322,18 @@ void ixgbe_restore_mdd_vf(struct ixgbe_h } /** + * ixgbe_fw_recovery_mode - Check if in FW NVM recovery mode + * @hw: pointer to hardware structure + * + **/ +bool ixgbe_fw_recovery_mode(struct ixgbe_hw *hw) +{ + if (hw->mac.ops.fw_recovery_mode) + return hw->mac.ops.fw_recovery_mode(hw); + return FALSE; +} + +/** * ixgbe_enter_lplu - Transition to low power states * @hw: pointer to hardware structure * Index: src/sys/dev/pci/ixgbe/ixgbe_api.h diff -u src/sys/dev/pci/ixgbe/ixgbe_api.h:1.9.8.3 src/sys/dev/pci/ixgbe/ixgbe_api.h:1.9.8.4 --- src/sys/dev/pci/ixgbe/ixgbe_api.h:1.9.8.3 Sat Apr 14 10:25:11 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_api.h Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_api.h,v 1.9.8.3 2018/04/14 10:25:11 martin Exp $ */ +/* $NetBSD: ixgbe_api.h,v 1.9.8.4 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -133,6 +133,7 @@ s32 ixgbe_set_vfta(struct ixgbe_hw *hw, s32 ixgbe_set_vlvf(struct ixgbe_hw *hw, u32 vlan, u32 vind, bool vlan_on, u32 *vfta_delta, u32 vfta, bool vlvf_bypass); +s32 ixgbe_toggle_txdctl(struct ixgbe_hw *hw, u32 vind); s32 ixgbe_fc_enable(struct ixgbe_hw *hw); s32 ixgbe_setup_fc(struct ixgbe_hw *hw); s32 ixgbe_set_fw_drv_ver(struct ixgbe_hw *hw, u8 maj, u8 min, u8 build, @@ -219,6 +220,7 @@ void ixgbe_disable_mdd(struct ixgbe_hw * void ixgbe_enable_mdd(struct ixgbe_hw *hw); void ixgbe_mdd_event(struct ixgbe_hw *hw, u32 *vf_bitmap); void ixgbe_restore_mdd_vf(struct ixgbe_hw *hw, u32 vf); +bool ixgbe_fw_recovery_mode(struct ixgbe_hw *hw); s32 ixgbe_enter_lplu(struct ixgbe_hw *hw); s32 ixgbe_handle_lasi(struct ixgbe_hw *hw); void ixgbe_set_rate_select_speed(struct ixgbe_hw *hw, ixgbe_link_speed speed); Index: src/sys/dev/pci/ixgbe/ixgbe_common.c diff -u src/sys/dev/pci/ixgbe/ixgbe_common.c:1.13.2.4 src/sys/dev/pci/ixgbe/ixgbe_common.c:1.13.2.5 --- src/sys/dev/pci/ixgbe/ixgbe_common.c:1.13.2.4 Sat Apr 14 10:25:11 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_common.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_common.c,v 1.13.2.4 2018/04/14 10:25:11 martin Exp $ */ +/* $NetBSD: ixgbe_common.c,v 1.13.2.5 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -136,6 +136,7 @@ s32 ixgbe_init_ops_generic(struct ixgbe_ mac->ops.init_uta_tables = NULL; mac->ops.enable_rx = ixgbe_enable_rx_generic; mac->ops.disable_rx = ixgbe_disable_rx_generic; + mac->ops.toggle_txdctl = ixgbe_toggle_txdctl_generic; /* Flow Control */ mac->ops.fc_enable = ixgbe_fc_enable_generic; @@ -4163,6 +4164,61 @@ s32 ixgbe_clear_vfta_generic(struct ixgb } /** + * ixgbe_toggle_txdctl_generic - Toggle VF's queues + * @hw: pointer to hardware structure + * @vf_number: VF index + * + * Enable and disable each queue in VF. + */ +s32 ixgbe_toggle_txdctl_generic(struct ixgbe_hw *hw, u32 vf_number) +{ + u8 queue_count, i; + u32 offset, reg; + + if (vf_number > 63) + return IXGBE_ERR_PARAM; + + /* + * Determine number of queues by checking + * number of virtual functions + */ + reg = IXGBE_READ_REG(hw, IXGBE_GCR_EXT); + switch (reg & IXGBE_GCR_EXT_VT_MODE_MASK) { + case IXGBE_GCR_EXT_VT_MODE_64: + queue_count = 2; + break; + case IXGBE_GCR_EXT_VT_MODE_32: + queue_count = 4; + break; + case IXGBE_GCR_EXT_VT_MODE_16: + queue_count = 8; + break; + default: + return IXGBE_ERR_CONFIG; + } + + /* Toggle queues */ + for (i = 0; i < queue_count; ++i) { + /* Calculate offset of current queue */ + offset = queue_count * vf_number + i; + + /* Enable queue */ + reg = IXGBE_READ_REG(hw, IXGBE_PVFTXDCTL(offset)); + reg |= IXGBE_TXDCTL_ENABLE; + IXGBE_WRITE_REG(hw, IXGBE_PVFTXDCTL(offset), reg); + IXGBE_WRITE_FLUSH(hw); + + /* Disable queue */ + reg = IXGBE_READ_REG(hw, IXGBE_PVFTXDCTL(offset)); + reg &= ~IXGBE_TXDCTL_ENABLE; + IXGBE_WRITE_REG(hw, IXGBE_PVFTXDCTL(offset), reg); + IXGBE_WRITE_FLUSH(hw); + } + + return IXGBE_SUCCESS; +} + +/** * ixgbe_need_crosstalk_fix - Determine if we need to do cross talk fix * @hw: pointer to hardware structure * @@ -4579,11 +4635,18 @@ s32 ixgbe_hic_unlocked(struct ixgbe_hw * msec_delay(1); } + /* For each command except "Apply Update" perform + * status checks in the HICR registry. + */ + if ((buffer[0] & IXGBE_HOST_INTERFACE_MASK_CMD) == + IXGBE_HOST_INTERFACE_APPLY_UPDATE_CMD) + return IXGBE_SUCCESS; + /* Check command completion */ if ((timeout && i == timeout) || !(IXGBE_READ_REG(hw, IXGBE_HICR) & IXGBE_HICR_SV)) { ERROR_REPORT1(IXGBE_ERROR_CAUTION, - "Command has failed with no status valid.\n"); + "Command has failed with no status valid.\n"); return IXGBE_ERR_HOST_INTERFACE_COMMAND; } @@ -4651,7 +4714,7 @@ s32 ixgbe_host_interface_command(struct * Read Flash command requires reading buffer length from * two byes instead of one byte */ - if (resp->cmd == 0x30) { + if (resp->cmd == 0x30 || resp->cmd == 0x31) { for (; bi < dword_len + 2; bi++) { buffer[bi] = IXGBE_READ_REG_ARRAY(hw, IXGBE_FLEX_MNG, bi); Index: src/sys/dev/pci/ixgbe/ixgbe_common.h diff -u src/sys/dev/pci/ixgbe/ixgbe_common.h:1.7.8.4 src/sys/dev/pci/ixgbe/ixgbe_common.h:1.7.8.5 --- src/sys/dev/pci/ixgbe/ixgbe_common.h:1.7.8.4 Sat Apr 14 10:25:11 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_common.h Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_common.h,v 1.7.8.4 2018/04/14 10:25:11 martin Exp $ */ +/* $NetBSD: ixgbe_common.h,v 1.7.8.5 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -146,6 +146,7 @@ s32 ixgbe_set_vlvf_generic(struct ixgbe_ bool vlvf_bypass); s32 ixgbe_clear_vfta_generic(struct ixgbe_hw *hw); s32 ixgbe_find_vlvf_slot(struct ixgbe_hw *hw, u32 vlan, bool vlvf_bypass); +s32 ixgbe_toggle_txdctl_generic(struct ixgbe_hw *hw, u32 vind); s32 ixgbe_check_mac_link_generic(struct ixgbe_hw *hw, ixgbe_link_speed *speed, Index: src/sys/dev/pci/ixgbe/ixgbe_features.h diff -u src/sys/dev/pci/ixgbe/ixgbe_features.h:1.1.4.2 src/sys/dev/pci/ixgbe/ixgbe_features.h:1.1.4.3 --- src/sys/dev/pci/ixgbe/ixgbe_features.h:1.1.4.2 Thu Dec 21 19:28:54 2017 +++ src/sys/dev/pci/ixgbe/ixgbe_features.h Mon Jul 22 17:53:35 2019 @@ -57,12 +57,13 @@ #define IXGBE_FEATURE_EEE (u32)(1 << 11) #define IXGBE_FEATURE_LEGACY_IRQ (u32)(1 << 12) #define IXGBE_FEATURE_NEEDS_CTXD (u32)(1 << 13) +#define IXGBE_FEATURE_RECOVERY_MODE (u32)(1 << 15) #define IXGBE_FEATURE_FLAGS "\20" \ "\1" "VF" "\2" "SRIOV" "\3" "RSS" "\4" "NETMAP" \ "\5" "FAN_FAIL" "\6" "TEMP_SENSOR" "\7" "BYPASS" "\10" "LEGACY_TX" \ "\11" "FDIR" "\12" "MSI" "\13" "MSIX" "\14" "EEE" \ - "\15" "LEGACY_IRQ" "\16" "NEEDS_CTXD" + "\15" "LEGACY_IRQ" "\16" "NEEDS_CTXD" "\20" "RECOVERY_MODE" /* Check for OS support. Undefine features if not included in the OS */ #ifndef PCI_IOV Index: src/sys/dev/pci/ixgbe/ixgbe_netmap.c diff -u src/sys/dev/pci/ixgbe/ixgbe_netmap.c:1.1.4.2 src/sys/dev/pci/ixgbe/ixgbe_netmap.c:1.1.4.3 --- src/sys/dev/pci/ixgbe/ixgbe_netmap.c:1.1.4.2 Thu Dec 21 19:28:54 2017 +++ src/sys/dev/pci/ixgbe/ixgbe_netmap.c Mon Jul 22 17:53:35 2019 @@ -408,7 +408,6 @@ ixgbe_netmap_rxsync(struct netmap_kring */ if (netmap_no_pendintr || force_update) { int crclen = (ix_crcstrip) ? 0 : 4; - uint16_t slot_flags = kring->nkr_slot_flags; nic_i = rxr->next_to_check; // or also k2n(kring->nr_hwtail) nm_i = netmap_idx_n2k(kring, nic_i); @@ -420,7 +419,7 @@ ixgbe_netmap_rxsync(struct netmap_kring if ((staterr & IXGBE_RXD_STAT_DD) == 0) break; ring->slot[nm_i].len = le16toh(curr->wb.upper.length) - crclen; - ring->slot[nm_i].flags = slot_flags; + ring->slot[nm_i].flags = 0; bus_dmamap_sync(rxr->ptag, rxr->rx_buffers[nic_i].pmap, BUS_DMASYNC_POSTREAD); nm_i = nm_next(nm_i, lim); Index: src/sys/dev/pci/ixgbe/ixgbe_mbx.c diff -u src/sys/dev/pci/ixgbe/ixgbe_mbx.c:1.6.8.2 src/sys/dev/pci/ixgbe/ixgbe_mbx.c:1.6.8.3 --- src/sys/dev/pci/ixgbe/ixgbe_mbx.c:1.6.8.2 Sat Apr 14 10:25:12 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_mbx.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_mbx.c,v 1.6.8.2 2018/04/14 10:25:12 martin Exp $ */ +/* $NetBSD: ixgbe_mbx.c,v 1.6.8.3 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -39,6 +39,26 @@ #include "ixgbe_mbx.h" /** + * ixgbe_clear_mbx - Clear Mailbox Memory + * @hw: pointer to the HW structure + * @vf_number: id of mailbox to write + * + * Set VFMBMEM of given VF to 0x0. + **/ +s32 ixgbe_clear_mbx(struct ixgbe_hw *hw, u16 vf_number) +{ + struct ixgbe_mbx_info *mbx = &hw->mbx; + s32 ret_val = IXGBE_SUCCESS; + + DEBUGFUNC("ixgbe_clear_mbx"); + + if (mbx->ops.clear) + ret_val = mbx->ops.clear(hw, vf_number); + + return ret_val; +} + +/** * ixgbe_poll_for_msg - Wait for message notification * @hw: pointer to the HW structure * @mbx_id: id of mailbox to write @@ -408,6 +428,7 @@ void ixgbe_init_mbx_params_vf(struct ixg mbx->ops.check_for_msg = ixgbe_check_for_msg_vf; mbx->ops.check_for_ack = ixgbe_check_for_ack_vf; mbx->ops.check_for_rst = ixgbe_check_for_rst_vf; + mbx->ops.clear = NULL; mbx->stats.msgs_tx.ev_count = 0; mbx->stats.msgs_rx.ev_count = 0; @@ -625,6 +646,27 @@ out_no_read: } /** + * ixgbe_clear_mbx_pf - Clear Mailbox Memory + * @hw: pointer to the HW structure + * @vf_number: the VF index + * + * Set VFMBMEM of given VF to 0x0. + **/ +static s32 ixgbe_clear_mbx_pf(struct ixgbe_hw *hw, u16 vf_number) +{ + u16 mbx_size = hw->mbx.size; + u16 i; + + if (vf_number > 63) + return IXGBE_ERR_PARAM; + + for (i = 0; i < mbx_size; ++i) + IXGBE_WRITE_REG_ARRAY(hw, IXGBE_PFMBMEM(vf_number), i, 0x0); + + return IXGBE_SUCCESS; +} + +/** * ixgbe_init_mbx_params_pf - set initial values for pf mailbox * @hw: pointer to the HW structure * @@ -653,6 +695,7 @@ void ixgbe_init_mbx_params_pf(struct ixg mbx->ops.check_for_msg = ixgbe_check_for_msg_pf; mbx->ops.check_for_ack = ixgbe_check_for_ack_pf; mbx->ops.check_for_rst = ixgbe_check_for_rst_pf; + mbx->ops.clear = ixgbe_clear_mbx_pf; mbx->stats.msgs_tx.ev_count = 0; mbx->stats.msgs_rx.ev_count = 0; Index: src/sys/dev/pci/ixgbe/ixgbe_mbx.h diff -u src/sys/dev/pci/ixgbe/ixgbe_mbx.h:1.10.8.2 src/sys/dev/pci/ixgbe/ixgbe_mbx.h:1.10.8.3 --- src/sys/dev/pci/ixgbe/ixgbe_mbx.h:1.10.8.2 Sat Apr 14 10:25:11 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_mbx.h Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_mbx.h,v 1.10.8.2 2018/04/14 10:25:11 martin Exp $ */ +/* $NetBSD: ixgbe_mbx.h,v 1.10.8.3 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -155,6 +155,7 @@ enum ixgbevf_xcast_modes { #define IXGBE_VF_MBX_INIT_TIMEOUT 2000 /* number of retries on mailbox */ #define IXGBE_VF_MBX_INIT_DELAY 500 /* microseconds between retries */ +s32 ixgbe_clear_mbx(struct ixgbe_hw *hw, u16 vf_number); void ixgbe_init_mbx_ops_generic(struct ixgbe_hw *hw); void ixgbe_init_mbx_params_vf(struct ixgbe_hw *); void ixgbe_init_mbx_params_pf(struct ixgbe_hw *); Index: src/sys/dev/pci/ixgbe/ixgbe_netbsd.c diff -u src/sys/dev/pci/ixgbe/ixgbe_netbsd.c:1.6.2.2 src/sys/dev/pci/ixgbe/ixgbe_netbsd.c:1.6.2.3 --- src/sys/dev/pci/ixgbe/ixgbe_netbsd.c:1.6.2.2 Tue Aug 7 13:33:23 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_netbsd.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_netbsd.c,v 1.6.2.2 2018/08/07 13:33:23 martin Exp $ */ +/* $NetBSD: ixgbe_netbsd.c,v 1.6.2.3 2019/07/22 17:53:35 martin Exp $ */ /* * Copyright (c) 2011 The NetBSD Foundation, Inc. * All rights reserved. @@ -273,3 +273,19 @@ ixgbe_pci_enable_busmaster(pci_chipset_t pci_conf_write(pc, tag, PCI_COMMAND_STATUS_REG, pci_cmd_word); } } + +u_int +atomic_load_acq_uint(volatile u_int *p) +{ + u_int rv; + + rv = *p; + /* + * XXX + * membar_sync() is far more than we need on most CPUs; + * we just don't have an MI load-acqure operation. + */ + membar_sync(); + + return rv; +} Index: src/sys/dev/pci/ixgbe/ixgbe_netbsd.h diff -u src/sys/dev/pci/ixgbe/ixgbe_netbsd.h:1.7.6.1 src/sys/dev/pci/ixgbe/ixgbe_netbsd.h:1.7.6.2 --- src/sys/dev/pci/ixgbe/ixgbe_netbsd.h:1.7.6.1 Sat Jun 9 14:59:43 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_netbsd.h Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/*$NetBSD: ixgbe_netbsd.h,v 1.7.6.1 2018/06/09 14:59:43 martin Exp $*/ +/*$NetBSD: ixgbe_netbsd.h,v 1.7.6.2 2019/07/22 17:53:35 martin Exp $*/ /* * Copyright (c) 2011 The NetBSD Foundation, Inc. * All rights reserved. @@ -96,4 +96,6 @@ void ixgbe_dmamap_unload(ixgbe_dma_tag_t struct mbuf *ixgbe_getjcl(ixgbe_extmem_head_t *, int, int, int, size_t); void ixgbe_pci_enable_busmaster(pci_chipset_tag_t, pcitag_t); +u_int atomic_load_acq_uint(volatile u_int *); + #endif /* _IXGBE_NETBSD_H */ Index: src/sys/dev/pci/ixgbe/ixgbe_phy.c diff -u src/sys/dev/pci/ixgbe/ixgbe_phy.c:1.11.6.3 src/sys/dev/pci/ixgbe/ixgbe_phy.c:1.11.6.4 --- src/sys/dev/pci/ixgbe/ixgbe_phy.c:1.11.6.3 Sat Apr 14 10:25:12 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_phy.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_phy.c,v 1.11.6.3 2018/04/14 10:25:12 martin Exp $ */ +/* $NetBSD: ixgbe_phy.c,v 1.11.6.4 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -2612,7 +2612,6 @@ static bool ixgbe_get_i2c_data(struct ix { u32 data_oe_bit = IXGBE_I2C_DATA_OE_N_EN_BY_MAC(hw); bool data; - UNREFERENCED_1PARAMETER(hw); DEBUGFUNC("ixgbe_get_i2c_data"); Index: src/sys/dev/pci/ixgbe/ixgbe_type.h diff -u src/sys/dev/pci/ixgbe/ixgbe_type.h:1.22.2.8 src/sys/dev/pci/ixgbe/ixgbe_type.h:1.22.2.9 --- src/sys/dev/pci/ixgbe/ixgbe_type.h:1.22.2.8 Mon Apr 1 12:35:38 2019 +++ src/sys/dev/pci/ixgbe/ixgbe_type.h Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_type.h,v 1.22.2.8 2019/04/01 12:35:38 martin Exp $ */ +/* $NetBSD: ixgbe_type.h,v 1.22.2.9 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -131,7 +131,6 @@ #define IXGBE_SUBDEV_ID_82599EN_SFP_OCP1 0x0001 #define IXGBE_DEV_ID_82599_XAUI_LOM PCI_PRODUCT_INTEL_82599_XAUI_LOM #define IXGBE_DEV_ID_82599_T3_LOM 0x151C -#define IXGBE_DEV_ID_82599_LS 0x154F #define IXGBE_DEV_ID_82599_VF 0x10ED #define IXGBE_DEV_ID_82599_VF_HV 0x152E #define IXGBE_DEV_ID_82599_BYPASS 0x155D @@ -211,6 +210,10 @@ #define IXGBE_FLA_X550EM_x IXGBE_FLA #define IXGBE_FLA_X550EM_a 0x15F68 #define IXGBE_FLA_BY_MAC(_hw) IXGBE_BY_MAC((_hw), FLA) +#define IXGBE_FLA_FL_SIZE_SHIFT_X540 17 +#define IXGBE_FLA_FL_SIZE_SHIFT_X550 12 +#define IXGBE_FLA_FL_SIZE_MASK_X540 (0x7 << IXGBE_FLA_FL_SIZE_SHIFT_X540) +#define IXGBE_FLA_FL_SIZE_MASK_X550 (0x7 << IXGBE_FLA_FL_SIZE_SHIFT_X550) #define IXGBE_EEMNGCTL 0x10110 #define IXGBE_EEMNGDATA 0x10114 @@ -878,6 +881,10 @@ struct ixgbe_dmac_config { #define IXGBE_RTTDQSEL 0x04904 #define IXGBE_RTTDT1C 0x04908 #define IXGBE_RTTDT1S 0x0490C +#define IXGBE_RTTQCNCR 0x08B00 +#define IXGBE_RTTQCNTG 0x04A90 +#define IXGBE_RTTBCNRD 0x0498C +#define IXGBE_RTTQCNRR 0x0498C #define IXGBE_RTTDTECC 0x04990 #define IXGBE_RTTDTECC_NO_BCN 0x00000100 @@ -888,6 +895,7 @@ struct ixgbe_dmac_config { #define IXGBE_RTTBCNRC_RF_INT_MASK \ (IXGBE_RTTBCNRC_RF_DEC_MASK << IXGBE_RTTBCNRC_RF_INT_SHIFT) #define IXGBE_RTTBCNRM 0x04980 +#define IXGBE_RTTQCNRM 0x04980 /* BCN (for DCB) Registers */ #define IXGBE_RTTBCNRS 0x04988 @@ -1096,6 +1104,9 @@ struct ixgbe_dmac_config { #define IXGBE_FWSM_MODE_MASK 0xE #define IXGBE_FWSM_TS_ENABLED 0x1 #define IXGBE_FWSM_FW_MODE_PT 0x4 +#define IXGBE_FWSM_FW_NVM_RECOVERY_MODE (1 << 5) +#define IXGBE_FWSM_EXT_ERR_IND_MASK 0x01F80000 +#define IXGBE_FWSM_FW_VAL_BIT (1 << 15) /* ARC Subsystem registers */ #define IXGBE_HICR 0x15F00 @@ -1441,6 +1452,7 @@ struct ixgbe_dmac_config { #define IXGBE_BARCTRL_FLSIZE 0x0700 #define IXGBE_BARCTRL_FLSIZE_SHIFT 8 #define IXGBE_BARCTRL_CSRSIZE 0x2000 +#define IXGBE_BARCTRL_CSRSIZE_SHIFT 13 /* RSCCTL Bit Masks */ #define IXGBE_RSCCTL_RSCEN 0x01 @@ -3759,7 +3771,6 @@ enum ixgbe_media_type { ixgbe_media_type_fiber, ixgbe_media_type_fiber_fixed, ixgbe_media_type_fiber_qsfp, - ixgbe_media_type_fiber_lco, ixgbe_media_type_copper, ixgbe_media_type_backplane, ixgbe_media_type_cx4, @@ -4049,6 +4060,7 @@ struct ixgbe_mac_operations { s32 (*init_uta_tables)(struct ixgbe_hw *); void (*set_mac_anti_spoofing)(struct ixgbe_hw *, bool, int); void (*set_vlan_anti_spoofing)(struct ixgbe_hw *, bool, int); + s32 (*toggle_txdctl)(struct ixgbe_hw *hw, u32 vf_index); /* Flow Control */ s32 (*fc_enable)(struct ixgbe_hw *); @@ -4078,6 +4090,7 @@ struct ixgbe_mac_operations { void (*enable_mdd)(struct ixgbe_hw *hw); void (*mdd_event)(struct ixgbe_hw *hw, u32 *vf_bitmap); void (*restore_mdd_vf)(struct ixgbe_hw *hw, u32 vf); + bool (*fw_recovery_mode)(struct ixgbe_hw *hw); }; struct ixgbe_phy_operations { @@ -4132,6 +4145,8 @@ struct ixgbe_eeprom_info { u16 address_bits; u16 word_page_size; u16 ctrl_word_3; + u8 nvm_image_ver_high; + u8 nvm_image_ver_low; }; #define IXGBE_FLAGS_DOUBLE_RESET_REQUIRED 0x01 @@ -4205,6 +4220,7 @@ struct ixgbe_mbx_operations { s32 (*check_for_msg)(struct ixgbe_hw *, u16); s32 (*check_for_ack)(struct ixgbe_hw *, u16); s32 (*check_for_rst)(struct ixgbe_hw *, u16); + s32 (*clear)(struct ixgbe_hw *hw, u16 vf_number); }; struct ixgbe_mbx_stats { @@ -4505,4 +4521,16 @@ struct ixgbe_bypass_eeprom { #define IXGBE_NW_MNG_IF_SEL_MDIO_PHY_ADD \ (0x1F << IXGBE_NW_MNG_IF_SEL_MDIO_PHY_ADD_SHIFT) +/* Code Command (Flash I/F Interface) */ +#define IXGBE_HOST_INTERFACE_FLASH_READ_CMD 0x30 +#define IXGBE_HOST_INTERFACE_SHADOW_RAM_READ_CMD 0x31 +#define IXGBE_HOST_INTERFACE_FLASH_WRITE_CMD 0x32 +#define IXGBE_HOST_INTERFACE_SHADOW_RAM_WRITE_CMD 0x33 +#define IXGBE_HOST_INTERFACE_FLASH_MODULE_UPDATE_CMD 0x34 +#define IXGBE_HOST_INTERFACE_FLASH_BLOCK_EREASE_CMD 0x35 +#define IXGBE_HOST_INTERFACE_SHADOW_RAM_DUMP_CMD 0x36 +#define IXGBE_HOST_INTERFACE_FLASH_INFO_CMD 0x37 +#define IXGBE_HOST_INTERFACE_APPLY_UPDATE_CMD 0x38 +#define IXGBE_HOST_INTERFACE_MASK_CMD 0x000000FF + #endif /* _IXGBE_TYPE_H_ */ Index: src/sys/dev/pci/ixgbe/ixgbe_vf.c diff -u src/sys/dev/pci/ixgbe/ixgbe_vf.c:1.12.8.2 src/sys/dev/pci/ixgbe/ixgbe_vf.c:1.12.8.3 --- src/sys/dev/pci/ixgbe/ixgbe_vf.c:1.12.8.2 Sat Apr 14 10:25:11 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_vf.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/* $NetBSD: ixgbe_vf.c,v 1.12.8.2 2018/04/14 10:25:11 martin Exp $ */ +/* $NetBSD: ixgbe_vf.c,v 1.12.8.3 2019/07/22 17:53:35 martin Exp $ */ /****************************************************************************** SPDX-License-Identifier: BSD-3-Clause @@ -388,7 +388,6 @@ s32 ixgbe_update_mc_addr_list_vf(struct u32 mc_addr_count, ixgbe_mc_addr_itr next, bool clear) { - struct ixgbe_mbx_info *mbx = &hw->mbx; u32 msgbuf[IXGBE_VFMAILBOX_SIZE]; u16 *vector_list = (u16 *)&msgbuf[1]; u32 vector; @@ -419,8 +418,8 @@ s32 ixgbe_update_mc_addr_list_vf(struct DEBUGOUT1("Hash value = 0x%03X\n", vector); vector_list[i] = (u16)vector; } - - return mbx->ops.write_posted(hw, msgbuf, IXGBE_VFMAILBOX_SIZE, 0); + return ixgbevf_write_msg_read_ack(hw, msgbuf, msgbuf, + IXGBE_VFMAILBOX_SIZE); } /** Index: src/sys/dev/pci/ixgbe/ixgbe_x550.c diff -u src/sys/dev/pci/ixgbe/ixgbe_x550.c:1.5.6.5 src/sys/dev/pci/ixgbe/ixgbe_x550.c:1.5.6.6 --- src/sys/dev/pci/ixgbe/ixgbe_x550.c:1.5.6.5 Tue Aug 7 13:33:23 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_x550.c Mon Jul 22 17:53:35 2019 @@ -87,6 +87,7 @@ s32 ixgbe_init_ops_X550(struct ixgbe_hw mac->ops.enable_mdd = ixgbe_enable_mdd_X550; mac->ops.mdd_event = ixgbe_mdd_event_X550; mac->ops.restore_mdd_vf = ixgbe_restore_mdd_vf_X550; + mac->ops.fw_recovery_mode = ixgbe_fw_recovery_mode_X550; mac->ops.disable_rx = ixgbe_disable_rx_x550; /* Manageability interface */ mac->ops.set_fw_drv_ver = ixgbe_set_fw_drv_ver_x550; @@ -446,7 +447,7 @@ static s32 ixgbe_identify_phy_x550em(str switch (hw->device_id) { case IXGBE_DEV_ID_X550EM_A_SFP: - return ixgbe_identify_module_generic(hw); + return ixgbe_identify_sfp_module_X550em(hw); case IXGBE_DEV_ID_X550EM_X_SFP: /* set up for CS4227 usage */ ixgbe_setup_mux_ctl(hw); @@ -454,7 +455,7 @@ static s32 ixgbe_identify_phy_x550em(str /* Fallthrough */ case IXGBE_DEV_ID_X550EM_A_SFP_N: - return ixgbe_identify_module_generic(hw); + return ixgbe_identify_sfp_module_X550em(hw); break; case IXGBE_DEV_ID_X550EM_X_KX4: hw->phy.type = ixgbe_phy_x550em_kx4; @@ -2083,7 +2084,14 @@ s32 ixgbe_get_link_capabilities_X550em(s else *speed = IXGBE_LINK_SPEED_10GB_FULL; } else { + *autoneg = TRUE; + switch (hw->phy.type) { + case ixgbe_phy_x550em_xfi: + *speed = IXGBE_LINK_SPEED_1GB_FULL | + IXGBE_LINK_SPEED_10GB_FULL; + *autoneg = FALSE; + break; case ixgbe_phy_ext_1g_t: case ixgbe_phy_sgmii: *speed = IXGBE_LINK_SPEED_1GB_FULL; @@ -2107,7 +2115,6 @@ s32 ixgbe_get_link_capabilities_X550em(s IXGBE_LINK_SPEED_1GB_FULL; break; } - *autoneg = TRUE; } return IXGBE_SUCCESS; @@ -4817,3 +4824,19 @@ s32 ixgbe_set_fw_drv_ver_x550(struct ixg return ret_val; } + +/** + * ixgbe_fw_recovery_mode_X550 - Check FW NVM recovery mode + * @hw: pointer t hardware structure + * + * Returns TRUE if in FW NVM recovery mode. + **/ +bool ixgbe_fw_recovery_mode_X550(struct ixgbe_hw *hw) +{ + u32 fwsm; + + fwsm = IXGBE_READ_REG(hw, IXGBE_FWSM_BY_MAC(hw)); + + return !!(fwsm & IXGBE_FWSM_FW_NVM_RECOVERY_MODE); +} + Index: src/sys/dev/pci/ixgbe/ixgbe_x550.h diff -u src/sys/dev/pci/ixgbe/ixgbe_x550.h:1.2.12.2 src/sys/dev/pci/ixgbe/ixgbe_x550.h:1.2.12.3 --- src/sys/dev/pci/ixgbe/ixgbe_x550.h:1.2.12.2 Wed Apr 4 16:18:49 2018 +++ src/sys/dev/pci/ixgbe/ixgbe_x550.h Mon Jul 22 17:53:35 2019 @@ -119,4 +119,5 @@ s32 ixgbe_reset_phy_t_X550em(struct ixgb s32 ixgbe_identify_sfp_module_X550em(struct ixgbe_hw *hw); s32 ixgbe_led_on_t_X550em(struct ixgbe_hw *hw, u32 led_idx); s32 ixgbe_led_off_t_X550em(struct ixgbe_hw *hw, u32 led_idx); +bool ixgbe_fw_recovery_mode_X550(struct ixgbe_hw *hw); #endif /* _IXGBE_X550_H_ */ Index: src/sys/dev/pci/ixgbe/ixv.c diff -u src/sys/dev/pci/ixgbe/ixv.c:1.56.2.21 src/sys/dev/pci/ixgbe/ixv.c:1.56.2.22 --- src/sys/dev/pci/ixgbe/ixv.c:1.56.2.21 Mon Apr 1 12:35:38 2019 +++ src/sys/dev/pci/ixgbe/ixv.c Mon Jul 22 17:53:35 2019 @@ -1,4 +1,4 @@ -/*$NetBSD: ixv.c,v 1.56.2.21 2019/04/01 12:35:38 martin Exp $*/ +/*$NetBSD: ixv.c,v 1.56.2.22 2019/07/22 17:53:35 martin Exp $*/ /****************************************************************************** @@ -47,6 +47,7 @@ * Driver version ************************************************************************/ static const char ixv_driver_version[] = "2.0.1-k"; +/* XXX NetBSD: + 1.5.17 */ /************************************************************************ * PCI Device ID Table @@ -78,41 +79,41 @@ static const char *ixv_strings[] = { /********************************************************************* * Function prototypes *********************************************************************/ -static int ixv_probe(device_t, cfdata_t, void *); +static int ixv_probe(device_t, cfdata_t, void *); static void ixv_attach(device_t, device_t, void *); -static int ixv_detach(device_t, int); +static int ixv_detach(device_t, int); #if 0 -static int ixv_shutdown(device_t); +static int ixv_shutdown(device_t); #endif static int ixv_ifflags_cb(struct ethercom *); -static int ixv_ioctl(struct ifnet *, u_long, void *); +static int ixv_ioctl(struct ifnet *, u_long, void *); static int ixv_init(struct ifnet *); static void ixv_init_locked(struct adapter *); static void ixv_ifstop(struct ifnet *, int); -static void ixv_stop(void *); -static void ixv_init_device_features(struct adapter *); -static void ixv_media_status(struct ifnet *, struct ifmediareq *); -static int ixv_media_change(struct ifnet *); -static int ixv_allocate_pci_resources(struct adapter *, +static void ixv_stop(void *); +static void ixv_init_device_features(struct adapter *); +static void ixv_media_status(struct ifnet *, struct ifmediareq *); +static int ixv_media_change(struct ifnet *); +static int ixv_allocate_pci_resources(struct adapter *, const struct pci_attach_args *); -static int ixv_allocate_msix(struct adapter *, +static int ixv_allocate_msix(struct adapter *, const struct pci_attach_args *); -static int ixv_configure_interrupts(struct adapter *); +static int ixv_configure_interrupts(struct adapter *); static void ixv_free_pci_resources(struct adapter *); -static void ixv_local_timer(void *); -static void ixv_local_timer_locked(void *); -static int ixv_setup_interface(device_t, struct adapter *); -static int ixv_negotiate_api(struct adapter *); - -static void ixv_initialize_transmit_units(struct adapter *); -static void ixv_initialize_receive_units(struct adapter *); -static void ixv_initialize_rss_mapping(struct adapter *); -static void ixv_check_link(struct adapter *); - -static void ixv_enable_intr(struct adapter *); -static void ixv_disable_intr(struct adapter *); -static void ixv_set_multi(struct adapter *); -static void ixv_update_link_status(struct adapter *); +static void ixv_local_timer(void *); +static void ixv_local_timer_locked(void *); +static int ixv_setup_interface(device_t, struct adapter *); +static int ixv_negotiate_api(struct adapter *); + +static void ixv_initialize_transmit_units(struct adapter *); +static void ixv_initialize_receive_units(struct adapter *); +static void ixv_initialize_rss_mapping(struct adapter *); +static s32 ixv_check_link(struct adapter *); + +static void ixv_enable_intr(struct adapter *); +static void ixv_disable_intr(struct adapter *); +static void ixv_set_multi(struct adapter *); +static void ixv_update_link_status(struct adapter *); static int ixv_sysctl_debug(SYSCTLFN_PROTO); static void ixv_set_ivar(struct adapter *, u8, u8, s8); static void ixv_configure_ivars(struct adapter *); @@ -131,16 +132,15 @@ static void ixv_init_stats(struct adapte static void ixv_update_stats(struct adapter *); static void ixv_add_stats_sysctls(struct adapter *); - /* Sysctl handlers */ static void ixv_set_sysctl_value(struct adapter *, const char *, const char *, int *, int); -static int ixv_sysctl_interrupt_rate_handler(SYSCTLFN_PROTO); -static int ixv_sysctl_next_to_check_handler(SYSCTLFN_PROTO); -static int ixv_sysctl_rdh_handler(SYSCTLFN_PROTO); -static int ixv_sysctl_rdt_handler(SYSCTLFN_PROTO); -static int ixv_sysctl_tdt_handler(SYSCTLFN_PROTO); -static int ixv_sysctl_tdh_handler(SYSCTLFN_PROTO); +static int ixv_sysctl_interrupt_rate_handler(SYSCTLFN_PROTO); +static int ixv_sysctl_next_to_check_handler(SYSCTLFN_PROTO); +static int ixv_sysctl_rdh_handler(SYSCTLFN_PROTO); +static int ixv_sysctl_rdt_handler(SYSCTLFN_PROTO); +static int ixv_sysctl_tdt_handler(SYSCTLFN_PROTO); +static int ixv_sysctl_tdh_handler(SYSCTLFN_PROTO); /* The MSI-X Interrupt handlers */ static int ixv_msix_que(void *); @@ -148,7 +148,7 @@ static int ixv_msix_mbx(void *); /* Deferred interrupt tasklets */ static void ixv_handle_que(void *); -static void ixv_handle_link(void *); +static void ixv_handle_link(void *); /* Workqueue handler for deferred work */ static void ixv_handle_que_work(struct work *, void *); @@ -203,7 +203,7 @@ TUNABLE_INT("hw.ixv.rx_process_limit", & static int ixv_tx_process_limit = 256; TUNABLE_INT("hw.ixv.tx_process_limit", &ixv_tx_process_limit); -/* Which pakcet processing uses workqueue or softint */ +/* Which packet processing uses workqueue or softint */ static bool ixv_txrx_workqueue = false; /* @@ -307,7 +307,7 @@ ixv_attach(device_t parent, device_t dev { struct adapter *adapter; struct ixgbe_hw *hw; - int error = 0; + int error = 0; pcireg_t id, subid; const ixgbe_vendor_info_t *ent; const struct pci_attach_args *pa = aux; @@ -580,7 +580,7 @@ err_out: static int ixv_detach(device_t dev, int flags) { - struct adapter *adapter = device_private(dev); + struct adapter *adapter = device_private(dev); struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que = adapter->queues; struct tx_ring *txr = adapter->tx_rings; @@ -597,8 +597,8 @@ ixv_detach(device_t dev, int flags) #if NVLAN > 0 /* Make sure VLANs are not using driver */ if (!VLAN_ATTACHED(&adapter->osdep.ec)) - ; /* nothing to do: no VLANs */ - else if ((flags & (DETACH_SHUTDOWN|DETACH_FORCE)) != 0) + ; /* nothing to do: no VLANs */ + else if ((flags & (DETACH_SHUTDOWN | DETACH_FORCE)) != 0) vlan_ifdetach(adapter->ifp); else { aprint_error_dev(dev, "VLANs in use, detach first\n"); @@ -724,10 +724,10 @@ static void ixv_init_locked(struct adapter *adapter) { struct ifnet *ifp = adapter->ifp; - device_t dev = adapter->dev; + device_t dev = adapter->dev; struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que; - int error = 0; + int error = 0; uint32_t mask; int i; @@ -798,7 +798,7 @@ ixv_init_locked(struct adapter *adapter) #endif } #endif - + /* Set up VLAN offload and filter */ ixv_setup_vlan_support(adapter); @@ -846,8 +846,8 @@ ixv_enable_queue(struct adapter *adapter { struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que = &adapter->queues[vector]; - u32 queue = 1 << vector; - u32 mask; + u32 queue = 1 << vector; + u32 mask; mutex_enter(&que->dc_mtx); if (que->disabled_count > 0 && --que->disabled_count > 0) @@ -867,8 +867,8 @@ ixv_disable_queue(struct adapter *adapte { struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que = &adapter->queues[vector]; - u64 queue = (u64)(1 << vector); - u32 mask; + u64 queue = (u64)(1 << vector); + u32 mask; mutex_enter(&que->dc_mtx); if (que->disabled_count++ > 0) @@ -895,7 +895,7 @@ static int ixv_msix_que(void *arg) { struct ix_queue *que = arg; - struct adapter *adapter = que->adapter; + struct adapter *adapter = que->adapter; struct tx_ring *txr = que->txr; struct rx_ring *rxr = que->rxr; bool more; @@ -1105,10 +1105,10 @@ static int ixv_negotiate_api(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - int mbx_api[] = { ixgbe_mbox_api_11, - ixgbe_mbox_api_10, - ixgbe_mbox_api_unknown }; - int i = 0; + int mbx_api[] = { ixgbe_mbox_api_11, + ixgbe_mbox_api_10, + ixgbe_mbox_api_unknown }; + int i = 0; while (mbx_api[i] != ixgbe_mbox_api_unknown) { if (ixgbevf_negotiate_api_version(hw, mbx_api[i]) == 0) @@ -1132,8 +1132,8 @@ ixv_set_multi(struct adapter *adapter) struct ether_multistep step; struct ethercom *ec = &adapter->osdep.ec; u8 mta[MAX_NUM_MULTICAST_ADDRESSES * IXGBE_ETH_LENGTH_OF_ADDRESS]; - u8 *update_ptr; - int mcnt = 0; + u8 *update_ptr; + int mcnt = 0; KASSERT(mutex_owned(&adapter->core_mtx)); IOCTL_DEBUGOUT("ixv_set_multi: begin"); @@ -1208,7 +1208,10 @@ ixv_local_timer_locked(void *arg) KASSERT(mutex_owned(&adapter->core_mtx)); - ixv_check_link(adapter); + if (ixv_check_link(adapter)) { + ixv_init_locked(adapter); + return; + } /* Stats Update */ ixv_update_stats(adapter); @@ -1217,7 +1220,7 @@ ixv_local_timer_locked(void *arg) v0 = v1 = v2 = v3 = v4 = v5 = v6 = v7 = 0; que = adapter->queues; for (i = 0; i < adapter->num_queues; i++, que++) { - struct tx_ring *txr = que->txr; + struct tx_ring *txr = que->txr; v0 += txr->q_efbig_tx_dma_setup; v1 += txr->q_mbuf_defrag_failed; @@ -1239,8 +1242,8 @@ ixv_local_timer_locked(void *arg) /* * Check the TX queues status - * - mark hung queues so we don't schedule on them - * - watchdog only if all queues show hung + * - mark hung queues so we don't schedule on them + * - watchdog only if all queues show hung */ que = adapter->queues; for (i = 0; i < adapter->num_queues; i++, que++) { @@ -1295,8 +1298,8 @@ watchdog: * ixv_update_link_status - Update OS on link state * * Note: Only updates the OS on the cached link state. - * The real check of the hardware only happens with - * a link interrupt. + * The real check of the hardware only happens with + * a link interrupt. ************************************************************************/ static void ixv_update_link_status(struct adapter *adapter) @@ -1344,7 +1347,7 @@ ixv_update_link_status(struct adapter *a /* * Do it when link active changes to DOWN. i.e. * a) LINK_STATE_UNKNOWN -> LINK_STATE_DOWN - * b) LINK_STATE_UP -> LINK_STATE_DOWN + * b) LINK_STATE_UP -> LINK_STATE_DOWN */ if (adapter->link_active != LINK_STATE_DOWN) { if (bootverbose) @@ -1375,8 +1378,8 @@ ixv_ifstop(struct ifnet *ifp, int disabl static void ixv_stop(void *arg) { - struct ifnet *ifp; - struct adapter *adapter = arg; + struct ifnet *ifp; + struct adapter *adapter = arg; struct ixgbe_hw *hw = &adapter->hw; ifp = adapter->ifp; @@ -1409,7 +1412,7 @@ ixv_allocate_pci_resources(struct adapte const struct pci_attach_args *pa) { pcireg_t memtype, csr; - device_t dev = adapter->dev; + device_t dev = adapter->dev; bus_addr_t addr; int flags; @@ -1419,7 +1422,7 @@ ixv_allocate_pci_resources(struct adapte case PCI_MAPREG_TYPE_MEM | PCI_MAPREG_MEM_TYPE_64BIT: adapter->osdep.mem_bus_space_tag = pa->pa_memt; if (pci_mapreg_info(pa->pa_pc, pa->pa_tag, PCI_BAR(0), - memtype, &addr, &adapter->osdep.mem_size, &flags) != 0) + memtype, &addr, &adapter->osdep.mem_size, &flags) != 0) goto map_err; if ((flags & BUS_SPACE_MAP_PREFETCHABLE) != 0) { aprint_normal_dev(dev, "clearing prefetchable bit\n"); @@ -1460,7 +1463,7 @@ map_err: static void ixv_free_pci_resources(struct adapter * adapter) { - struct ix_queue *que = adapter->queues; + struct ix_queue *que = adapter->queues; int rid; /* @@ -1555,8 +1558,8 @@ ixv_setup_interface(device_t dev, struct /* Set capability flags */ ifp->if_capabilities |= IFCAP_HWCSUM - | IFCAP_TSOv4 - | IFCAP_TSOv6; + | IFCAP_TSOv4 + | IFCAP_TSOv6; ifp->if_capenable = 0; ec->ec_capabilities |= ETHERCAP_VLAN_HWTAGGING @@ -1644,10 +1647,10 @@ static void ixv_initialize_rss_mapping(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; - u32 reta = 0, mrqc, rss_key[10]; - int queue_id; - int i, j; - u32 rss_hash_config; + u32 reta = 0, mrqc, rss_key[10]; + int queue_id; + int i, j; + u32 rss_hash_config; /* force use default RSS key. */ #ifdef __NetBSD__ @@ -1704,9 +1707,9 @@ ixv_initialize_rss_mapping(struct adapte * traffic. */ rss_hash_config = RSS_HASHTYPE_RSS_IPV4 - | RSS_HASHTYPE_RSS_TCP_IPV4 - | RSS_HASHTYPE_RSS_IPV6 - | RSS_HASHTYPE_RSS_TCP_IPV6; + | RSS_HASHTYPE_RSS_TCP_IPV4 + | RSS_HASHTYPE_RSS_IPV6 + | RSS_HASHTYPE_RSS_TCP_IPV6; } mrqc = IXGBE_MRQC_RSSEN; @@ -1744,7 +1747,7 @@ ixv_initialize_receive_units(struct adap struct rx_ring *rxr = adapter->rx_rings; struct ixgbe_hw *hw = &adapter->hw; struct ifnet *ifp = adapter->ifp; - u32 bufsz, rxcsum, psrtype; + u32 bufsz, psrtype; if (ifp->if_mtu > ETHERMTU) bufsz = 4096 >> IXGBE_SRRCTL_BSIZEPKT_SHIFT; @@ -1752,10 +1755,10 @@ ixv_initialize_receive_units(struct adap bufsz = 2048 >> IXGBE_SRRCTL_BSIZEPKT_SHIFT; psrtype = IXGBE_PSRTYPE_TCPHDR - | IXGBE_PSRTYPE_UDPHDR - | IXGBE_PSRTYPE_IPV4HDR - | IXGBE_PSRTYPE_IPV6HDR - | IXGBE_PSRTYPE_L2HDR; + | IXGBE_PSRTYPE_UDPHDR + | IXGBE_PSRTYPE_IPV4HDR + | IXGBE_PSRTYPE_IPV6HDR + | IXGBE_PSRTYPE_L2HDR; if (adapter->num_queues > 1) psrtype |= 1 << 29; @@ -1838,7 +1841,7 @@ ixv_initialize_receive_units(struct adap if ((adapter->feat_en & IXGBE_FEATURE_NETMAP) && (ifp->if_capenable & IFCAP_NETMAP)) { struct netmap_adapter *na = NA(adapter->ifp); - struct netmap_kring *kring = &na->rx_rings[i]; + struct netmap_kring *kring = na->rx_rings[i]; int t = na->num_rx_desc - 1 - nm_kr_rxspace(kring); IXGBE_WRITE_REG(hw, IXGBE_VFRDT(rxr->me), t); @@ -1848,22 +1851,7 @@ ixv_initialize_receive_units(struct adap adapter->num_rx_desc - 1); } - rxcsum = IXGBE_READ_REG(hw, IXGBE_RXCSUM); - ixv_initialize_rss_mapping(adapter); - - if (adapter->num_queues > 1) { - /* RSS and RX IPP Checksum are mutually exclusive */ - rxcsum |= IXGBE_RXCSUM_PCSD; - } - - if (ifp->if_capenable & IFCAP_RXCSUM) - rxcsum |= IXGBE_RXCSUM_PCSD; - - if (!(rxcsum & IXGBE_RXCSUM_PCSD)) - rxcsum |= IXGBE_RXCSUM_IPPCSE; - - IXGBE_WRITE_REG(hw, IXGBE_RXCSUM, rxcsum); } /* ixv_initialize_receive_units */ /************************************************************************ @@ -1871,7 +1859,7 @@ ixv_initialize_receive_units(struct adap * * Retrieves the TDH value from the hardware ************************************************************************/ -static int +static int ixv_sysctl_tdh_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; @@ -1891,7 +1879,7 @@ ixv_sysctl_tdh_handler(SYSCTLFN_ARGS) * * Retrieves the TDT value from the hardware ************************************************************************/ -static int +static int ixv_sysctl_tdt_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; @@ -1912,7 +1900,7 @@ ixv_sysctl_tdt_handler(SYSCTLFN_ARGS) * * Retrieves the next_to_check value ************************************************************************/ -static int +static int ixv_sysctl_next_to_check_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; @@ -1932,7 +1920,7 @@ ixv_sysctl_next_to_check_handler(SYSCTLF * * Retrieves the RDH value from the hardware ************************************************************************/ -static int +static int ixv_sysctl_rdh_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; @@ -1952,7 +1940,7 @@ ixv_sysctl_rdh_handler(SYSCTLFN_ARGS) * * Retrieves the RDT value from the hardware ************************************************************************/ -static int +static int ixv_sysctl_rdt_handler(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; @@ -2097,7 +2085,7 @@ ixv_enable_intr(struct adapter *adapter) { struct ixgbe_hw *hw = &adapter->hw; struct ix_queue *que = adapter->queues; - u32 mask; + u32 mask; int i; /* For VTEIAC */ @@ -2146,7 +2134,7 @@ static void ixv_set_ivar(struct adapter *adapter, u8 entry, u8 vector, s8 type) { struct ixgbe_hw *hw = &adapter->hw; - u32 ivar, index; + u32 ivar, index; vector |= IXGBE_IVAR_ALLOC_VAL; @@ -2155,7 +2143,7 @@ ixv_set_ivar(struct adapter *adapter, u8 ivar &= ~0xFF; ivar |= vector; IXGBE_WRITE_REG(hw, IXGBE_VTIVAR_MISC, ivar); - } else { /* RX/TX IVARS */ + } else { /* RX/TX IVARS */ index = (16 * (entry & 1)) + (8 * type); ivar = IXGBE_READ_REG(hw, IXGBE_VTIVAR(entry >> 1)); ivar &= ~(0xFF << index); @@ -2243,7 +2231,7 @@ ixv_init_stats(struct adapter *adapter) } /* ixv_init_stats */ #define UPDATE_STAT_32(reg, last, count) \ -{ \ +{ \ u32 current = IXGBE_READ_REG(hw, (reg)); \ if (current < (last)) \ count.ev_count += 0x100000000LL; \ @@ -2252,11 +2240,11 @@ ixv_init_stats(struct adapter *adapter) count.ev_count |= current; \ } -#define UPDATE_STAT_36(lsb, msb, last, count) \ -{ \ +#define UPDATE_STAT_36(lsb, msb, last, count) \ +{ \ u64 cur_lsb = IXGBE_READ_REG(hw, (lsb)); \ u64 cur_msb = IXGBE_READ_REG(hw, (msb)); \ - u64 current = ((cur_msb << 32) | cur_lsb); \ + u64 current = ((cur_msb << 32) | cur_lsb); \ if (current < (last)) \ count.ev_count += 0x1000000000LL; \ (last) = current; \ @@ -2297,7 +2285,7 @@ ixv_sysctl_interrupt_rate_handler(SYSCTL { struct sysctlnode node = *rnode; struct ix_queue *que = (struct ix_queue *)node.sysctl_data; - struct adapter *adapter = que->adapter; + struct adapter *adapter = que->adapter; uint32_t reg, usec, rate; int error; @@ -2401,9 +2389,9 @@ ixv_add_device_sysctls(struct adapter *a static void ixv_add_stats_sysctls(struct adapter *adapter) { - device_t dev = adapter->dev; - struct tx_ring *txr = adapter->tx_rings; - struct rx_ring *rxr = adapter->rx_rings; + device_t dev = adapter->dev; + struct tx_ring *txr = adapter->tx_rings; + struct rx_ring *rxr = adapter->rx_rings; struct ixgbevf_hw_stats *stats = &adapter->stats.vf; struct ixgbe_hw *hw = &adapter->hw; const struct sysctlnode *rnode, *cnode; @@ -2587,7 +2575,7 @@ static void ixv_set_sysctl_value(struct adapter *adapter, const char *name, const char *description, int *limit, int value) { - device_t dev = adapter->dev; + device_t dev = adapter->dev; struct sysctllog **log; const struct sysctlnode *rnode, *cnode; @@ -2614,18 +2602,14 @@ ixv_set_sysctl_value(struct adapter *ada static void ixv_print_debug_info(struct adapter *adapter) { - device_t dev = adapter->dev; - struct ixgbe_hw *hw = &adapter->hw; - struct ix_queue *que = adapter->queues; - struct rx_ring *rxr; - struct tx_ring *txr; + device_t dev = adapter->dev; + struct ix_queue *que = adapter->queues; + struct rx_ring *rxr; + struct tx_ring *txr; #ifdef LRO - struct lro_ctrl *lro; + struct lro_ctrl *lro; #endif /* LRO */ - device_printf(dev, "Error Byte Count = %u \n", - IXGBE_READ_REG(hw, IXGBE_ERRBC)); - for (int i = 0; i < adapter->num_queues; i++, que++) { txr = que->txr; rxr = que->rxr; @@ -2639,10 +2623,10 @@ ixv_print_debug_info(struct adapter *ada device_printf(dev, "RX(%d) Bytes Received: %lu\n", rxr->me, (long)rxr->rx_bytes.ev_count); #ifdef LRO - device_printf(dev, "RX(%d) LRO Queued= %lld\n", - rxr->me, (long long)lro->lro_queued); - device_printf(dev, "RX(%d) LRO Flushed= %lld\n", - rxr->me, (long long)lro->lro_flushed); + device_printf(dev, "RX(%d) LRO Queued= %ju\n", + rxr->me, (uintmax_t)lro->lro_queued); + device_printf(dev, "RX(%d) LRO Flushed= %ju\n", + rxr->me, (uintmax_t)lro->lro_flushed); #endif /* LRO */ device_printf(dev, "TX(%d) Packets Sent: %lu\n", txr->me, (long)txr->total_packets.ev_count); @@ -2662,7 +2646,7 @@ ixv_sysctl_debug(SYSCTLFN_ARGS) { struct sysctlnode node = *rnode; struct adapter *adapter = (struct adapter *)node.sysctl_data; - int error, result; + int error, result; node.sysctl_data = &result; error = sysctl_lookup(SYSCTLFN_CALL(&node)); @@ -2683,9 +2667,9 @@ static void ixv_init_device_features(struct adapter *adapter) { adapter->feat_cap = IXGBE_FEATURE_NETMAP - | IXGBE_FEATURE_VF - | IXGBE_FEATURE_RSS - | IXGBE_FEATURE_LEGACY_TX; + | IXGBE_FEATURE_VF + | IXGBE_FEATURE_RSS + | IXGBE_FEATURE_LEGACY_TX; /* A tad short on feature flags for VFs, atm. */ switch (adapter->hw.mac.type) { @@ -2774,10 +2758,10 @@ ixv_ioctl(struct ifnet *ifp, u_long comm struct adapter *adapter = ifp->if_softc; struct ifcapreq *ifcr = data; struct ifreq *ifr = data; - int error = 0; + int error = 0; int l4csum_en; - const int l4csum = IFCAP_CSUM_TCPv4_Rx|IFCAP_CSUM_UDPv4_Rx| - IFCAP_CSUM_TCPv6_Rx|IFCAP_CSUM_UDPv6_Rx; + const int l4csum = IFCAP_CSUM_TCPv4_Rx | IFCAP_CSUM_UDPv4_Rx | + IFCAP_CSUM_TCPv6_Rx | IFCAP_CSUM_UDPv6_Rx; switch (command) { case SIOCSIFFLAGS: @@ -2864,9 +2848,9 @@ static void ixv_handle_que(void *context) { struct ix_queue *que = context; - struct adapter *adapter = que->adapter; + struct adapter *adapter = que->adapter; struct tx_ring *txr = que->txr; - struct ifnet *ifp = adapter->ifp; + struct ifnet *ifp = adapter->ifp; bool more; que->handleq.ev_count++; @@ -2929,7 +2913,7 @@ ixv_allocate_msix(struct adapter *adapte device_t dev = adapter->dev; struct ix_queue *que = adapter->queues; struct tx_ring *txr = adapter->tx_rings; - int error, msix_ctrl, rid, vector = 0; + int error, msix_ctrl, rid, vector = 0; pci_chipset_tag_t pc; pcitag_t tag; char intrbuf[PCI_INTRSTR_LEN]; @@ -2973,7 +2957,7 @@ ixv_allocate_msix(struct adapter *adapte return (ENXIO); } que->msix = vector; - adapter->active_queues |= (u64)(1 << que->msix); + adapter->active_queues |= (u64)(1 << que->msix); cpu_id = i; /* Round-robin affinity */ @@ -2999,7 +2983,7 @@ ixv_allocate_msix(struct adapter *adapte ixv_handle_que, que); if (que->que_si == NULL) { aprint_error_dev(dev, - "could not establish software interrupt\n"); + "could not establish software interrupt\n"); } } snprintf(wqname, sizeof(wqname), "%sdeferTx", device_xname(dev)); @@ -3042,7 +3026,8 @@ ixv_allocate_msix(struct adapter *adapte /* Round-robin affinity */ kcpuset_zero(affinity); kcpuset_set(affinity, cpu_id % ncpu); - error = interrupt_distribute(adapter->osdep.ihs[vector], affinity,NULL); + error = interrupt_distribute(adapter->osdep.ihs[vector], + affinity, NULL); aprint_normal_dev(dev, "for link, interrupting at %s", intrstr); @@ -3108,7 +3093,7 @@ ixv_configure_interrupts(struct adapter if (msgs >= want) msgs = want; else { - aprint_error_dev(dev, + aprint_error_dev(dev, "MSI-X Configuration Problem, " "%d vectors but %d queues wanted!\n", msgs, want); @@ -3146,15 +3131,18 @@ ixv_handle_link(void *context) /************************************************************************ * ixv_check_link - Used in the local timer to poll for link changes ************************************************************************/ -static void +static s32 ixv_check_link(struct adapter *adapter) { + s32 error; KASSERT(mutex_owned(&adapter->core_mtx)); adapter->hw.mac.get_link_status = TRUE; - adapter->hw.mac.ops.check_link(&adapter->hw, &adapter->link_speed, - &adapter->link_up, FALSE); + error = adapter->hw.mac.ops.check_link(&adapter->hw, + &adapter->link_speed, &adapter->link_up, FALSE); ixv_update_link_status(adapter); + + return error; } /* ixv_check_link */