1/******************************************************************************
2
3  Copyright (c) 2013-2019, Intel Corporation
4  All rights reserved.
5
6  Redistribution and use in source and binary forms, with or without
7  modification, are permitted provided that the following conditions are met:
8
9   1. Redistributions of source code must retain the above copyright notice,
10      this list of conditions and the following disclaimer.
11
12   2. Redistributions in binary form must reproduce the above copyright
13      notice, this list of conditions and the following disclaimer in the
14      documentation and/or other materials provided with the distribution.
15
16   3. Neither the name of the Intel Corporation nor the names of its
17      contributors may be used to endorse or promote products derived from
18      this software without specific prior written permission.
19
20  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
24  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
25  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
26  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
29  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
30  POSSIBILITY OF SUCH DAMAGE.
31
32******************************************************************************/
33/*$FreeBSD: stable/11/sys/dev/ixl/ixl_pf_main.c 369202 2021-02-02 14:27:33Z donner $*/
34
35
36#include "ixl_pf.h"
37
38#ifdef PCI_IOV
39#include "ixl_pf_iov.h"
40#endif
41
42#ifdef IXL_IW
43#include "ixl_iw.h"
44#include "ixl_iw_int.h"
45#endif
46
47#ifdef DEV_NETMAP
48#include <dev/netmap/if_ixl_netmap.h>
49#endif /* DEV_NETMAP */
50
51static int	ixl_vsi_setup_queue(struct ixl_vsi *, struct ixl_queue *, int);
52static u64	ixl_max_aq_speed_to_value(u8);
53static u8	ixl_convert_sysctl_aq_link_speed(u8, bool);
54static void	ixl_sbuf_print_bytes(struct sbuf *, u8 *, int, int, bool);
55static enum i40e_status_code ixl_set_lla(struct ixl_vsi *);
56static const char * ixl_link_speed_string(u8 link_speed);
57
58
59/* Sysctls */
60static int	ixl_sysctl_set_flowcntl(SYSCTL_HANDLER_ARGS);
61static int	ixl_sysctl_set_advertise(SYSCTL_HANDLER_ARGS);
62static int	ixl_sysctl_supported_speeds(SYSCTL_HANDLER_ARGS);
63static int	ixl_sysctl_current_speed(SYSCTL_HANDLER_ARGS);
64static int	ixl_sysctl_show_fw(SYSCTL_HANDLER_ARGS);
65static int	ixl_sysctl_unallocated_queues(SYSCTL_HANDLER_ARGS);
66static int	ixl_sysctl_pf_tx_itr(SYSCTL_HANDLER_ARGS);
67static int	ixl_sysctl_pf_rx_itr(SYSCTL_HANDLER_ARGS);
68static int	ixl_sysctl_eee_enable(SYSCTL_HANDLER_ARGS);
69
70/* Debug Sysctls */
71static int 	ixl_sysctl_link_status(SYSCTL_HANDLER_ARGS);
72static int	ixl_sysctl_phy_abilities(SYSCTL_HANDLER_ARGS);
73static int	ixl_sysctl_sw_filter_list(SYSCTL_HANDLER_ARGS);
74static int	ixl_sysctl_hw_res_alloc(SYSCTL_HANDLER_ARGS);
75static int	ixl_sysctl_switch_config(SYSCTL_HANDLER_ARGS);
76static int	ixl_sysctl_switch_vlans(SYSCTL_HANDLER_ARGS);
77static int	ixl_sysctl_hkey(SYSCTL_HANDLER_ARGS);
78static int	ixl_sysctl_hena(SYSCTL_HANDLER_ARGS);
79static int	ixl_sysctl_hlut(SYSCTL_HANDLER_ARGS);
80static int	ixl_sysctl_fw_link_management(SYSCTL_HANDLER_ARGS);
81static int	ixl_sysctl_read_i2c_byte(SYSCTL_HANDLER_ARGS);
82static int	ixl_sysctl_write_i2c_byte(SYSCTL_HANDLER_ARGS);
83static int	ixl_sysctl_fec_fc_ability(SYSCTL_HANDLER_ARGS);
84static int	ixl_sysctl_fec_rs_ability(SYSCTL_HANDLER_ARGS);
85static int	ixl_sysctl_fec_fc_request(SYSCTL_HANDLER_ARGS);
86static int	ixl_sysctl_fec_rs_request(SYSCTL_HANDLER_ARGS);
87static int	ixl_sysctl_fec_auto_enable(SYSCTL_HANDLER_ARGS);
88static int	ixl_sysctl_dump_debug_data(SYSCTL_HANDLER_ARGS);
89static int	ixl_sysctl_fw_lldp(SYSCTL_HANDLER_ARGS);
90static int	ixl_sysctl_read_i2c_diag_data(SYSCTL_HANDLER_ARGS);
91
92
93#ifdef IXL_IW
94extern int ixl_enable_iwarp;
95extern int ixl_limit_iwarp_msix;
96#endif
97
98const uint8_t ixl_bcast_addr[ETHER_ADDR_LEN] =
99    {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
100
101const char * const ixl_fc_string[6] = {
102	"None",
103	"Rx",
104	"Tx",
105	"Full",
106	"Priority",
107	"Default"
108};
109
110static char *ixl_fec_string[3] = {
111       "CL108 RS-FEC",
112       "CL74 FC-FEC/BASE-R",
113       "None"
114};
115
116MALLOC_DEFINE(M_IXL, "ixl", "ixl driver allocations");
117
118void
119ixl_debug_core(struct ixl_pf *pf, enum ixl_dbg_mask mask, char *fmt, ...)
120{
121	va_list args;
122
123	if (!(mask & pf->dbg_mask))
124		return;
125
126	/* Re-implement device_printf() */
127	device_print_prettyname(pf->dev);
128	va_start(args, fmt);
129	vprintf(fmt, args);
130	va_end(args);
131}
132
133/*
134** Put the FW, API, NVM, EEtrackID, and OEM version information into a string
135*/
136void
137ixl_nvm_version_str(struct i40e_hw *hw, struct sbuf *buf)
138{
139	u8 oem_ver = (u8)(hw->nvm.oem_ver >> 24);
140	u16 oem_build = (u16)((hw->nvm.oem_ver >> 16) & 0xFFFF);
141	u8 oem_patch = (u8)(hw->nvm.oem_ver & 0xFF);
142
143	sbuf_printf(buf,
144	    "fw %d.%d.%05d api %d.%d nvm %x.%02x etid %08x oem %d.%d.%d",
145	    hw->aq.fw_maj_ver, hw->aq.fw_min_ver, hw->aq.fw_build,
146	    hw->aq.api_maj_ver, hw->aq.api_min_ver,
147	    (hw->nvm.version & IXL_NVM_VERSION_HI_MASK) >>
148	    IXL_NVM_VERSION_HI_SHIFT,
149	    (hw->nvm.version & IXL_NVM_VERSION_LO_MASK) >>
150	    IXL_NVM_VERSION_LO_SHIFT,
151	    hw->nvm.eetrack,
152	    oem_ver, oem_build, oem_patch);
153}
154
155void
156ixl_print_nvm_version(struct ixl_pf *pf)
157{
158	struct i40e_hw *hw = &pf->hw;
159	device_t dev = pf->dev;
160	struct sbuf *sbuf;
161
162	sbuf = sbuf_new_auto();
163	ixl_nvm_version_str(hw, sbuf);
164	sbuf_finish(sbuf);
165	device_printf(dev, "%s\n", sbuf_data(sbuf));
166	sbuf_delete(sbuf);
167}
168
169bool
170ixl_fw_recovery_mode(struct ixl_pf *pf)
171{
172	return (rd32(&pf->hw, I40E_GL_FWSTS) & I40E_GL_FWSTS_FWS1B_MASK);
173}
174
175static void
176ixl_configure_tx_itr(struct ixl_pf *pf)
177{
178	struct i40e_hw		*hw = &pf->hw;
179	struct ixl_vsi		*vsi = &pf->vsi;
180	struct ixl_queue	*que = vsi->queues;
181
182	vsi->tx_itr_setting = pf->tx_itr;
183
184	for (int i = 0; i < vsi->num_queues; i++, que++) {
185		struct tx_ring	*txr = &que->txr;
186
187		wr32(hw, I40E_PFINT_ITRN(IXL_TX_ITR, i),
188		    vsi->tx_itr_setting);
189		txr->itr = vsi->tx_itr_setting;
190		txr->latency = IXL_AVE_LATENCY;
191	}
192}
193
194static void
195ixl_configure_rx_itr(struct ixl_pf *pf)
196{
197	struct i40e_hw		*hw = &pf->hw;
198	struct ixl_vsi		*vsi = &pf->vsi;
199	struct ixl_queue	*que = vsi->queues;
200
201	vsi->rx_itr_setting = pf->rx_itr;
202
203	for (int i = 0; i < vsi->num_queues; i++, que++) {
204		struct rx_ring 	*rxr = &que->rxr;
205
206		wr32(hw, I40E_PFINT_ITRN(IXL_RX_ITR, i),
207		    vsi->rx_itr_setting);
208		rxr->itr = vsi->rx_itr_setting;
209		rxr->latency = IXL_AVE_LATENCY;
210	}
211}
212
213/*
214 * Write PF ITR values to queue ITR registers.
215 */
216void
217ixl_configure_itr(struct ixl_pf *pf)
218{
219	ixl_configure_tx_itr(pf);
220	ixl_configure_rx_itr(pf);
221}
222
223/*********************************************************************
224 *  Init entry point
225 *
226 *  This routine is used in two ways. It is used by the stack as
227 *  init entry point in network interface structure. It is also used
228 *  by the driver as a hw/sw initialization routine to get to a
229 *  consistent state.
230 *
231 *  return 0 on success, positive on failure
232 **********************************************************************/
233void
234ixl_init_locked(struct ixl_pf *pf)
235{
236	struct i40e_hw	*hw = &pf->hw;
237	struct ixl_vsi	*vsi = &pf->vsi;
238	struct ifnet	*ifp = vsi->ifp;
239	device_t 	dev = pf->dev;
240	struct i40e_filter_control_settings	filter;
241
242	INIT_DEBUGOUT("ixl_init_locked: begin");
243	IXL_PF_LOCK_ASSERT(pf);
244
245	if ((pf->state & IXL_PF_STATE_RECOVERY_MODE) != 0) {
246		device_printf(dev, "Running in recovery mode, only firmware update available\n");
247		return;
248	}
249
250	ixl_stop_locked(pf);
251
252	/*
253	 * If the aq is dead here, it probably means something outside of the driver
254	 * did something to the adapter, like a PF reset.
255	 * So rebuild the driver's state here if that occurs.
256	 */
257	if (!i40e_check_asq_alive(&pf->hw)) {
258		device_printf(dev, "Admin Queue is down; resetting...\n");
259		ixl_teardown_hw_structs(pf);
260		ixl_reset(pf);
261	}
262
263	/* Get the latest mac address... User might use a LAA */
264	if (ixl_set_lla(vsi)) {
265		device_printf(dev, "LLA address change failed!\n");
266		return;
267	}
268
269	/* Set the various hardware offload abilities */
270	ifp->if_hwassist = 0;
271	if (ifp->if_capenable & IFCAP_TSO)
272		ifp->if_hwassist |= CSUM_TSO;
273	if (ifp->if_capenable & IFCAP_TXCSUM)
274		ifp->if_hwassist |= (CSUM_TCP | CSUM_UDP);
275	if (ifp->if_capenable & IFCAP_TXCSUM_IPV6)
276		ifp->if_hwassist |= (CSUM_TCP_IPV6 | CSUM_UDP_IPV6);
277
278	/* Set up the device filtering */
279	bzero(&filter, sizeof(filter));
280	filter.enable_ethtype = TRUE;
281	filter.enable_macvlan = TRUE;
282	filter.enable_fdir = FALSE;
283	filter.hash_lut_size = I40E_HASH_LUT_SIZE_512;
284	if (i40e_set_filter_control(hw, &filter))
285		device_printf(dev, "i40e_set_filter_control() failed\n");
286
287	/* Prepare the VSI: rings, hmc contexts, etc... */
288	if (ixl_initialize_vsi(vsi)) {
289		device_printf(dev, "initialize vsi failed!!\n");
290		return;
291	}
292
293	/* Set up RSS */
294	ixl_config_rss(pf);
295
296	/* Set up MSI/X routing and the ITR settings */
297	if (pf->msix > 1) {
298		ixl_configure_queue_intr_msix(pf);
299		ixl_configure_itr(pf);
300	} else
301		ixl_configure_legacy(pf);
302
303	ixl_enable_rings(vsi);
304
305	i40e_aq_set_default_vsi(hw, vsi->seid, NULL);
306
307	ixl_reconfigure_filters(vsi);
308
309	/* Check if PROMISC or ALLMULTI flags have been set
310	 * by user before bringing interface up */
311	ixl_set_promisc(vsi);
312
313	/* And now turn on interrupts */
314	ixl_enable_intr(vsi);
315
316	/* Get link info */
317	hw->phy.get_link_info = TRUE;
318	i40e_get_link_status(hw, &pf->link_up);
319	ixl_update_link_status(pf);
320
321	/* Now inform the stack we're ready */
322	ifp->if_drv_flags |= IFF_DRV_RUNNING;
323
324#ifdef IXL_IW
325	if (ixl_enable_iwarp && pf->iw_enabled) {
326		int ret = ixl_iw_pf_init(pf);
327		if (ret)
328			device_printf(dev,
329			    "initialize iwarp failed, code %d\n", ret);
330	}
331#endif
332}
333
334
335/*********************************************************************
336 *
337 *  Get the hardware capabilities
338 *
339 **********************************************************************/
340
341int
342ixl_get_hw_capabilities(struct ixl_pf *pf)
343{
344	struct i40e_aqc_list_capabilities_element_resp *buf;
345	struct i40e_hw	*hw = &pf->hw;
346	device_t 	dev = pf->dev;
347	int             error, len, i2c_intfc_num;
348	u16		needed;
349	bool		again = TRUE;
350
351	if ((pf->state & IXL_PF_STATE_RECOVERY_MODE) != 0) {
352		hw->func_caps.iwarp = 0;
353		return 0;
354	}
355
356	len = 40 * sizeof(struct i40e_aqc_list_capabilities_element_resp);
357retry:
358	if (!(buf = (struct i40e_aqc_list_capabilities_element_resp *)
359	    malloc(len, M_DEVBUF, M_NOWAIT | M_ZERO))) {
360		device_printf(dev, "Unable to allocate cap memory\n");
361                return (ENOMEM);
362	}
363
364	/* This populates the hw struct */
365        error = i40e_aq_discover_capabilities(hw, buf, len,
366	    &needed, i40e_aqc_opc_list_func_capabilities, NULL);
367	free(buf, M_DEVBUF);
368	if ((pf->hw.aq.asq_last_status == I40E_AQ_RC_ENOMEM) &&
369	    (again == TRUE)) {
370		/* retry once with a larger buffer */
371		again = FALSE;
372		len = needed;
373		goto retry;
374	} else if (pf->hw.aq.asq_last_status != I40E_AQ_RC_OK) {
375		device_printf(dev, "capability discovery failed: %d\n",
376		    pf->hw.aq.asq_last_status);
377		return (ENODEV);
378	}
379
380#ifdef IXL_DEBUG
381	device_printf(dev, "pf_id=%d, num_vfs=%d, msix_pf=%d, "
382	    "msix_vf=%d, fd_g=%d, fd_b=%d, tx_qp=%d rx_qp=%d qbase=%d\n",
383	    hw->pf_id, hw->func_caps.num_vfs,
384	    hw->func_caps.num_msix_vectors,
385	    hw->func_caps.num_msix_vectors_vf,
386	    hw->func_caps.fd_filters_guaranteed,
387	    hw->func_caps.fd_filters_best_effort,
388	    hw->func_caps.num_tx_qp,
389	    hw->func_caps.num_rx_qp,
390	    hw->func_caps.base_queue);
391#endif
392	/*
393	 * Some devices have both MDIO and I2C; since this isn't reported
394	 * by the FW, check registers to see if an I2C interface exists.
395	 */
396	i2c_intfc_num = ixl_find_i2c_interface(pf);
397	if (i2c_intfc_num != -1)
398		pf->has_i2c = true;
399
400	/* Determine functions to use for driver I2C accesses */
401	switch (pf->i2c_access_method) {
402	case IXL_I2C_ACCESS_METHOD_BEST_AVAILABLE: {
403		if (hw->mac.type == I40E_MAC_XL710 &&
404		    hw->aq.api_maj_ver == 1 &&
405		    hw->aq.api_min_ver >= 7) {
406			pf->read_i2c_byte = ixl_read_i2c_byte_aq;
407			pf->write_i2c_byte = ixl_write_i2c_byte_aq;
408		} else {
409			pf->read_i2c_byte = ixl_read_i2c_byte_reg;
410			pf->write_i2c_byte = ixl_write_i2c_byte_reg;
411		}
412		break;
413	}
414	case IXL_I2C_ACCESS_METHOD_AQ:
415		pf->read_i2c_byte = ixl_read_i2c_byte_aq;
416		pf->write_i2c_byte = ixl_write_i2c_byte_aq;
417		break;
418	case IXL_I2C_ACCESS_METHOD_REGISTER_I2CCMD:
419		pf->read_i2c_byte = ixl_read_i2c_byte_reg;
420		pf->write_i2c_byte = ixl_write_i2c_byte_reg;
421		break;
422	case IXL_I2C_ACCESS_METHOD_BIT_BANG_I2CPARAMS:
423		pf->read_i2c_byte = ixl_read_i2c_byte_bb;
424		pf->write_i2c_byte = ixl_write_i2c_byte_bb;
425		break;
426	default:
427		/* Should not happen */
428		device_printf(dev, "Error setting I2C access functions\n");
429		break;
430	}
431
432	/* Print a subset of the capability information. */
433	device_printf(dev, "PF-ID[%d]: VFs %d, MSIX %d, VF MSIX %d, QPs %d, %s\n",
434	    hw->pf_id, hw->func_caps.num_vfs, hw->func_caps.num_msix_vectors,
435	    hw->func_caps.num_msix_vectors_vf, hw->func_caps.num_tx_qp,
436	    (hw->func_caps.mdio_port_mode == 2) ? "I2C" :
437	    (hw->func_caps.mdio_port_mode == 1 && pf->has_i2c) ? "MDIO & I2C" :
438	    (hw->func_caps.mdio_port_mode == 1) ? "MDIO dedicated" :
439	    "MDIO shared");
440
441	return (error);
442}
443
444void
445ixl_cap_txcsum_tso(struct ixl_vsi *vsi, struct ifnet *ifp, int mask)
446{
447	device_t 	dev = vsi->dev;
448
449	/* Enable/disable TXCSUM/TSO4 */
450	if (!(ifp->if_capenable & IFCAP_TXCSUM)
451	    && !(ifp->if_capenable & IFCAP_TSO4)) {
452		if (mask & IFCAP_TXCSUM) {
453			ifp->if_capenable |= IFCAP_TXCSUM;
454			/* enable TXCSUM, restore TSO if previously enabled */
455			if (vsi->flags & IXL_FLAGS_KEEP_TSO4) {
456				vsi->flags &= ~IXL_FLAGS_KEEP_TSO4;
457				ifp->if_capenable |= IFCAP_TSO4;
458			}
459		}
460		else if (mask & IFCAP_TSO4) {
461			ifp->if_capenable |= (IFCAP_TXCSUM | IFCAP_TSO4);
462			vsi->flags &= ~IXL_FLAGS_KEEP_TSO4;
463			device_printf(dev,
464			    "TSO4 requires txcsum, enabling both...\n");
465		}
466	} else if((ifp->if_capenable & IFCAP_TXCSUM)
467	    && !(ifp->if_capenable & IFCAP_TSO4)) {
468		if (mask & IFCAP_TXCSUM)
469			ifp->if_capenable &= ~IFCAP_TXCSUM;
470		else if (mask & IFCAP_TSO4)
471			ifp->if_capenable |= IFCAP_TSO4;
472	} else if((ifp->if_capenable & IFCAP_TXCSUM)
473	    && (ifp->if_capenable & IFCAP_TSO4)) {
474		if (mask & IFCAP_TXCSUM) {
475			vsi->flags |= IXL_FLAGS_KEEP_TSO4;
476			ifp->if_capenable &= ~(IFCAP_TXCSUM | IFCAP_TSO4);
477			device_printf(dev,
478			    "TSO4 requires txcsum, disabling both...\n");
479		} else if (mask & IFCAP_TSO4)
480			ifp->if_capenable &= ~IFCAP_TSO4;
481	}
482
483	/* Enable/disable TXCSUM_IPV6/TSO6 */
484	if (!(ifp->if_capenable & IFCAP_TXCSUM_IPV6)
485	    && !(ifp->if_capenable & IFCAP_TSO6)) {
486		if (mask & IFCAP_TXCSUM_IPV6) {
487			ifp->if_capenable |= IFCAP_TXCSUM_IPV6;
488			if (vsi->flags & IXL_FLAGS_KEEP_TSO6) {
489				vsi->flags &= ~IXL_FLAGS_KEEP_TSO6;
490				ifp->if_capenable |= IFCAP_TSO6;
491			}
492		} else if (mask & IFCAP_TSO6) {
493			ifp->if_capenable |= (IFCAP_TXCSUM_IPV6 | IFCAP_TSO6);
494			vsi->flags &= ~IXL_FLAGS_KEEP_TSO6;
495			device_printf(dev,
496			    "TSO6 requires txcsum6, enabling both...\n");
497		}
498	} else if((ifp->if_capenable & IFCAP_TXCSUM_IPV6)
499	    && !(ifp->if_capenable & IFCAP_TSO6)) {
500		if (mask & IFCAP_TXCSUM_IPV6)
501			ifp->if_capenable &= ~IFCAP_TXCSUM_IPV6;
502		else if (mask & IFCAP_TSO6)
503			ifp->if_capenable |= IFCAP_TSO6;
504	} else if ((ifp->if_capenable & IFCAP_TXCSUM_IPV6)
505	    && (ifp->if_capenable & IFCAP_TSO6)) {
506		if (mask & IFCAP_TXCSUM_IPV6) {
507			vsi->flags |= IXL_FLAGS_KEEP_TSO6;
508			ifp->if_capenable &= ~(IFCAP_TXCSUM_IPV6 | IFCAP_TSO6);
509			device_printf(dev,
510			    "TSO6 requires txcsum6, disabling both...\n");
511		} else if (mask & IFCAP_TSO6)
512			ifp->if_capenable &= ~IFCAP_TSO6;
513	}
514}
515
516/* For the set_advertise sysctl */
517void
518ixl_set_initial_advertised_speeds(struct ixl_pf *pf)
519{
520	device_t dev = pf->dev;
521	int err;
522
523	/* Make sure to initialize the device to the complete list of
524	 * supported speeds on driver load, to ensure unloading and
525	 * reloading the driver will restore this value.
526	 */
527	err = ixl_set_advertised_speeds(pf, pf->supported_speeds, true);
528	if (err) {
529		/* Non-fatal error */
530		device_printf(dev, "%s: ixl_set_advertised_speeds() error %d\n",
531			      __func__, err);
532		return;
533	}
534
535	pf->advertised_speed =
536	    ixl_convert_sysctl_aq_link_speed(pf->supported_speeds, false);
537}
538
539int
540ixl_teardown_hw_structs(struct ixl_pf *pf)
541{
542	enum i40e_status_code status = 0;
543	struct i40e_hw *hw = &pf->hw;
544	device_t dev = pf->dev;
545
546	/* Shutdown LAN HMC */
547	if (hw->hmc.hmc_obj) {
548		status = i40e_shutdown_lan_hmc(hw);
549		if (status) {
550			device_printf(dev,
551			    "init: LAN HMC shutdown failure; status %d\n", status);
552			goto err_out;
553		}
554	}
555
556	/* Shutdown admin queue */
557	ixl_disable_intr0(hw);
558	status = i40e_shutdown_adminq(hw);
559	if (status)
560		device_printf(dev,
561		    "init: Admin Queue shutdown failure; status %d\n", status);
562
563err_out:
564	return (status);
565}
566
567int
568ixl_reset(struct ixl_pf *pf)
569{
570	struct i40e_hw *hw = &pf->hw;
571	device_t dev = pf->dev;
572	u8 set_fc_err_mask;
573	int error = 0;
574
575	// XXX: clear_hw() actually writes to hw registers -- maybe this isn't necessary
576	i40e_clear_hw(hw);
577	error = i40e_pf_reset(hw);
578	if (error) {
579		device_printf(dev, "init: PF reset failure\n");
580		error = EIO;
581		goto err_out;
582	}
583
584	error = i40e_init_adminq(hw);
585	if (error) {
586		device_printf(dev, "init: Admin queue init failure;"
587		    " status code %d\n", error);
588		error = EIO;
589		goto err_out;
590	}
591
592	i40e_clear_pxe_mode(hw);
593
594	error = ixl_get_hw_capabilities(pf);
595	if (error) {
596		device_printf(dev, "init: Error retrieving HW capabilities;"
597		    " status code %d\n", error);
598		goto err_out;
599	}
600
601	error = i40e_init_lan_hmc(hw, hw->func_caps.num_tx_qp,
602	    hw->func_caps.num_rx_qp, 0, 0);
603	if (error) {
604		device_printf(dev, "init: LAN HMC init failed; status code %d\n",
605		    error);
606		error = EIO;
607		goto err_out;
608	}
609
610	error = i40e_configure_lan_hmc(hw, I40E_HMC_MODEL_DIRECT_ONLY);
611	if (error) {
612		device_printf(dev, "init: LAN HMC config failed; status code %d\n",
613		    error);
614		error = EIO;
615		goto err_out;
616	}
617
618	// XXX: possible fix for panic, but our failure recovery is still broken
619	error = ixl_switch_config(pf);
620	if (error) {
621		device_printf(dev, "init: ixl_switch_config() failed: %d\n",
622		     error);
623		goto err_out;
624	}
625
626	error = i40e_aq_set_phy_int_mask(hw, IXL_DEFAULT_PHY_INT_MASK,
627	    NULL);
628        if (error) {
629		device_printf(dev, "init: i40e_aq_set_phy_mask() failed: err %d,"
630		    " aq_err %d\n", error, hw->aq.asq_last_status);
631		error = EIO;
632		goto err_out;
633	}
634
635	error = i40e_set_fc(hw, &set_fc_err_mask, true);
636	if (error) {
637		device_printf(dev, "init: setting link flow control failed; retcode %d,"
638		    " fc_err_mask 0x%02x\n", error, set_fc_err_mask);
639		goto err_out;
640	}
641
642	// XXX: (Rebuild VSIs?)
643
644	/* Firmware delay workaround */
645	if (((hw->aq.fw_maj_ver == 4) && (hw->aq.fw_min_ver < 33)) ||
646	    (hw->aq.fw_maj_ver < 4)) {
647		i40e_msec_delay(75);
648		error = i40e_aq_set_link_restart_an(hw, TRUE, NULL);
649		if (error) {
650			device_printf(dev, "init: link restart failed, aq_err %d\n",
651			    hw->aq.asq_last_status);
652			goto err_out;
653		}
654	}
655
656
657	/* Re-enable admin queue interrupt */
658	if (pf->msix > 1) {
659		ixl_configure_intr0_msix(pf);
660		ixl_enable_intr0(hw);
661	}
662
663err_out:
664	return (error);
665}
666
667/*
668** MSIX Interrupt Handlers and Tasklets
669*/
670void
671ixl_handle_que(void *context, int pending)
672{
673	struct ixl_queue *que = context;
674	struct ixl_vsi *vsi = que->vsi;
675	struct ixl_pf *pf = (struct ixl_pf *)vsi->back;
676	struct i40e_hw  *hw = vsi->hw;
677	struct tx_ring  *txr = &que->txr;
678	struct ifnet    *ifp = vsi->ifp;
679	bool		more;
680
681	if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
682		more = ixl_rxeof(que, IXL_RX_LIMIT);
683		IXL_TX_LOCK(txr);
684		ixl_txeof(que);
685		if (!drbr_empty(ifp, txr->br))
686			ixl_mq_start_locked(ifp, txr);
687		IXL_TX_UNLOCK(txr);
688		if (more) {
689			taskqueue_enqueue(que->tq, &que->task);
690			return;
691		}
692	}
693
694	/* Re-enable queue interrupt */
695	if (pf->msix > 1)
696		ixl_enable_queue(hw, que->me);
697	else
698		ixl_enable_intr0(hw);
699}
700
701
702/*********************************************************************
703 *
704 *  Legacy Interrupt Service routine
705 *
706 **********************************************************************/
707void
708ixl_intr(void *arg)
709{
710	struct ixl_pf		*pf = arg;
711	struct i40e_hw		*hw =  &pf->hw;
712	struct ixl_vsi		*vsi = &pf->vsi;
713	struct ixl_queue	*que = vsi->queues;
714	struct ifnet		*ifp = vsi->ifp;
715	struct tx_ring		*txr = &que->txr;
716        u32			icr0;
717	bool			more;
718
719	ixl_disable_intr0(hw);
720
721	pf->admin_irq++;
722
723	/* Clear PBA at start of ISR if using legacy interrupts */
724	if (pf->msix == 0)
725		wr32(hw, I40E_PFINT_DYN_CTL0,
726		    I40E_PFINT_DYN_CTLN_CLEARPBA_MASK |
727		    (IXL_ITR_NONE << I40E_PFINT_DYN_CTLN_ITR_INDX_SHIFT));
728
729	icr0 = rd32(hw, I40E_PFINT_ICR0);
730
731
732#ifdef PCI_IOV
733	if (icr0 & I40E_PFINT_ICR0_VFLR_MASK)
734		taskqueue_enqueue(pf->tq, &pf->vflr_task);
735#endif
736
737	if (icr0 & I40E_PFINT_ICR0_ADMINQ_MASK)
738		taskqueue_enqueue(pf->tq, &pf->adminq);
739
740	if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
741		++que->irqs;
742
743		more = ixl_rxeof(que, IXL_RX_LIMIT);
744
745		IXL_TX_LOCK(txr);
746		ixl_txeof(que);
747		if (!drbr_empty(vsi->ifp, txr->br))
748			ixl_mq_start_locked(ifp, txr);
749		IXL_TX_UNLOCK(txr);
750
751		if (more)
752			taskqueue_enqueue(que->tq, &que->task);
753	}
754
755	ixl_enable_intr0(hw);
756}
757
758
759/*********************************************************************
760 *
761 *  MSIX VSI Interrupt Service routine
762 *
763 **********************************************************************/
764void
765ixl_msix_que(void *arg)
766{
767	struct ixl_queue *que = arg;
768	struct ixl_vsi	*vsi = que->vsi;
769	struct i40e_hw	*hw = vsi->hw;
770	struct tx_ring	*txr = &que->txr;
771	bool		more_tx, more_rx;
772
773	/* Protect against spurious interrupts */
774	if (!(vsi->ifp->if_drv_flags & IFF_DRV_RUNNING))
775		return;
776
777	/* There are drivers which disable auto-masking of interrupts,
778	 * which is a global setting for all ports. We have to make sure
779	 * to mask it to not lose IRQs */
780	ixl_disable_queue(hw, que->me);
781
782	++que->irqs;
783
784	more_rx = ixl_rxeof(que, IXL_RX_LIMIT);
785
786	IXL_TX_LOCK(txr);
787	more_tx = ixl_txeof(que);
788	/*
789	** Make certain that if the stack
790	** has anything queued the task gets
791	** scheduled to handle it.
792	*/
793	if (!drbr_empty(vsi->ifp, txr->br))
794		more_tx = 1;
795	IXL_TX_UNLOCK(txr);
796
797	ixl_set_queue_rx_itr(que);
798	ixl_set_queue_tx_itr(que);
799
800	if (more_tx || more_rx)
801		taskqueue_enqueue(que->tq, &que->task);
802	else
803		ixl_enable_queue(hw, que->me);
804
805	return;
806}
807
808
809/*********************************************************************
810 *
811 *  MSIX Admin Queue Interrupt Service routine
812 *
813 **********************************************************************/
814void
815ixl_msix_adminq(void *arg)
816{
817	struct ixl_pf	*pf = arg;
818	struct i40e_hw	*hw = &pf->hw;
819	device_t	dev = pf->dev;
820	u32		reg, mask, rstat_reg;
821	bool		do_task = FALSE;
822
823	++pf->admin_irq;
824
825	reg = rd32(hw, I40E_PFINT_ICR0);
826	mask = rd32(hw, I40E_PFINT_ICR0_ENA);
827
828	/* Check on the cause */
829	if (reg & I40E_PFINT_ICR0_ADMINQ_MASK) {
830		mask &= ~I40E_PFINT_ICR0_ADMINQ_MASK;
831		do_task = TRUE;
832	}
833
834	if (reg & I40E_PFINT_ICR0_MAL_DETECT_MASK) {
835		ixl_handle_mdd_event(pf);
836		mask &= ~I40E_PFINT_ICR0_MAL_DETECT_MASK;
837	}
838
839	if (reg & I40E_PFINT_ICR0_GRST_MASK) {
840		device_printf(dev, "Reset Requested!\n");
841		rstat_reg = rd32(hw, I40E_GLGEN_RSTAT);
842		rstat_reg = (rstat_reg & I40E_GLGEN_RSTAT_RESET_TYPE_MASK)
843		    >> I40E_GLGEN_RSTAT_RESET_TYPE_SHIFT;
844		device_printf(dev, "Reset type: ");
845		switch (rstat_reg) {
846		/* These others might be handled similarly to an EMPR reset */
847		case I40E_RESET_CORER:
848			printf("CORER\n");
849			break;
850		case I40E_RESET_GLOBR:
851			printf("GLOBR\n");
852			break;
853		case I40E_RESET_EMPR:
854			printf("EMPR\n");
855			atomic_set_int(&pf->state, IXL_PF_STATE_EMPR_RESETTING);
856			break;
857		default:
858			printf("POR\n");
859			break;
860		}
861		/* overload admin queue task to check reset progress */
862		do_task = TRUE;
863	}
864
865	if (reg & I40E_PFINT_ICR0_ECC_ERR_MASK) {
866		device_printf(dev, "ECC Error detected!\n");
867	}
868
869	if (reg & I40E_PFINT_ICR0_HMC_ERR_MASK) {
870		reg = rd32(hw, I40E_PFHMC_ERRORINFO);
871		if (reg & I40E_PFHMC_ERRORINFO_ERROR_DETECTED_MASK) {
872			device_printf(dev, "HMC Error detected!\n");
873			device_printf(dev, "INFO 0x%08x\n", reg);
874			reg = rd32(hw, I40E_PFHMC_ERRORDATA);
875			device_printf(dev, "DATA 0x%08x\n", reg);
876			wr32(hw, I40E_PFHMC_ERRORINFO, 0);
877		}
878	}
879
880	if (reg & I40E_PFINT_ICR0_PCI_EXCEPTION_MASK) {
881		device_printf(dev, "PCI Exception detected!\n");
882	}
883
884#ifdef PCI_IOV
885	if (reg & I40E_PFINT_ICR0_VFLR_MASK) {
886		mask &= ~I40E_PFINT_ICR0_ENA_VFLR_MASK;
887		taskqueue_enqueue(pf->tq, &pf->vflr_task);
888	}
889#endif
890
891	if (do_task)
892		taskqueue_enqueue(pf->tq, &pf->adminq);
893	else
894		ixl_enable_intr0(hw);
895}
896
897void
898ixl_set_promisc(struct ixl_vsi *vsi)
899{
900	struct ifnet	*ifp = vsi->ifp;
901	struct i40e_hw	*hw = vsi->hw;
902	int		err, mcnt = 0;
903	bool		uni = FALSE, multi = FALSE;
904
905        if (ifp->if_flags & IFF_PROMISC)
906		uni = multi = TRUE;
907	else if (ifp->if_flags & IFF_ALLMULTI)
908			multi = TRUE;
909	else { /* Need to count the multicast addresses */
910		struct  ifmultiaddr *ifma;
911		if_maddr_rlock(ifp);
912		TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
913			if (ifma->ifma_addr->sa_family != AF_LINK)
914				continue;
915			if (mcnt == MAX_MULTICAST_ADDR) {
916				multi = TRUE;
917				break;
918			}
919			mcnt++;
920		}
921		if_maddr_runlock(ifp);
922	}
923
924	err = i40e_aq_set_vsi_unicast_promiscuous(hw,
925	    vsi->seid, uni, NULL, TRUE);
926	err = i40e_aq_set_vsi_multicast_promiscuous(hw,
927	    vsi->seid, multi, NULL);
928	return;
929}
930
931/*********************************************************************
932 * 	Filter Routines
933 *
934 *	Routines for multicast and vlan filter management.
935 *
936 *********************************************************************/
937void
938ixl_add_multi(struct ixl_vsi *vsi)
939{
940	struct ifmultiaddr	*ifma;
941	struct ifnet		*ifp = vsi->ifp;
942	struct i40e_hw		*hw = vsi->hw;
943	int			mcnt = 0, flags;
944
945	IOCTL_DEBUGOUT("ixl_add_multi: begin");
946
947	if_maddr_rlock(ifp);
948	/*
949	** First just get a count, to decide if we
950	** we simply use multicast promiscuous.
951	*/
952	TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
953		if (ifma->ifma_addr->sa_family != AF_LINK)
954			continue;
955		mcnt++;
956	}
957	if_maddr_runlock(ifp);
958
959	if (__predict_false(mcnt >= MAX_MULTICAST_ADDR)) {
960		/* delete existing MC filters */
961		ixl_del_hw_filters(vsi, mcnt);
962		i40e_aq_set_vsi_multicast_promiscuous(hw,
963		    vsi->seid, TRUE, NULL);
964		return;
965	}
966
967	mcnt = 0;
968	if_maddr_rlock(ifp);
969	TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
970		if (ifma->ifma_addr->sa_family != AF_LINK)
971			continue;
972		ixl_add_mc_filter(vsi,
973		    (u8*)LLADDR((struct sockaddr_dl *) ifma->ifma_addr));
974		mcnt++;
975	}
976	if_maddr_runlock(ifp);
977	if (mcnt > 0) {
978		flags = (IXL_FILTER_ADD | IXL_FILTER_USED | IXL_FILTER_MC);
979		ixl_add_hw_filters(vsi, flags, mcnt);
980	}
981
982	IOCTL_DEBUGOUT("ixl_add_multi: end");
983	return;
984}
985
986void
987ixl_del_multi(struct ixl_vsi *vsi)
988{
989	struct ifnet		*ifp = vsi->ifp;
990	struct ifmultiaddr	*ifma;
991	struct ixl_mac_filter	*f;
992	int			mcnt = 0;
993	bool		match = FALSE;
994
995	IOCTL_DEBUGOUT("ixl_del_multi: begin");
996
997	/* Search for removed multicast addresses */
998	if_maddr_rlock(ifp);
999	SLIST_FOREACH(f, &vsi->ftl, next) {
1000		if ((f->flags & IXL_FILTER_USED) && (f->flags & IXL_FILTER_MC)) {
1001			match = FALSE;
1002			TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
1003				if (ifma->ifma_addr->sa_family != AF_LINK)
1004					continue;
1005				u8 *mc_addr = (u8 *)LLADDR((struct sockaddr_dl *)ifma->ifma_addr);
1006				if (cmp_etheraddr(f->macaddr, mc_addr)) {
1007					match = TRUE;
1008					break;
1009				}
1010			}
1011			if (match == FALSE) {
1012				f->flags |= IXL_FILTER_DEL;
1013				mcnt++;
1014			}
1015		}
1016	}
1017	if_maddr_runlock(ifp);
1018
1019	if (mcnt > 0)
1020		ixl_del_hw_filters(vsi, mcnt);
1021}
1022
1023/*********************************************************************
1024 *  Timer routine
1025 *
1026 *  This routine checks for link status, updates statistics,
1027 *  and runs the watchdog check.
1028 *
1029 **********************************************************************/
1030
1031void
1032ixl_local_timer(void *arg)
1033{
1034	struct ixl_pf		*pf = arg;
1035	struct ifnet *ifp = pf->vsi.ifp;
1036
1037	if (ixl_fw_recovery_mode(pf)) {
1038		if (!(atomic_load_acq_int(&pf->state) & IXL_PF_STATE_RECOVERY_MODE)) {
1039			if (ifp->if_drv_flags & IFF_DRV_RUNNING)
1040			    ixl_stop_locked(pf);
1041			atomic_set_int(&pf->state, IXL_PF_STATE_RECOVERY_MODE | IXL_PF_STATE_EMPR_RESETTING);
1042			device_printf(pf->dev, "Firmware recovery mode detected. Limiting functionality. Refer to Intel(R) Ethernet Adapters and Devices User Guide for details on firmware recovery mode.\n");
1043		}
1044	}
1045
1046	IXL_PF_LOCK_ASSERT(pf);
1047
1048	/* Fire off the adminq task */
1049	taskqueue_enqueue(pf->tq, &pf->adminq);
1050
1051	if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
1052		/* Update stats */
1053		ixl_update_stats_counters(pf);
1054	}
1055
1056	if (ixl_queue_hang_check(&pf->vsi)) {
1057		/* Increment stat when a queue shows hung */
1058		pf->watchdog_events++;
1059	}
1060
1061	callout_reset(&pf->timer, hz, ixl_local_timer, pf);
1062}
1063
1064void
1065ixl_link_up_msg(struct ixl_pf *pf)
1066{
1067	struct i40e_hw *hw = &pf->hw;
1068	struct ifnet *ifp = pf->vsi.ifp;
1069	char *req_fec_string, *neg_fec_string;
1070	u8 fec_abilities;
1071
1072	fec_abilities = hw->phy.link_info.req_fec_info;
1073	/* If both RS and KR are requested, only show RS */
1074	if (fec_abilities & I40E_AQ_REQUEST_FEC_RS)
1075		req_fec_string = ixl_fec_string[0];
1076	else if (fec_abilities & I40E_AQ_REQUEST_FEC_KR)
1077		req_fec_string = ixl_fec_string[1];
1078	else
1079		req_fec_string = ixl_fec_string[2];
1080
1081	if (hw->phy.link_info.fec_info & I40E_AQ_CONFIG_FEC_RS_ENA)
1082		neg_fec_string = ixl_fec_string[0];
1083	else if (hw->phy.link_info.fec_info & I40E_AQ_CONFIG_FEC_KR_ENA)
1084		neg_fec_string = ixl_fec_string[1];
1085	else
1086		neg_fec_string = ixl_fec_string[2];
1087
1088	log(LOG_NOTICE, "%s: Link is up, %s Full Duplex, Requested FEC: %s, Negotiated FEC: %s, Autoneg: %s, Flow Control: %s\n",
1089	    ifp->if_xname,
1090	    ixl_link_speed_string(hw->phy.link_info.link_speed),
1091	    req_fec_string, neg_fec_string,
1092	    (hw->phy.link_info.an_info & I40E_AQ_AN_COMPLETED) ? "True" : "False",
1093	    (hw->phy.link_info.an_info & I40E_AQ_LINK_PAUSE_TX &&
1094	        hw->phy.link_info.an_info & I40E_AQ_LINK_PAUSE_RX) ?
1095		ixl_fc_string[3] : (hw->phy.link_info.an_info & I40E_AQ_LINK_PAUSE_TX) ?
1096		ixl_fc_string[2] : (hw->phy.link_info.an_info & I40E_AQ_LINK_PAUSE_RX) ?
1097		ixl_fc_string[1] : ixl_fc_string[0]);
1098}
1099
1100/*
1101** Note: this routine updates the OS on the link state
1102**	the real check of the hardware only happens with
1103**	a link interrupt.
1104*/
1105void
1106ixl_update_link_status(struct ixl_pf *pf)
1107{
1108	struct ixl_vsi		*vsi = &pf->vsi;
1109	struct ifnet		*ifp = vsi->ifp;
1110	device_t		dev = pf->dev;
1111
1112	if (pf->link_up) {
1113		if (vsi->link_active == FALSE) {
1114			vsi->link_active = TRUE;
1115#if __FreeBSD_version >= 1100000
1116			ifp->if_baudrate = ixl_max_aq_speed_to_value(pf->link_speed);
1117#else
1118			if_initbaudrate(ifp, ixl_max_aq_speed_to_value(pf->link_speed));
1119#endif
1120			if_link_state_change(ifp, LINK_STATE_UP);
1121			ixl_link_up_msg(pf);
1122#ifdef PCI_IOV
1123			ixl_broadcast_link_state(pf);
1124#endif
1125		}
1126	} else { /* Link down */
1127		if (vsi->link_active == TRUE) {
1128			if (bootverbose)
1129				device_printf(dev, "Link is Down\n");
1130			if_link_state_change(ifp, LINK_STATE_DOWN);
1131			vsi->link_active = FALSE;
1132#ifdef PCI_IOV
1133			ixl_broadcast_link_state(pf);
1134#endif
1135		}
1136	}
1137}
1138
1139/*********************************************************************
1140 *
1141 *  This routine disables all traffic on the adapter by issuing a
1142 *  global reset on the MAC and deallocates TX/RX buffers.
1143 *
1144 **********************************************************************/
1145
1146void
1147ixl_stop_locked(struct ixl_pf *pf)
1148{
1149	struct ixl_vsi	*vsi = &pf->vsi;
1150	struct ifnet	*ifp = vsi->ifp;
1151
1152	INIT_DEBUGOUT("ixl_stop: begin\n");
1153
1154	IXL_PF_LOCK_ASSERT(pf);
1155
1156	/* Tell the stack that the interface is no longer active */
1157	ifp->if_drv_flags &= ~(IFF_DRV_RUNNING);
1158
1159#ifdef IXL_IW
1160	/* Stop iWARP device */
1161	if (ixl_enable_iwarp && pf->iw_enabled)
1162		ixl_iw_pf_stop(pf);
1163#endif
1164
1165	ixl_disable_rings_intr(vsi);
1166	ixl_disable_rings(vsi);
1167}
1168
1169void
1170ixl_stop(struct ixl_pf *pf)
1171{
1172	IXL_PF_LOCK(pf);
1173	ixl_stop_locked(pf);
1174	IXL_PF_UNLOCK(pf);
1175}
1176
1177/*********************************************************************
1178 *
1179 *  Setup MSIX Interrupt resources and handlers for the VSI
1180 *
1181 **********************************************************************/
1182int
1183ixl_setup_legacy(struct ixl_pf *pf)
1184{
1185	device_t        dev = pf->dev;
1186	int 		error, rid = 0;
1187
1188	if (pf->msix == 1)
1189		rid = 1;
1190	pf->res = bus_alloc_resource_any(dev, SYS_RES_IRQ,
1191	    &rid, RF_SHAREABLE | RF_ACTIVE);
1192	if (pf->res == NULL) {
1193		device_printf(dev, "bus_alloc_resource_any() for"
1194		    " legacy/msi interrupt\n");
1195		return (ENXIO);
1196	}
1197
1198	/* Set the handler function */
1199	error = bus_setup_intr(dev, pf->res,
1200	    INTR_TYPE_NET | INTR_MPSAFE, NULL,
1201	    ixl_intr, pf, &pf->tag);
1202	if (error) {
1203		pf->res = NULL;
1204		device_printf(dev, "bus_setup_intr() for legacy/msi"
1205		    " interrupt handler failed, error %d\n", error);
1206		return (ENXIO);
1207	}
1208	error = bus_describe_intr(dev, pf->res, pf->tag, "irq");
1209	if (error) {
1210		/* non-fatal */
1211		device_printf(dev, "bus_describe_intr() for Admin Queue"
1212		    " interrupt name failed, error %d\n", error);
1213	}
1214
1215	return (0);
1216}
1217
1218int
1219ixl_setup_adminq_tq(struct ixl_pf *pf)
1220{
1221	device_t dev = pf->dev;
1222	int error = 0;
1223
1224	/* Tasklet for Admin Queue interrupts */
1225	TASK_INIT(&pf->adminq, 0, ixl_do_adminq, pf);
1226#ifdef PCI_IOV
1227	/* VFLR Tasklet */
1228	TASK_INIT(&pf->vflr_task, 0, ixl_handle_vflr, pf);
1229#endif
1230	/* Create and start Admin Queue taskqueue */
1231	pf->tq = taskqueue_create_fast("ixl_aq", M_NOWAIT,
1232	    taskqueue_thread_enqueue, &pf->tq);
1233	if (!pf->tq) {
1234		device_printf(dev, "taskqueue_create_fast (for AQ) returned NULL!\n");
1235		return (ENOMEM);
1236	}
1237	error = taskqueue_start_threads(&pf->tq, 1, PI_NET, "%s aq",
1238	    device_get_nameunit(dev));
1239	if (error) {
1240		device_printf(dev, "taskqueue_start_threads (for AQ) error: %d\n",
1241		    error);
1242		taskqueue_free(pf->tq);
1243		return (error);
1244	}
1245	return (0);
1246}
1247
1248int
1249ixl_setup_queue_tqs(struct ixl_vsi *vsi)
1250{
1251	struct ixl_queue *que = vsi->queues;
1252	device_t dev = vsi->dev;
1253#ifdef  RSS
1254	int		cpu_id = 0;
1255        cpuset_t	cpu_mask;
1256#endif
1257
1258	/* Create queue tasks and start queue taskqueues */
1259	for (int i = 0; i < vsi->num_queues; i++, que++) {
1260		TASK_INIT(&que->tx_task, 0, ixl_deferred_mq_start, que);
1261		TASK_INIT(&que->task, 0, ixl_handle_que, que);
1262		que->tq = taskqueue_create_fast("ixl_que", M_NOWAIT,
1263		    taskqueue_thread_enqueue, &que->tq);
1264#ifdef RSS
1265		CPU_SETOF(cpu_id, &cpu_mask);
1266		taskqueue_start_threads_cpuset(&que->tq, 1, PI_NET,
1267		    &cpu_mask, "%s (bucket %d)",
1268		    device_get_nameunit(dev), cpu_id);
1269#else
1270		taskqueue_start_threads(&que->tq, 1, PI_NET,
1271		    "%s (que %d)", device_get_nameunit(dev), que->me);
1272#endif
1273	}
1274
1275	return (0);
1276}
1277
1278void
1279ixl_free_adminq_tq(struct ixl_pf *pf)
1280{
1281	if (pf->tq) {
1282		taskqueue_free(pf->tq);
1283		pf->tq = NULL;
1284	}
1285}
1286
1287void
1288ixl_free_queue_tqs(struct ixl_vsi *vsi)
1289{
1290	struct ixl_queue *que = vsi->queues;
1291
1292	for (int i = 0; i < vsi->num_queues; i++, que++) {
1293		if (que->tq) {
1294			taskqueue_free(que->tq);
1295			que->tq = NULL;
1296		}
1297	}
1298}
1299
1300int
1301ixl_setup_adminq_msix(struct ixl_pf *pf)
1302{
1303	device_t dev = pf->dev;
1304	int rid, error = 0;
1305
1306	/* Admin IRQ rid is 1, vector is 0 */
1307	rid = 1;
1308	/* Get interrupt resource from bus */
1309	pf->res = bus_alloc_resource_any(dev,
1310    	    SYS_RES_IRQ, &rid, RF_SHAREABLE | RF_ACTIVE);
1311	if (!pf->res) {
1312		device_printf(dev, "bus_alloc_resource_any() for Admin Queue"
1313		    " interrupt failed [rid=%d]\n", rid);
1314		return (ENXIO);
1315	}
1316	/* Then associate interrupt with handler */
1317	error = bus_setup_intr(dev, pf->res,
1318	    INTR_TYPE_NET | INTR_MPSAFE, NULL,
1319	    ixl_msix_adminq, pf, &pf->tag);
1320	if (error) {
1321		pf->res = NULL;
1322		device_printf(dev, "bus_setup_intr() for Admin Queue"
1323		    " interrupt handler failed, error %d\n", error);
1324		return (ENXIO);
1325	}
1326	error = bus_describe_intr(dev, pf->res, pf->tag, "aq");
1327	if (error) {
1328		/* non-fatal */
1329		device_printf(dev, "bus_describe_intr() for Admin Queue"
1330		    " interrupt name failed, error %d\n", error);
1331	}
1332	pf->admvec = 0;
1333
1334	return (0);
1335}
1336
1337/*
1338 * Allocate interrupt resources from bus and associate an interrupt handler
1339 * to those for the VSI's queues.
1340 */
1341int
1342ixl_setup_queue_msix(struct ixl_vsi *vsi)
1343{
1344	device_t	dev = vsi->dev;
1345	struct 		ixl_queue *que = vsi->queues;
1346	struct		tx_ring	 *txr;
1347	int 		error, rid, vector = 1;
1348
1349	/* Queue interrupt vector numbers start at 1 (adminq intr is 0) */
1350	for (int i = 0; i < vsi->num_queues; i++, vector++, que++) {
1351		int cpu_id = i;
1352		rid = vector + 1;
1353		txr = &que->txr;
1354		que->res = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid,
1355		    RF_SHAREABLE | RF_ACTIVE);
1356		if (!que->res) {
1357			device_printf(dev, "bus_alloc_resource_any() for"
1358			    " Queue %d interrupt failed [rid=%d]\n",
1359			    que->me, rid);
1360			return (ENXIO);
1361		}
1362		/* Set the handler function */
1363		error = bus_setup_intr(dev, que->res,
1364		    INTR_TYPE_NET | INTR_MPSAFE, NULL,
1365		    ixl_msix_que, que, &que->tag);
1366		if (error) {
1367			device_printf(dev, "bus_setup_intr() for Queue %d"
1368			    " interrupt handler failed, error %d\n",
1369			    que->me, error);
1370			bus_release_resource(dev, SYS_RES_IRQ, rid, que->res);
1371			return (error);
1372		}
1373		error = bus_describe_intr(dev, que->res, que->tag, "q%d", i);
1374		if (error) {
1375			device_printf(dev, "bus_describe_intr() for Queue %d"
1376			    " interrupt name failed, error %d\n",
1377			    que->me, error);
1378		}
1379		/* Bind the vector to a CPU */
1380#ifdef RSS
1381		cpu_id = rss_getcpu(i % rss_getnumbuckets());
1382#endif
1383		error = bus_bind_intr(dev, que->res, cpu_id);
1384		if (error) {
1385			device_printf(dev, "bus_bind_intr() for Queue %d"
1386			    " to CPU %d failed, error %d\n",
1387			    que->me, cpu_id, error);
1388		}
1389		que->msix = vector;
1390	}
1391
1392	return (0);
1393}
1394
1395/*
1396 * Allocate MSI/X vectors from the OS.
1397 * Returns 0 for legacy, 1 for MSI, >1 for MSIX.
1398 */
1399int
1400ixl_init_msix(struct ixl_pf *pf)
1401{
1402	device_t dev = pf->dev;
1403	struct i40e_hw *hw = &pf->hw;
1404#ifdef IXL_IW
1405#if __FreeBSD_version >= 1100000
1406        cpuset_t cpu_set;
1407#endif
1408#endif
1409	int auto_max_queues;
1410	int rid, want, vectors, queues, available;
1411#ifdef IXL_IW
1412	int iw_want=0, iw_vectors;
1413
1414	pf->iw_msix = 0;
1415#endif
1416
1417	/* Override by tuneable */
1418	if (!pf->enable_msix)
1419		goto no_msix;
1420
1421	/* First try MSI/X */
1422	rid = PCIR_BAR(IXL_MSIX_BAR);
1423	pf->msix_mem = bus_alloc_resource_any(dev,
1424	    SYS_RES_MEMORY, &rid, RF_ACTIVE);
1425       	if (!pf->msix_mem) {
1426		/* May not be enabled */
1427		device_printf(pf->dev,
1428		    "Unable to map MSIX table\n");
1429		goto no_msix;
1430	}
1431
1432	available = pci_msix_count(dev);
1433	if (available < 2) {
1434		/* system has msix disabled (0), or only one vector (1) */
1435		device_printf(pf->dev, "Less than two MSI-X vectors available\n");
1436		bus_release_resource(dev, SYS_RES_MEMORY,
1437		    rid, pf->msix_mem);
1438		pf->msix_mem = NULL;
1439		goto no_msix;
1440	}
1441
1442	/* Clamp max number of queues based on:
1443	 * - # of MSI-X vectors available
1444	 * - # of cpus available
1445	 * - # of queues that can be assigned to the LAN VSI
1446	 */
1447	auto_max_queues = min(mp_ncpus, available - 1);
1448	if (hw->mac.type == I40E_MAC_X722)
1449		auto_max_queues = min(auto_max_queues, 128);
1450	else
1451		auto_max_queues = min(auto_max_queues, 64);
1452
1453	/* Override with tunable value if tunable is less than autoconfig count */
1454	if ((pf->max_queues != 0) && (pf->max_queues <= auto_max_queues))
1455		queues = pf->max_queues;
1456	/* Use autoconfig amount if that's lower */
1457	else if ((pf->max_queues != 0) && (pf->max_queues > auto_max_queues)) {
1458		device_printf(dev, "ixl_max_queues (%d) is too large, using "
1459		    "autoconfig amount (%d)...\n",
1460		    pf->max_queues, auto_max_queues);
1461		queues = auto_max_queues;
1462	}
1463	/* Limit maximum auto-configured queues to 8 if no user value is set */
1464	else
1465		queues = min(auto_max_queues, 8);
1466
1467#ifdef  RSS
1468	/* If we're doing RSS, clamp at the number of RSS buckets */
1469	if (queues > rss_getnumbuckets())
1470		queues = rss_getnumbuckets();
1471#endif
1472
1473	/*
1474	** Want one vector (RX/TX pair) per queue
1475	** plus an additional for the admin queue.
1476	*/
1477	want = queues + 1;
1478	if (want <= available)	/* Have enough */
1479		vectors = want;
1480	else {
1481               	device_printf(pf->dev,
1482		    "MSIX Configuration Problem, "
1483		    "%d vectors available but %d wanted!\n",
1484		    available, want);
1485		pf->msix_mem = NULL;
1486		goto no_msix; /* Will go to Legacy setup */
1487	}
1488
1489#ifdef IXL_IW
1490	if (ixl_enable_iwarp && hw->func_caps.iwarp) {
1491#if __FreeBSD_version >= 1100000
1492		if(bus_get_cpus(dev, INTR_CPUS, sizeof(cpu_set), &cpu_set) == 0)
1493		{
1494			iw_want = min(CPU_COUNT(&cpu_set), IXL_IW_MAX_MSIX);
1495		}
1496#endif
1497		if(!iw_want)
1498			iw_want = min(mp_ncpus, IXL_IW_MAX_MSIX);
1499		if(ixl_limit_iwarp_msix > 0)
1500			iw_want = min(iw_want, ixl_limit_iwarp_msix);
1501		else
1502			iw_want = min(iw_want, 1);
1503
1504		available -= vectors;
1505		if (available > 0) {
1506			iw_vectors = (available >= iw_want) ?
1507				iw_want : available;
1508			vectors += iw_vectors;
1509		} else
1510			iw_vectors = 0;
1511	}
1512#endif
1513
1514	ixl_set_msix_enable(dev);
1515	if (pci_alloc_msix(dev, &vectors) == 0) {
1516               	device_printf(pf->dev,
1517		    "Using MSIX interrupts with %d vectors\n", vectors);
1518		pf->msix = vectors;
1519#ifdef IXL_IW
1520		if (ixl_enable_iwarp && hw->func_caps.iwarp)
1521		{
1522			pf->iw_msix = iw_vectors;
1523			device_printf(pf->dev,
1524					"Reserving %d MSIX interrupts for iWARP CEQ and AEQ\n",
1525					iw_vectors);
1526		}
1527#endif
1528
1529		pf->vsi.num_queues = queues;
1530#ifdef RSS
1531		/*
1532		 * If we're doing RSS, the number of queues needs to
1533		 * match the number of RSS buckets that are configured.
1534		 *
1535		 * + If there's more queues than RSS buckets, we'll end
1536		 *   up with queues that get no traffic.
1537		 *
1538		 * + If there's more RSS buckets than queues, we'll end
1539		 *   up having multiple RSS buckets map to the same queue,
1540		 *   so there'll be some contention.
1541		 */
1542		if (queues != rss_getnumbuckets()) {
1543			device_printf(dev,
1544			    "%s: queues (%d) != RSS buckets (%d)"
1545			    "; performance will be impacted.\n",
1546			    __func__, queues, rss_getnumbuckets());
1547		}
1548#endif
1549		return (vectors);
1550	}
1551no_msix:
1552	vectors = pci_msi_count(dev);
1553	pf->vsi.num_queues = 1;
1554	pf->max_queues = 1;
1555	if (vectors == 1 && pci_alloc_msi(dev, &vectors) == 0)
1556		device_printf(pf->dev, "Using an MSI interrupt\n");
1557	else {
1558		vectors = 0;
1559		device_printf(pf->dev, "Using a Legacy interrupt\n");
1560	}
1561	return (vectors);
1562}
1563
1564/*
1565 * Configure admin queue/misc interrupt cause registers in hardware.
1566 */
1567void
1568ixl_configure_intr0_msix(struct ixl_pf *pf)
1569{
1570	struct i40e_hw *hw = &pf->hw;
1571	u32 reg;
1572
1573	/* First set up the adminq - vector 0 */
1574	wr32(hw, I40E_PFINT_ICR0_ENA, 0);  /* disable all */
1575	rd32(hw, I40E_PFINT_ICR0);         /* read to clear */
1576
1577	reg = I40E_PFINT_ICR0_ENA_ECC_ERR_MASK |
1578	    I40E_PFINT_ICR0_ENA_GRST_MASK |
1579	    I40E_PFINT_ICR0_ENA_HMC_ERR_MASK |
1580	    I40E_PFINT_ICR0_ENA_ADMINQ_MASK |
1581	    I40E_PFINT_ICR0_ENA_MAL_DETECT_MASK |
1582	    I40E_PFINT_ICR0_ENA_VFLR_MASK |
1583	    I40E_PFINT_ICR0_ENA_PE_CRITERR_MASK |
1584	    I40E_PFINT_ICR0_ENA_PCI_EXCEPTION_MASK;
1585	wr32(hw, I40E_PFINT_ICR0_ENA, reg);
1586
1587	/*
1588	 * 0x7FF is the end of the queue list.
1589	 * This means we won't use MSI-X vector 0 for a queue interrupt
1590	 * in MSIX mode.
1591	 */
1592	wr32(hw, I40E_PFINT_LNKLST0, 0x7FF);
1593	/* Value is in 2 usec units, so 0x3E is 62*2 = 124 usecs. */
1594	wr32(hw, I40E_PFINT_ITR0(IXL_RX_ITR), 0x3E);
1595
1596	wr32(hw, I40E_PFINT_DYN_CTL0,
1597	    I40E_PFINT_DYN_CTL0_SW_ITR_INDX_MASK |
1598	    I40E_PFINT_DYN_CTL0_INTENA_MSK_MASK);
1599
1600	wr32(hw, I40E_PFINT_STAT_CTL0, 0);
1601}
1602
1603/*
1604 * Configure queue interrupt cause registers in hardware.
1605 */
1606void
1607ixl_configure_queue_intr_msix(struct ixl_pf *pf)
1608{
1609	struct i40e_hw	*hw = &pf->hw;
1610	struct ixl_vsi *vsi = &pf->vsi;
1611	u32		reg;
1612	u16		vector = 1;
1613
1614	for (int i = 0; i < vsi->num_queues; i++, vector++) {
1615		wr32(hw, I40E_PFINT_DYN_CTLN(i), 0);
1616		/* First queue type is RX / 0 */
1617		wr32(hw, I40E_PFINT_LNKLSTN(i), i);
1618
1619		reg = I40E_QINT_RQCTL_CAUSE_ENA_MASK |
1620		(IXL_RX_ITR << I40E_QINT_RQCTL_ITR_INDX_SHIFT) |
1621		(vector << I40E_QINT_RQCTL_MSIX_INDX_SHIFT) |
1622		(i << I40E_QINT_RQCTL_NEXTQ_INDX_SHIFT) |
1623		(I40E_QUEUE_TYPE_TX << I40E_QINT_RQCTL_NEXTQ_TYPE_SHIFT);
1624		wr32(hw, I40E_QINT_RQCTL(i), reg);
1625
1626		reg = I40E_QINT_TQCTL_CAUSE_ENA_MASK |
1627		(IXL_TX_ITR << I40E_QINT_TQCTL_ITR_INDX_SHIFT) |
1628		(vector << I40E_QINT_TQCTL_MSIX_INDX_SHIFT) |
1629		(IXL_QUEUE_EOL << I40E_QINT_TQCTL_NEXTQ_INDX_SHIFT) |
1630		(I40E_QUEUE_TYPE_RX << I40E_QINT_TQCTL_NEXTQ_TYPE_SHIFT);
1631		wr32(hw, I40E_QINT_TQCTL(i), reg);
1632	}
1633}
1634
1635/*
1636 * Configure for MSI single vector operation
1637 */
1638void
1639ixl_configure_legacy(struct ixl_pf *pf)
1640{
1641	struct i40e_hw	*hw = &pf->hw;
1642	struct ixl_vsi	*vsi = &pf->vsi;
1643	struct ixl_queue *que = vsi->queues;
1644	struct rx_ring 	*rxr = &que->rxr;
1645	struct tx_ring	*txr = &que->txr;
1646	u32 reg;
1647
1648	/* Configure ITR */
1649	vsi->tx_itr_setting = pf->tx_itr;
1650	wr32(hw, I40E_PFINT_ITR0(IXL_TX_ITR),
1651	    vsi->tx_itr_setting);
1652	txr->itr = vsi->tx_itr_setting;
1653
1654	vsi->rx_itr_setting = pf->rx_itr;
1655	wr32(hw, I40E_PFINT_ITR0(IXL_RX_ITR),
1656	    vsi->rx_itr_setting);
1657	rxr->itr = vsi->rx_itr_setting;
1658
1659	/* Setup "other" causes */
1660	reg = I40E_PFINT_ICR0_ENA_ECC_ERR_MASK
1661	    | I40E_PFINT_ICR0_ENA_MAL_DETECT_MASK
1662	    | I40E_PFINT_ICR0_ENA_GRST_MASK
1663	    | I40E_PFINT_ICR0_ENA_PCI_EXCEPTION_MASK
1664	    | I40E_PFINT_ICR0_ENA_HMC_ERR_MASK
1665	    | I40E_PFINT_ICR0_ENA_PE_CRITERR_MASK
1666	    | I40E_PFINT_ICR0_ENA_VFLR_MASK
1667	    | I40E_PFINT_ICR0_ENA_ADMINQ_MASK
1668	    ;
1669	wr32(hw, I40E_PFINT_ICR0_ENA, reg);
1670
1671	/* No ITR for non-queue interrupts */
1672	wr32(hw, I40E_PFINT_STAT_CTL0,
1673	    IXL_ITR_NONE << I40E_PFINT_STAT_CTL0_OTHER_ITR_INDX_SHIFT);
1674
1675	/* FIRSTQ_INDX = 0, FIRSTQ_TYPE = 0 (rx) */
1676	wr32(hw, I40E_PFINT_LNKLST0, 0);
1677
1678	/* Associate the queue pair to the vector and enable the q int */
1679	reg = I40E_QINT_RQCTL_CAUSE_ENA_MASK
1680	    | (IXL_RX_ITR << I40E_QINT_RQCTL_ITR_INDX_SHIFT)
1681	    | (I40E_QUEUE_TYPE_TX << I40E_QINT_RQCTL_NEXTQ_TYPE_SHIFT);
1682	wr32(hw, I40E_QINT_RQCTL(0), reg);
1683
1684	reg = I40E_QINT_TQCTL_CAUSE_ENA_MASK
1685	    | (IXL_TX_ITR << I40E_QINT_TQCTL_ITR_INDX_SHIFT)
1686	    | (IXL_QUEUE_EOL << I40E_QINT_TQCTL_NEXTQ_INDX_SHIFT);
1687	wr32(hw, I40E_QINT_TQCTL(0), reg);
1688}
1689
1690int
1691ixl_allocate_pci_resources(struct ixl_pf *pf)
1692{
1693	int             rid;
1694	struct i40e_hw *hw = &pf->hw;
1695	device_t        dev = pf->dev;
1696
1697	/* Map BAR0 */
1698	rid = PCIR_BAR(0);
1699	pf->pci_mem = bus_alloc_resource_any(dev, SYS_RES_MEMORY,
1700	    &rid, RF_ACTIVE);
1701
1702	if (!(pf->pci_mem)) {
1703		device_printf(dev, "Unable to allocate bus resource: PCI memory\n");
1704		return (ENXIO);
1705	}
1706	/* Ensure proper PCI device operation */
1707	ixl_set_busmaster(dev);
1708
1709	/* Save off the PCI information */
1710	hw->vendor_id = pci_get_vendor(dev);
1711	hw->device_id = pci_get_device(dev);
1712	hw->revision_id = pci_read_config(dev, PCIR_REVID, 1);
1713	hw->subsystem_vendor_id =
1714	    pci_read_config(dev, PCIR_SUBVEND_0, 2);
1715	hw->subsystem_device_id =
1716	    pci_read_config(dev, PCIR_SUBDEV_0, 2);
1717
1718	hw->bus.device = pci_get_slot(dev);
1719	hw->bus.func = pci_get_function(dev);
1720
1721	/* Save off register access information */
1722	pf->osdep.mem_bus_space_tag =
1723		rman_get_bustag(pf->pci_mem);
1724	pf->osdep.mem_bus_space_handle =
1725		rman_get_bushandle(pf->pci_mem);
1726	pf->osdep.mem_bus_space_size = rman_get_size(pf->pci_mem);
1727	pf->osdep.flush_reg = I40E_GLGEN_STAT;
1728	pf->hw.hw_addr = (u8 *) &pf->osdep.mem_bus_space_handle;
1729
1730	pf->hw.back = &pf->osdep;
1731
1732	return (0);
1733}
1734
1735/*
1736 * Teardown and release the admin queue/misc vector
1737 * interrupt.
1738 */
1739int
1740ixl_teardown_adminq_msix(struct ixl_pf *pf)
1741{
1742	device_t		dev = pf->dev;
1743	int			rid, error = 0;
1744
1745	if (pf->admvec) /* we are doing MSIX */
1746		rid = pf->admvec + 1;
1747	else
1748		(pf->msix != 0) ? (rid = 1):(rid = 0);
1749
1750	if (pf->tag != NULL) {
1751		bus_teardown_intr(dev, pf->res, pf->tag);
1752		if (error) {
1753			device_printf(dev, "bus_teardown_intr() for"
1754			    " interrupt 0 failed\n");
1755			// return (ENXIO);
1756		}
1757		pf->tag = NULL;
1758	}
1759	if (pf->res != NULL) {
1760		bus_release_resource(dev, SYS_RES_IRQ, rid, pf->res);
1761		if (error) {
1762			device_printf(dev, "bus_release_resource() for"
1763			    " interrupt 0 failed [rid=%d]\n", rid);
1764			// return (ENXIO);
1765		}
1766		pf->res = NULL;
1767	}
1768
1769	return (0);
1770}
1771
1772int
1773ixl_teardown_queue_msix(struct ixl_vsi *vsi)
1774{
1775	struct ixl_pf		*pf = (struct ixl_pf *)vsi->back;
1776	struct ixl_queue	*que = vsi->queues;
1777	device_t		dev = vsi->dev;
1778	int			rid, error = 0;
1779
1780	/* We may get here before stations are setup */
1781	if ((pf->msix < 2) || (que == NULL))
1782		return (0);
1783
1784	/* Release all MSIX queue resources */
1785	for (int i = 0; i < vsi->num_queues; i++, que++) {
1786		rid = que->msix + 1;
1787		if (que->tag != NULL) {
1788			error = bus_teardown_intr(dev, que->res, que->tag);
1789			if (error) {
1790				device_printf(dev, "bus_teardown_intr() for"
1791				    " Queue %d interrupt failed\n",
1792				    que->me);
1793				// return (ENXIO);
1794			}
1795			que->tag = NULL;
1796		}
1797		if (que->res != NULL) {
1798			error = bus_release_resource(dev, SYS_RES_IRQ, rid, que->res);
1799			if (error) {
1800				device_printf(dev, "bus_release_resource() for"
1801				    " Queue %d interrupt failed [rid=%d]\n",
1802				    que->me, rid);
1803				// return (ENXIO);
1804			}
1805			que->res = NULL;
1806		}
1807	}
1808
1809	return (0);
1810}
1811
1812void
1813ixl_free_pci_resources(struct ixl_pf *pf)
1814{
1815	device_t		dev = pf->dev;
1816	int			memrid;
1817
1818	ixl_teardown_queue_msix(&pf->vsi);
1819	ixl_teardown_adminq_msix(pf);
1820
1821	if (pf->msix > 0)
1822		pci_release_msi(dev);
1823
1824	memrid = PCIR_BAR(IXL_MSIX_BAR);
1825
1826	if (pf->msix_mem != NULL)
1827		bus_release_resource(dev, SYS_RES_MEMORY,
1828		    memrid, pf->msix_mem);
1829
1830	if (pf->pci_mem != NULL)
1831		bus_release_resource(dev, SYS_RES_MEMORY,
1832		    PCIR_BAR(0), pf->pci_mem);
1833
1834	return;
1835}
1836
1837void
1838ixl_add_ifmedia(struct ixl_vsi *vsi, u64 phy_types)
1839{
1840	/* Display supported media types */
1841	if (phy_types & (I40E_CAP_PHY_TYPE_100BASE_TX))
1842		ifmedia_add(&vsi->media, IFM_ETHER | IFM_100_TX, 0, NULL);
1843
1844	if (phy_types & (I40E_CAP_PHY_TYPE_1000BASE_T))
1845		ifmedia_add(&vsi->media, IFM_ETHER | IFM_1000_T, 0, NULL);
1846	if (phy_types & (I40E_CAP_PHY_TYPE_1000BASE_SX))
1847		ifmedia_add(&vsi->media, IFM_ETHER | IFM_1000_SX, 0, NULL);
1848	if (phy_types & (I40E_CAP_PHY_TYPE_1000BASE_LX))
1849		ifmedia_add(&vsi->media, IFM_ETHER | IFM_1000_LX, 0, NULL);
1850
1851	if (phy_types & (I40E_CAP_PHY_TYPE_2_5GBASE_T))
1852		ifmedia_add(&vsi->media, IFM_ETHER | IFM_2500_T, 0, NULL);
1853
1854	if (phy_types & (I40E_CAP_PHY_TYPE_5GBASE_T))
1855		ifmedia_add(&vsi->media, IFM_ETHER | IFM_5000_T, 0, NULL);
1856
1857	if (phy_types & (I40E_CAP_PHY_TYPE_XAUI) ||
1858	    phy_types & (I40E_CAP_PHY_TYPE_XFI) ||
1859	    phy_types & (I40E_CAP_PHY_TYPE_10GBASE_SFPP_CU))
1860		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_TWINAX, 0, NULL);
1861
1862	if (phy_types & (I40E_CAP_PHY_TYPE_10GBASE_SR))
1863		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_SR, 0, NULL);
1864	if (phy_types & (I40E_CAP_PHY_TYPE_10GBASE_LR))
1865		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_LR, 0, NULL);
1866	if (phy_types & (I40E_CAP_PHY_TYPE_10GBASE_T))
1867		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_T, 0, NULL);
1868
1869	if (phy_types & (I40E_CAP_PHY_TYPE_40GBASE_CR4) ||
1870	    phy_types & (I40E_CAP_PHY_TYPE_40GBASE_CR4_CU) ||
1871	    phy_types & (I40E_CAP_PHY_TYPE_40GBASE_AOC) ||
1872	    phy_types & (I40E_CAP_PHY_TYPE_XLAUI) ||
1873	    phy_types & (I40E_CAP_PHY_TYPE_40GBASE_KR4))
1874		ifmedia_add(&vsi->media, IFM_ETHER | IFM_40G_CR4, 0, NULL);
1875	if (phy_types & (I40E_CAP_PHY_TYPE_40GBASE_SR4))
1876		ifmedia_add(&vsi->media, IFM_ETHER | IFM_40G_SR4, 0, NULL);
1877	if (phy_types & (I40E_CAP_PHY_TYPE_40GBASE_LR4))
1878		ifmedia_add(&vsi->media, IFM_ETHER | IFM_40G_LR4, 0, NULL);
1879
1880	if (phy_types & (I40E_CAP_PHY_TYPE_1000BASE_KX))
1881		ifmedia_add(&vsi->media, IFM_ETHER | IFM_1000_KX, 0, NULL);
1882
1883	if (phy_types & (I40E_CAP_PHY_TYPE_10GBASE_CR1_CU)
1884	    || phy_types & (I40E_CAP_PHY_TYPE_10GBASE_CR1))
1885		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_CR1, 0, NULL);
1886	if (phy_types & (I40E_CAP_PHY_TYPE_10GBASE_AOC))
1887		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_AOC, 0, NULL);
1888	if (phy_types & (I40E_CAP_PHY_TYPE_SFI))
1889		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_SFI, 0, NULL);
1890	if (phy_types & (I40E_CAP_PHY_TYPE_10GBASE_KX4))
1891		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_KX4, 0, NULL);
1892	if (phy_types & (I40E_CAP_PHY_TYPE_10GBASE_KR))
1893		ifmedia_add(&vsi->media, IFM_ETHER | IFM_10G_KR, 0, NULL);
1894
1895	if (phy_types & (I40E_CAP_PHY_TYPE_20GBASE_KR2))
1896		ifmedia_add(&vsi->media, IFM_ETHER | IFM_20G_KR2, 0, NULL);
1897
1898	if (phy_types & (I40E_CAP_PHY_TYPE_40GBASE_KR4))
1899		ifmedia_add(&vsi->media, IFM_ETHER | IFM_40G_KR4, 0, NULL);
1900	if (phy_types & (I40E_CAP_PHY_TYPE_XLPPI))
1901		ifmedia_add(&vsi->media, IFM_ETHER | IFM_40G_XLPPI, 0, NULL);
1902
1903	if (phy_types & (I40E_CAP_PHY_TYPE_25GBASE_KR))
1904		ifmedia_add(&vsi->media, IFM_ETHER | IFM_25G_KR, 0, NULL);
1905	if (phy_types & (I40E_CAP_PHY_TYPE_25GBASE_CR))
1906		ifmedia_add(&vsi->media, IFM_ETHER | IFM_25G_CR, 0, NULL);
1907	if (phy_types & (I40E_CAP_PHY_TYPE_25GBASE_SR))
1908		ifmedia_add(&vsi->media, IFM_ETHER | IFM_25G_SR, 0, NULL);
1909	if (phy_types & (I40E_CAP_PHY_TYPE_25GBASE_LR))
1910		ifmedia_add(&vsi->media, IFM_ETHER | IFM_25G_LR, 0, NULL);
1911	if (phy_types & (I40E_CAP_PHY_TYPE_25GBASE_AOC))
1912		ifmedia_add(&vsi->media, IFM_ETHER | IFM_25G_AOC, 0, NULL);
1913	if (phy_types & (I40E_CAP_PHY_TYPE_25GBASE_ACC))
1914		ifmedia_add(&vsi->media, IFM_ETHER | IFM_25G_ACC, 0, NULL);
1915}
1916
1917/*********************************************************************
1918 *
1919 *  Setup networking device structure and register an interface.
1920 *
1921 **********************************************************************/
1922int
1923ixl_setup_interface(device_t dev, struct ixl_vsi *vsi)
1924{
1925	struct ixl_pf		*pf = (struct ixl_pf *)vsi->back;
1926	struct ifnet		*ifp;
1927	struct i40e_hw		*hw = vsi->hw;
1928	struct ixl_queue	*que = vsi->queues;
1929	struct i40e_aq_get_phy_abilities_resp abilities;
1930	enum i40e_status_code aq_error = 0;
1931
1932	INIT_DEBUGOUT("ixl_setup_interface: begin");
1933
1934	ifp = vsi->ifp = if_alloc(IFT_ETHER);
1935	if (ifp == NULL) {
1936		device_printf(dev, "can not allocate ifnet structure\n");
1937		return (ENOMEM);
1938	}
1939	if_initname(ifp, device_get_name(dev), device_get_unit(dev));
1940	ifp->if_mtu = ETHERMTU;
1941	ifp->if_init = ixl_init;
1942	ifp->if_softc = vsi;
1943	ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
1944	ifp->if_ioctl = ixl_ioctl;
1945
1946#if __FreeBSD_version >= 1100036
1947	if_setgetcounterfn(ifp, ixl_get_counter);
1948#endif
1949
1950	ifp->if_transmit = ixl_mq_start;
1951
1952	ifp->if_qflush = ixl_qflush;
1953
1954	ifp->if_snd.ifq_maxlen = que->num_tx_desc - 2;
1955
1956	vsi->max_frame_size =
1957	    ifp->if_mtu + ETHER_HDR_LEN + ETHER_CRC_LEN
1958	    + ETHER_VLAN_ENCAP_LEN;
1959
1960	/* Set TSO limits */
1961	ifp->if_hw_tsomax = IP_MAXPACKET - (ETHER_HDR_LEN + ETHER_CRC_LEN);
1962	ifp->if_hw_tsomaxsegcount = IXL_MAX_TSO_SEGS;
1963	ifp->if_hw_tsomaxsegsize = IXL_MAX_DMA_SEG_SIZE;
1964
1965	/*
1966	 * Tell the upper layer(s) we support long frames.
1967	 */
1968	ifp->if_hdrlen = sizeof(struct ether_vlan_header);
1969
1970	ifp->if_capabilities |= IFCAP_HWCSUM;
1971	ifp->if_capabilities |= IFCAP_HWCSUM_IPV6;
1972	ifp->if_capabilities |= IFCAP_TSO;
1973	ifp->if_capabilities |= IFCAP_JUMBO_MTU;
1974	ifp->if_capabilities |= IFCAP_LRO;
1975
1976	/* VLAN capabilties */
1977	ifp->if_capabilities |= IFCAP_VLAN_HWTAGGING
1978			     |  IFCAP_VLAN_HWTSO
1979			     |  IFCAP_VLAN_MTU
1980			     |  IFCAP_VLAN_HWCSUM;
1981	ifp->if_capenable = ifp->if_capabilities;
1982
1983	/*
1984	** Don't turn this on by default, if vlans are
1985	** created on another pseudo device (eg. lagg)
1986	** then vlan events are not passed thru, breaking
1987	** operation, but with HW FILTER off it works. If
1988	** using vlans directly on the ixl driver you can
1989	** enable this and get full hardware tag filtering.
1990	*/
1991	ifp->if_capabilities |= IFCAP_VLAN_HWFILTER;
1992
1993	/*
1994	 * Specify the media types supported by this adapter and register
1995	 * callbacks to update media and link information
1996	 */
1997	ifmedia_init(&vsi->media, IFM_IMASK, ixl_media_change,
1998		     ixl_media_status);
1999
2000	if ((atomic_load_acq_int(&pf->state) & IXL_PF_STATE_RECOVERY_MODE) == 0) {
2001		aq_error = i40e_aq_get_phy_capabilities(hw,
2002		    FALSE, TRUE, &abilities, NULL);
2003		/* May need delay to detect fiber correctly */
2004		if (aq_error == I40E_ERR_UNKNOWN_PHY) {
2005			i40e_msec_delay(200);
2006			aq_error = i40e_aq_get_phy_capabilities(hw, FALSE,
2007			    TRUE, &abilities, NULL);
2008		}
2009		if (aq_error) {
2010			if (aq_error == I40E_ERR_UNKNOWN_PHY)
2011				device_printf(dev, "Unknown PHY type detected!\n");
2012			else
2013				device_printf(dev,
2014				    "Error getting supported media types, err %d,"
2015				    " AQ error %d\n", aq_error, hw->aq.asq_last_status);
2016		} else {
2017			pf->supported_speeds = abilities.link_speed;
2018#if __FreeBSD_version >= 1100000
2019			ifp->if_baudrate = ixl_max_aq_speed_to_value(pf->supported_speeds);
2020#else
2021			if_initbaudrate(ifp, ixl_max_aq_speed_to_value(pf->supported_speeds));
2022#endif
2023
2024			ixl_add_ifmedia(vsi, hw->phy.phy_types);
2025		}
2026	}
2027
2028	/* Use autoselect media by default */
2029	ifmedia_add(&vsi->media, IFM_ETHER | IFM_AUTO, 0, NULL);
2030	ifmedia_set(&vsi->media, IFM_ETHER | IFM_AUTO);
2031
2032	ether_ifattach(ifp, hw->mac.addr);
2033
2034	return (0);
2035}
2036
2037/*
2038** Run when the Admin Queue gets a link state change interrupt.
2039*/
2040void
2041ixl_link_event(struct ixl_pf *pf, struct i40e_arq_event_info *e)
2042{
2043	struct i40e_hw	*hw = &pf->hw;
2044	device_t dev = pf->dev;
2045	struct i40e_aqc_get_link_status *status =
2046	    (struct i40e_aqc_get_link_status *)&e->desc.params.raw;
2047
2048	/* Request link status from adapter */
2049	hw->phy.get_link_info = TRUE;
2050	i40e_get_link_status(hw, &pf->link_up);
2051
2052	/* Print out message if an unqualified module is found */
2053	if ((status->link_info & I40E_AQ_MEDIA_AVAILABLE) &&
2054	    (pf->advertised_speed) &&
2055	    (!(status->an_info & I40E_AQ_QUALIFIED_MODULE)) &&
2056	    (!(status->link_info & I40E_AQ_LINK_UP)))
2057		device_printf(dev, "Link failed because "
2058		    "an unqualified module was detected!\n");
2059
2060	/* Update OS link info */
2061	ixl_update_link_status(pf);
2062}
2063
2064/*********************************************************************
2065 *
2066 *  Get Firmware Switch configuration
2067 *	- this will need to be more robust when more complex
2068 *	  switch configurations are enabled.
2069 *
2070 **********************************************************************/
2071int
2072ixl_switch_config(struct ixl_pf *pf)
2073{
2074	struct i40e_hw	*hw = &pf->hw;
2075	struct ixl_vsi	*vsi = &pf->vsi;
2076	device_t 	dev = vsi->dev;
2077	struct i40e_aqc_get_switch_config_resp *sw_config;
2078	u8	aq_buf[I40E_AQ_LARGE_BUF];
2079	int	ret;
2080	u16	next = 0;
2081
2082	memset(&aq_buf, 0, sizeof(aq_buf));
2083	sw_config = (struct i40e_aqc_get_switch_config_resp *)aq_buf;
2084	ret = i40e_aq_get_switch_config(hw, sw_config,
2085	    sizeof(aq_buf), &next, NULL);
2086	if (ret) {
2087		device_printf(dev, "aq_get_switch_config() failed, error %d,"
2088		    " aq_error %d\n", ret, pf->hw.aq.asq_last_status);
2089		return (ret);
2090	}
2091	if (pf->dbg_mask & IXL_DBG_SWITCH_INFO) {
2092		device_printf(dev,
2093		    "Switch config: header reported: %d in structure, %d total\n",
2094		    sw_config->header.num_reported, sw_config->header.num_total);
2095		for (int i = 0; i < sw_config->header.num_reported; i++) {
2096			device_printf(dev,
2097			    "-> %d: type=%d seid=%d uplink=%d downlink=%d\n", i,
2098			    sw_config->element[i].element_type,
2099			    sw_config->element[i].seid,
2100			    sw_config->element[i].uplink_seid,
2101			    sw_config->element[i].downlink_seid);
2102		}
2103	}
2104	/* Simplified due to a single VSI */
2105	vsi->uplink_seid = sw_config->element[0].uplink_seid;
2106	vsi->downlink_seid = sw_config->element[0].downlink_seid;
2107	vsi->seid = sw_config->element[0].seid;
2108	return (ret);
2109}
2110
2111/*********************************************************************
2112 *
2113 *  Initialize the VSI:  this handles contexts, which means things
2114 *  			 like the number of descriptors, buffer size,
2115 *			 plus we init the rings thru this function.
2116 *
2117 **********************************************************************/
2118int
2119ixl_initialize_vsi(struct ixl_vsi *vsi)
2120{
2121	struct ixl_pf		*pf = vsi->back;
2122	struct ixl_queue	*que = vsi->queues;
2123	device_t		dev = vsi->dev;
2124	struct i40e_hw		*hw = vsi->hw;
2125	struct i40e_vsi_context	ctxt;
2126	int 			tc_queues;
2127	int			err = 0;
2128
2129	memset(&ctxt, 0, sizeof(ctxt));
2130	ctxt.seid = vsi->seid;
2131	if (pf->veb_seid != 0)
2132		ctxt.uplink_seid = pf->veb_seid;
2133	ctxt.pf_num = hw->pf_id;
2134	err = i40e_aq_get_vsi_params(hw, &ctxt, NULL);
2135	if (err) {
2136		device_printf(dev, "i40e_aq_get_vsi_params() failed, error %d"
2137		    " aq_error %d\n", err, hw->aq.asq_last_status);
2138		return (err);
2139	}
2140	ixl_dbg(pf, IXL_DBG_SWITCH_INFO,
2141	    "get_vsi_params: seid: %d, uplinkseid: %d, vsi_number: %d, "
2142	    "vsis_allocated: %d, vsis_unallocated: %d, flags: 0x%x, "
2143	    "pfnum: %d, vfnum: %d, stat idx: %d, enabled: %d\n", ctxt.seid,
2144	    ctxt.uplink_seid, ctxt.vsi_number,
2145	    ctxt.vsis_allocated, ctxt.vsis_unallocated,
2146	    ctxt.flags, ctxt.pf_num, ctxt.vf_num,
2147	    ctxt.info.stat_counter_idx, ctxt.info.up_enable_bits);
2148	/*
2149	** Set the queue and traffic class bits
2150	**  - when multiple traffic classes are supported
2151	**    this will need to be more robust.
2152	*/
2153	ctxt.info.valid_sections = I40E_AQ_VSI_PROP_QUEUE_MAP_VALID;
2154	ctxt.info.mapping_flags |= I40E_AQ_VSI_QUE_MAP_CONTIG;
2155	/* In contig mode, que_mapping[0] is first queue index used by this VSI */
2156	ctxt.info.queue_mapping[0] = 0;
2157	/*
2158	 * This VSI will only use traffic class 0; start traffic class 0's
2159	 * queue allocation at queue 0, and assign it 2^tc_queues queues (though
2160	 * the driver may not use all of them).
2161	 */
2162	tc_queues = bsrl(pf->qtag.num_allocated);
2163	ctxt.info.tc_mapping[0] = ((0 << I40E_AQ_VSI_TC_QUE_OFFSET_SHIFT)
2164	    & I40E_AQ_VSI_TC_QUE_OFFSET_MASK) |
2165	    ((tc_queues << I40E_AQ_VSI_TC_QUE_NUMBER_SHIFT)
2166	    & I40E_AQ_VSI_TC_QUE_NUMBER_MASK);
2167
2168	/* Set VLAN receive stripping mode */
2169	ctxt.info.valid_sections |= I40E_AQ_VSI_PROP_VLAN_VALID;
2170	ctxt.info.port_vlan_flags = I40E_AQ_VSI_PVLAN_MODE_ALL;
2171	if (vsi->ifp->if_capenable & IFCAP_VLAN_HWTAGGING)
2172		ctxt.info.port_vlan_flags |= I40E_AQ_VSI_PVLAN_EMOD_STR_BOTH;
2173	else
2174		ctxt.info.port_vlan_flags |= I40E_AQ_VSI_PVLAN_EMOD_NOTHING;
2175
2176#ifdef IXL_IW
2177	/* Set TCP Enable for iWARP capable VSI */
2178	if (ixl_enable_iwarp && pf->iw_enabled) {
2179		ctxt.info.valid_sections |=
2180		    htole16(I40E_AQ_VSI_PROP_QUEUE_OPT_VALID);
2181		ctxt.info.queueing_opt_flags |= I40E_AQ_VSI_QUE_OPT_TCP_ENA;
2182	}
2183#endif
2184	/* Save VSI number and info for use later */
2185	vsi->vsi_num = ctxt.vsi_number;
2186	bcopy(&ctxt.info, &vsi->info, sizeof(vsi->info));
2187
2188	/* Reset VSI statistics */
2189	ixl_vsi_reset_stats(vsi);
2190
2191	ctxt.flags = htole16(I40E_AQ_VSI_TYPE_PF);
2192
2193	err = i40e_aq_update_vsi_params(hw, &ctxt, NULL);
2194	if (err) {
2195		device_printf(dev, "i40e_aq_update_vsi_params() failed, error %d,"
2196		    " aq_error %d\n", err, hw->aq.asq_last_status);
2197		return (err);
2198	}
2199
2200	for (int i = 0; i < vsi->num_queues; i++, que++) {
2201		struct tx_ring		*txr = &que->txr;
2202		struct rx_ring 		*rxr = &que->rxr;
2203		struct i40e_hmc_obj_txq tctx;
2204		struct i40e_hmc_obj_rxq rctx;
2205		u32			txctl;
2206		u16			size;
2207
2208		/* Setup the HMC TX Context  */
2209		size = que->num_tx_desc * sizeof(struct i40e_tx_desc);
2210		bzero(&tctx, sizeof(tctx));
2211		tctx.new_context = 1;
2212		tctx.base = (txr->dma.pa/IXL_TX_CTX_BASE_UNITS);
2213		tctx.qlen = que->num_tx_desc;
2214		tctx.fc_ena = 0;	/* Disable FCoE */
2215		/*
2216		 * This value needs to pulled from the VSI that this queue
2217		 * is assigned to. Index into array is traffic class.
2218		 */
2219		tctx.rdylist = vsi->info.qs_handle[0];
2220		/*
2221		 * Set these to enable Head Writeback
2222		 * - Address is last entry in TX ring (reserved for HWB index)
2223		 * Leave these as 0 for Descriptor Writeback
2224		 */
2225		if (vsi->enable_head_writeback) {
2226			tctx.head_wb_ena = 1;
2227			tctx.head_wb_addr = txr->dma.pa +
2228			    (que->num_tx_desc * sizeof(struct i40e_tx_desc));
2229		}
2230		tctx.rdylist_act = 0;
2231		err = i40e_clear_lan_tx_queue_context(hw, i);
2232		if (err) {
2233			device_printf(dev, "Unable to clear TX context\n");
2234			break;
2235		}
2236		err = i40e_set_lan_tx_queue_context(hw, i, &tctx);
2237		if (err) {
2238			device_printf(dev, "Unable to set TX context\n");
2239			break;
2240		}
2241		/* Associate the ring with this PF */
2242		txctl = I40E_QTX_CTL_PF_QUEUE;
2243		txctl |= ((hw->pf_id << I40E_QTX_CTL_PF_INDX_SHIFT) &
2244		    I40E_QTX_CTL_PF_INDX_MASK);
2245		wr32(hw, I40E_QTX_CTL(i), txctl);
2246		ixl_flush(hw);
2247
2248		/* Do ring (re)init */
2249		ixl_init_tx_ring(que);
2250
2251		/* Next setup the HMC RX Context  */
2252		if (vsi->max_frame_size <= MCLBYTES)
2253			rxr->mbuf_sz = MCLBYTES;
2254		else
2255			rxr->mbuf_sz = MJUMPAGESIZE;
2256
2257		u16 max_rxmax = rxr->mbuf_sz * hw->func_caps.rx_buf_chain_len;
2258
2259		/* Set up an RX context for the HMC */
2260		memset(&rctx, 0, sizeof(struct i40e_hmc_obj_rxq));
2261		rctx.dbuff = rxr->mbuf_sz >> I40E_RXQ_CTX_DBUFF_SHIFT;
2262		/* ignore header split for now */
2263		rctx.hbuff = 0 >> I40E_RXQ_CTX_HBUFF_SHIFT;
2264		rctx.rxmax = (vsi->max_frame_size < max_rxmax) ?
2265		    vsi->max_frame_size : max_rxmax;
2266		rctx.dtype = 0;
2267		rctx.dsize = 1;		/* do 32byte descriptors */
2268		rctx.hsplit_0 = 0;	/* no header split */
2269		rctx.base = (rxr->dma.pa/IXL_RX_CTX_BASE_UNITS);
2270		rctx.qlen = que->num_rx_desc;
2271		rctx.tphrdesc_ena = 1;
2272		rctx.tphwdesc_ena = 1;
2273		rctx.tphdata_ena = 0;	/* Header Split related */
2274		rctx.tphhead_ena = 0;	/* Header Split related */
2275		rctx.lrxqthresh = 2;	/* Interrupt at <128 desc avail */
2276		rctx.crcstrip = 1;
2277		rctx.l2tsel = 1;
2278		rctx.showiv = 1;	/* Strip inner VLAN header */
2279		rctx.fc_ena = 0;	/* Disable FCoE */
2280		rctx.prefena = 1;	/* Prefetch descriptors */
2281
2282		err = i40e_clear_lan_rx_queue_context(hw, i);
2283		if (err) {
2284			device_printf(dev,
2285			    "Unable to clear RX context %d\n", i);
2286			break;
2287		}
2288		err = i40e_set_lan_rx_queue_context(hw, i, &rctx);
2289		if (err) {
2290			device_printf(dev, "Unable to set RX context %d\n", i);
2291			break;
2292		}
2293		err = ixl_init_rx_ring(que);
2294		if (err) {
2295			device_printf(dev, "Fail in init_rx_ring %d\n", i);
2296			break;
2297		}
2298#ifdef DEV_NETMAP
2299		/* preserve queue */
2300		if (vsi->ifp->if_capenable & IFCAP_NETMAP) {
2301			struct netmap_adapter *na = NA(vsi->ifp);
2302			struct netmap_kring *kring = na->rx_rings[i];
2303			int t = na->num_rx_desc - 1 - nm_kr_rxspace(kring);
2304			wr32(vsi->hw, I40E_QRX_TAIL(que->me), t);
2305		} else
2306#endif /* DEV_NETMAP */
2307		wr32(vsi->hw, I40E_QRX_TAIL(que->me), que->num_rx_desc - 1);
2308	}
2309	return (err);
2310}
2311
2312void
2313ixl_vsi_free_queues(struct ixl_vsi *vsi)
2314{
2315	struct ixl_pf		*pf = (struct ixl_pf *)vsi->back;
2316	struct ixl_queue	*que = vsi->queues;
2317
2318	if (NULL == vsi->queues)
2319		return;
2320
2321	for (int i = 0; i < vsi->num_queues; i++, que++) {
2322		struct tx_ring *txr = &que->txr;
2323		struct rx_ring *rxr = &que->rxr;
2324
2325		if (!mtx_initialized(&txr->mtx)) /* uninitialized */
2326			continue;
2327		IXL_TX_LOCK(txr);
2328		if (txr->br)
2329			buf_ring_free(txr->br, M_DEVBUF);
2330		ixl_free_que_tx(que);
2331		if (txr->base)
2332			i40e_free_dma_mem(&pf->hw, &txr->dma);
2333		IXL_TX_UNLOCK(txr);
2334		IXL_TX_LOCK_DESTROY(txr);
2335
2336		if (!mtx_initialized(&rxr->mtx)) /* uninitialized */
2337			continue;
2338		IXL_RX_LOCK(rxr);
2339		ixl_free_que_rx(que);
2340		if (rxr->base)
2341			i40e_free_dma_mem(&pf->hw, &rxr->dma);
2342		IXL_RX_UNLOCK(rxr);
2343		IXL_RX_LOCK_DESTROY(rxr);
2344	}
2345
2346	sysctl_ctx_free(&vsi->sysctl_ctx);
2347}
2348
2349
2350/*********************************************************************
2351 *
2352 *  Free all VSI structs.
2353 *
2354 **********************************************************************/
2355void
2356ixl_free_vsi(struct ixl_vsi *vsi)
2357{
2358	/* Free station queues */
2359	ixl_vsi_free_queues(vsi);
2360	if (vsi->queues)
2361		free(vsi->queues, M_DEVBUF);
2362
2363	/* Free VSI filter list */
2364	ixl_free_mac_filters(vsi);
2365}
2366
2367void
2368ixl_free_mac_filters(struct ixl_vsi *vsi)
2369{
2370	struct ixl_mac_filter *f;
2371
2372	while (!SLIST_EMPTY(&vsi->ftl)) {
2373		f = SLIST_FIRST(&vsi->ftl);
2374		SLIST_REMOVE_HEAD(&vsi->ftl, next);
2375		free(f, M_DEVBUF);
2376	}
2377
2378	vsi->num_hw_filters = 0;
2379}
2380
2381/*
2382 * Fill out fields in queue struct and setup tx/rx memory and structs
2383 */
2384static int
2385ixl_vsi_setup_queue(struct ixl_vsi *vsi, struct ixl_queue *que, int index)
2386{
2387	struct ixl_pf	*pf = (struct ixl_pf *)vsi->back;
2388	device_t dev = pf->dev;
2389	struct i40e_hw *hw = &pf->hw;
2390	struct tx_ring *txr = &que->txr;
2391	struct rx_ring *rxr = &que->rxr;
2392	int error = 0;
2393	int rsize, tsize;
2394
2395	que->num_tx_desc = vsi->num_tx_desc;
2396	que->num_rx_desc = vsi->num_rx_desc;
2397	que->me = index;
2398	que->vsi = vsi;
2399
2400	txr->que = que;
2401	txr->tail = I40E_QTX_TAIL(que->me);
2402
2403	/* Initialize the TX lock */
2404	snprintf(txr->mtx_name, sizeof(txr->mtx_name), "%s:tx(%d)",
2405	    device_get_nameunit(dev), que->me);
2406	mtx_init(&txr->mtx, txr->mtx_name, NULL, MTX_DEF);
2407	/*
2408	 * Create the TX descriptor ring
2409	 *
2410	 * In Head Writeback mode, the descriptor ring is one bigger
2411	 * than the number of descriptors for space for the HW to
2412	 * write back index of last completed descriptor.
2413	 */
2414	if (vsi->enable_head_writeback) {
2415		tsize = roundup2((que->num_tx_desc *
2416		    sizeof(struct i40e_tx_desc)) +
2417		    sizeof(u32), DBA_ALIGN);
2418	} else {
2419		tsize = roundup2((que->num_tx_desc *
2420		    sizeof(struct i40e_tx_desc)), DBA_ALIGN);
2421	}
2422	if (i40e_allocate_dma_mem(hw,
2423	    &txr->dma, i40e_mem_reserved, tsize, DBA_ALIGN)) {
2424		device_printf(dev,
2425		    "Unable to allocate TX Descriptor memory\n");
2426		error = ENOMEM;
2427		goto err_destroy_tx_mtx;
2428	}
2429	txr->base = (struct i40e_tx_desc *)txr->dma.va;
2430	bzero((void *)txr->base, tsize);
2431	/* Now allocate transmit soft structs for the ring */
2432	if (ixl_allocate_tx_data(que)) {
2433		device_printf(dev,
2434		    "Critical Failure setting up TX structures\n");
2435		error = ENOMEM;
2436		goto err_free_tx_dma;
2437	}
2438	/* Allocate a buf ring */
2439	txr->br = buf_ring_alloc(DEFAULT_TXBRSZ, M_DEVBUF,
2440	    M_NOWAIT, &txr->mtx);
2441	if (txr->br == NULL) {
2442		device_printf(dev,
2443		    "Critical Failure setting up TX buf ring\n");
2444		error = ENOMEM;
2445		goto err_free_tx_data;
2446	}
2447
2448	rsize = roundup2(que->num_rx_desc *
2449	    sizeof(union i40e_rx_desc), DBA_ALIGN);
2450	rxr->que = que;
2451	rxr->tail = I40E_QRX_TAIL(que->me);
2452
2453	/* Initialize the RX side lock */
2454	snprintf(rxr->mtx_name, sizeof(rxr->mtx_name), "%s:rx(%d)",
2455	    device_get_nameunit(dev), que->me);
2456	mtx_init(&rxr->mtx, rxr->mtx_name, NULL, MTX_DEF);
2457
2458	if (i40e_allocate_dma_mem(hw,
2459	    &rxr->dma, i40e_mem_reserved, rsize, 4096)) {
2460		device_printf(dev,
2461		    "Unable to allocate RX Descriptor memory\n");
2462		error = ENOMEM;
2463		goto err_destroy_rx_mtx;
2464	}
2465	rxr->base = (union i40e_rx_desc *)rxr->dma.va;
2466	bzero((void *)rxr->base, rsize);
2467	/* Allocate receive soft structs for the ring*/
2468	if (ixl_allocate_rx_data(que)) {
2469		device_printf(dev,
2470		    "Critical Failure setting up receive structs\n");
2471		error = ENOMEM;
2472		goto err_free_rx_dma;
2473	}
2474
2475	return (0);
2476
2477err_free_rx_dma:
2478	i40e_free_dma_mem(&pf->hw, &rxr->dma);
2479err_destroy_rx_mtx:
2480	mtx_destroy(&rxr->mtx);
2481	/* err_free_tx_buf_ring */
2482	buf_ring_free(txr->br, M_DEVBUF);
2483err_free_tx_data:
2484	ixl_free_que_tx(que);
2485err_free_tx_dma:
2486	i40e_free_dma_mem(&pf->hw, &txr->dma);
2487err_destroy_tx_mtx:
2488	mtx_destroy(&txr->mtx);
2489
2490	return (error);
2491}
2492
2493int
2494ixl_vsi_setup_queues(struct ixl_vsi *vsi)
2495{
2496	struct ixl_queue	*que;
2497	int			error = 0;
2498
2499	for (int i = 0; i < vsi->num_queues; i++) {
2500		que = &vsi->queues[i];
2501		error = ixl_vsi_setup_queue(vsi, que, i);
2502		if (error)
2503			break;
2504	}
2505	if (error == 0)
2506		sysctl_ctx_init(&vsi->sysctl_ctx);
2507
2508	return (error);
2509}
2510
2511
2512/*********************************************************************
2513 *
2514 *  Allocate memory for the VSI (virtual station interface) and their
2515 *  associated queues, rings and the descriptors associated with each,
2516 *  called only once at attach.
2517 *
2518 **********************************************************************/
2519int
2520ixl_setup_stations(struct ixl_pf *pf)
2521{
2522	device_t		dev = pf->dev;
2523	struct ixl_vsi		*vsi;
2524	int			error = 0;
2525
2526	vsi = &pf->vsi;
2527	vsi->back = (void *)pf;
2528	vsi->hw = &pf->hw;
2529	vsi->id = 0;
2530	vsi->num_vlans = 0;
2531	vsi->back = pf;
2532
2533	if (pf->msix > 1)
2534		vsi->flags |= IXL_FLAGS_USES_MSIX;
2535
2536	/* Get memory for the station queues */
2537        if (!(vsi->queues =
2538            (struct ixl_queue *) malloc(sizeof(struct ixl_queue) *
2539            vsi->num_queues, M_DEVBUF, M_NOWAIT | M_ZERO))) {
2540                device_printf(dev, "Unable to allocate queue memory\n");
2541                error = ENOMEM;
2542		goto ixl_setup_stations_err;
2543        }
2544
2545	/* Then setup each queue */
2546	error = ixl_vsi_setup_queues(vsi);
2547ixl_setup_stations_err:
2548	return (error);
2549}
2550
2551/*
2552** Provide a update to the queue RX
2553** interrupt moderation value.
2554*/
2555void
2556ixl_set_queue_rx_itr(struct ixl_queue *que)
2557{
2558	struct ixl_vsi	*vsi = que->vsi;
2559	struct ixl_pf	*pf = (struct ixl_pf *)vsi->back;
2560	struct i40e_hw	*hw = vsi->hw;
2561	struct rx_ring	*rxr = &que->rxr;
2562	u16		rx_itr;
2563	u16		rx_latency = 0;
2564	int		rx_bytes;
2565
2566	/* Idle, do nothing */
2567	if (rxr->bytes == 0)
2568		return;
2569
2570	if (pf->dynamic_rx_itr) {
2571		rx_bytes = rxr->bytes/rxr->itr;
2572		rx_itr = rxr->itr;
2573
2574		/* Adjust latency range */
2575		switch (rxr->latency) {
2576		case IXL_LOW_LATENCY:
2577			if (rx_bytes > 10) {
2578				rx_latency = IXL_AVE_LATENCY;
2579				rx_itr = IXL_ITR_20K;
2580			}
2581			break;
2582		case IXL_AVE_LATENCY:
2583			if (rx_bytes > 20) {
2584				rx_latency = IXL_BULK_LATENCY;
2585				rx_itr = IXL_ITR_8K;
2586			} else if (rx_bytes <= 10) {
2587				rx_latency = IXL_LOW_LATENCY;
2588				rx_itr = IXL_ITR_100K;
2589			}
2590			break;
2591		case IXL_BULK_LATENCY:
2592			if (rx_bytes <= 20) {
2593				rx_latency = IXL_AVE_LATENCY;
2594				rx_itr = IXL_ITR_20K;
2595			}
2596			break;
2597       		 }
2598
2599		rxr->latency = rx_latency;
2600
2601		if (rx_itr != rxr->itr) {
2602			/* do an exponential smoothing */
2603			rx_itr = (10 * rx_itr * rxr->itr) /
2604			    ((9 * rx_itr) + rxr->itr);
2605			rxr->itr = min(rx_itr, IXL_MAX_ITR);
2606			wr32(hw, I40E_PFINT_ITRN(IXL_RX_ITR,
2607			    que->me), rxr->itr);
2608		}
2609	} else { /* We may have have toggled to non-dynamic */
2610		if (vsi->rx_itr_setting & IXL_ITR_DYNAMIC)
2611			vsi->rx_itr_setting = pf->rx_itr;
2612		/* Update the hardware if needed */
2613		if (rxr->itr != vsi->rx_itr_setting) {
2614			rxr->itr = vsi->rx_itr_setting;
2615			wr32(hw, I40E_PFINT_ITRN(IXL_RX_ITR,
2616			    que->me), rxr->itr);
2617		}
2618	}
2619	rxr->bytes = 0;
2620	rxr->packets = 0;
2621	return;
2622}
2623
2624
2625/*
2626** Provide a update to the queue TX
2627** interrupt moderation value.
2628*/
2629void
2630ixl_set_queue_tx_itr(struct ixl_queue *que)
2631{
2632	struct ixl_vsi	*vsi = que->vsi;
2633	struct ixl_pf	*pf = (struct ixl_pf *)vsi->back;
2634	struct i40e_hw	*hw = vsi->hw;
2635	struct tx_ring	*txr = &que->txr;
2636	u16		tx_itr;
2637	u16		tx_latency = 0;
2638	int		tx_bytes;
2639
2640
2641	/* Idle, do nothing */
2642	if (txr->bytes == 0)
2643		return;
2644
2645	if (pf->dynamic_tx_itr) {
2646		tx_bytes = txr->bytes/txr->itr;
2647		tx_itr = txr->itr;
2648
2649		switch (txr->latency) {
2650		case IXL_LOW_LATENCY:
2651			if (tx_bytes > 10) {
2652				tx_latency = IXL_AVE_LATENCY;
2653				tx_itr = IXL_ITR_20K;
2654			}
2655			break;
2656		case IXL_AVE_LATENCY:
2657			if (tx_bytes > 20) {
2658				tx_latency = IXL_BULK_LATENCY;
2659				tx_itr = IXL_ITR_8K;
2660			} else if (tx_bytes <= 10) {
2661				tx_latency = IXL_LOW_LATENCY;
2662				tx_itr = IXL_ITR_100K;
2663			}
2664			break;
2665		case IXL_BULK_LATENCY:
2666			if (tx_bytes <= 20) {
2667				tx_latency = IXL_AVE_LATENCY;
2668				tx_itr = IXL_ITR_20K;
2669			}
2670			break;
2671		}
2672
2673		txr->latency = tx_latency;
2674
2675		if (tx_itr != txr->itr) {
2676       	         /* do an exponential smoothing */
2677			tx_itr = (10 * tx_itr * txr->itr) /
2678			    ((9 * tx_itr) + txr->itr);
2679			txr->itr = min(tx_itr, IXL_MAX_ITR);
2680			wr32(hw, I40E_PFINT_ITRN(IXL_TX_ITR,
2681			    que->me), txr->itr);
2682		}
2683
2684	} else { /* We may have have toggled to non-dynamic */
2685		if (vsi->tx_itr_setting & IXL_ITR_DYNAMIC)
2686			vsi->tx_itr_setting = pf->tx_itr;
2687		/* Update the hardware if needed */
2688		if (txr->itr != vsi->tx_itr_setting) {
2689			txr->itr = vsi->tx_itr_setting;
2690			wr32(hw, I40E_PFINT_ITRN(IXL_TX_ITR,
2691			    que->me), txr->itr);
2692		}
2693	}
2694	txr->bytes = 0;
2695	txr->packets = 0;
2696	return;
2697}
2698
2699void
2700ixl_vsi_add_sysctls(struct ixl_vsi * vsi, const char * sysctl_name, bool queues_sysctls)
2701{
2702	struct sysctl_oid *tree;
2703	struct sysctl_oid_list *child;
2704	struct sysctl_oid_list *vsi_list;
2705
2706	tree = device_get_sysctl_tree(vsi->dev);
2707	child = SYSCTL_CHILDREN(tree);
2708	vsi->vsi_node = SYSCTL_ADD_NODE(&vsi->sysctl_ctx, child, OID_AUTO, sysctl_name,
2709			CTLFLAG_RD, NULL, "VSI Number");
2710
2711	vsi_list = SYSCTL_CHILDREN(vsi->vsi_node);
2712	ixl_add_sysctls_eth_stats(&vsi->sysctl_ctx, vsi_list, &vsi->eth_stats);
2713
2714	if (queues_sysctls)
2715		ixl_vsi_add_queues_stats(vsi);
2716}
2717
2718/*
2719 * Used to set the Tx ITR value for all of the PF LAN VSI's queues.
2720 * Writes to the ITR registers immediately.
2721 */
2722static int
2723ixl_sysctl_pf_tx_itr(SYSCTL_HANDLER_ARGS)
2724{
2725	struct ixl_pf *pf = (struct ixl_pf *)arg1;
2726	device_t dev = pf->dev;
2727	int error = 0;
2728	int requested_tx_itr;
2729
2730	requested_tx_itr = pf->tx_itr;
2731	error = sysctl_handle_int(oidp, &requested_tx_itr, 0, req);
2732	if ((error) || (req->newptr == NULL))
2733		return (error);
2734	if (pf->dynamic_tx_itr) {
2735		device_printf(dev,
2736		    "Cannot set TX itr value while dynamic TX itr is enabled\n");
2737		    return (EINVAL);
2738	}
2739	if (requested_tx_itr < 0 || requested_tx_itr > IXL_MAX_ITR) {
2740		device_printf(dev,
2741		    "Invalid TX itr value; value must be between 0 and %d\n",
2742		        IXL_MAX_ITR);
2743		return (EINVAL);
2744	}
2745
2746	pf->tx_itr = requested_tx_itr;
2747	ixl_configure_tx_itr(pf);
2748
2749	return (error);
2750}
2751
2752/*
2753 * Used to set the Rx ITR value for all of the PF LAN VSI's queues.
2754 * Writes to the ITR registers immediately.
2755 */
2756static int
2757ixl_sysctl_pf_rx_itr(SYSCTL_HANDLER_ARGS)
2758{
2759	struct ixl_pf *pf = (struct ixl_pf *)arg1;
2760	device_t dev = pf->dev;
2761	int error = 0;
2762	int requested_rx_itr;
2763
2764	requested_rx_itr = pf->rx_itr;
2765	error = sysctl_handle_int(oidp, &requested_rx_itr, 0, req);
2766	if ((error) || (req->newptr == NULL))
2767		return (error);
2768	if (pf->dynamic_rx_itr) {
2769		device_printf(dev,
2770		    "Cannot set RX itr value while dynamic RX itr is enabled\n");
2771		    return (EINVAL);
2772	}
2773	if (requested_rx_itr < 0 || requested_rx_itr > IXL_MAX_ITR) {
2774		device_printf(dev,
2775		    "Invalid RX itr value; value must be between 0 and %d\n",
2776		        IXL_MAX_ITR);
2777		return (EINVAL);
2778	}
2779
2780	pf->rx_itr = requested_rx_itr;
2781	ixl_configure_rx_itr(pf);
2782
2783	return (error);
2784}
2785
2786void
2787ixl_add_hw_stats(struct ixl_pf *pf)
2788{
2789	device_t dev = pf->dev;
2790	struct i40e_hw_port_stats *pf_stats = &pf->stats;
2791
2792	struct sysctl_ctx_list *ctx = device_get_sysctl_ctx(dev);
2793	struct sysctl_oid *tree = device_get_sysctl_tree(dev);
2794	struct sysctl_oid_list *child = SYSCTL_CHILDREN(tree);
2795
2796	/* Driver statistics */
2797	SYSCTL_ADD_UQUAD(ctx, child, OID_AUTO, "watchdog_events",
2798			CTLFLAG_RD, &pf->watchdog_events,
2799			"Watchdog timeouts");
2800	SYSCTL_ADD_UQUAD(ctx, child, OID_AUTO, "admin_irq",
2801			CTLFLAG_RD, &pf->admin_irq,
2802			"Admin Queue IRQ Handled");
2803
2804	ixl_vsi_add_sysctls(&pf->vsi, "pf", true);
2805	/* MAC stats */
2806	ixl_add_sysctls_mac_stats(ctx, child, pf_stats);
2807}
2808
2809void
2810ixl_add_sysctls_mac_stats(struct sysctl_ctx_list *ctx,
2811	struct sysctl_oid_list *child,
2812	struct i40e_hw_port_stats *stats)
2813{
2814	struct sysctl_oid *stat_node = SYSCTL_ADD_NODE(ctx, child, OID_AUTO, "mac",
2815				    CTLFLAG_RD, NULL, "Mac Statistics");
2816	struct sysctl_oid_list *stat_list = SYSCTL_CHILDREN(stat_node);
2817
2818	struct i40e_eth_stats *eth_stats = &stats->eth;
2819	ixl_add_sysctls_eth_stats(ctx, stat_list, eth_stats);
2820
2821	struct ixl_sysctl_info ctls[] =
2822	{
2823		{&stats->crc_errors, "crc_errors", "CRC Errors"},
2824		{&stats->illegal_bytes, "illegal_bytes", "Illegal Byte Errors"},
2825		{&stats->mac_local_faults, "local_faults", "MAC Local Faults"},
2826		{&stats->mac_remote_faults, "remote_faults", "MAC Remote Faults"},
2827		{&stats->rx_length_errors, "rx_length_errors", "Receive Length Errors"},
2828		/* Packet Reception Stats */
2829		{&stats->rx_size_64, "rx_frames_64", "64 byte frames received"},
2830		{&stats->rx_size_127, "rx_frames_65_127", "65-127 byte frames received"},
2831		{&stats->rx_size_255, "rx_frames_128_255", "128-255 byte frames received"},
2832		{&stats->rx_size_511, "rx_frames_256_511", "256-511 byte frames received"},
2833		{&stats->rx_size_1023, "rx_frames_512_1023", "512-1023 byte frames received"},
2834		{&stats->rx_size_1522, "rx_frames_1024_1522", "1024-1522 byte frames received"},
2835		{&stats->rx_size_big, "rx_frames_big", "1523-9522 byte frames received"},
2836		{&stats->rx_undersize, "rx_undersize", "Undersized packets received"},
2837		{&stats->rx_fragments, "rx_fragmented", "Fragmented packets received"},
2838		{&stats->rx_oversize, "rx_oversized", "Oversized packets received"},
2839		{&stats->rx_jabber, "rx_jabber", "Received Jabber"},
2840		{&stats->checksum_error, "checksum_errors", "Checksum Errors"},
2841		/* Packet Transmission Stats */
2842		{&stats->tx_size_64, "tx_frames_64", "64 byte frames transmitted"},
2843		{&stats->tx_size_127, "tx_frames_65_127", "65-127 byte frames transmitted"},
2844		{&stats->tx_size_255, "tx_frames_128_255", "128-255 byte frames transmitted"},
2845		{&stats->tx_size_511, "tx_frames_256_511", "256-511 byte frames transmitted"},
2846		{&stats->tx_size_1023, "tx_frames_512_1023", "512-1023 byte frames transmitted"},
2847		{&stats->tx_size_1522, "tx_frames_1024_1522", "1024-1522 byte frames transmitted"},
2848		{&stats->tx_size_big, "tx_frames_big", "1523-9522 byte frames transmitted"},
2849		/* Flow control */
2850		{&stats->link_xon_tx, "xon_txd", "Link XON transmitted"},
2851		{&stats->link_xon_rx, "xon_recvd", "Link XON received"},
2852		{&stats->link_xoff_tx, "xoff_txd", "Link XOFF transmitted"},
2853		{&stats->link_xoff_rx, "xoff_recvd", "Link XOFF received"},
2854		/* End */
2855		{0,0,0}
2856	};
2857
2858	struct ixl_sysctl_info *entry = ctls;
2859	while (entry->stat != 0)
2860	{
2861		SYSCTL_ADD_UQUAD(ctx, stat_list, OID_AUTO, entry->name,
2862				CTLFLAG_RD, entry->stat,
2863				entry->description);
2864		entry++;
2865	}
2866}
2867
2868void
2869ixl_set_rss_key(struct ixl_pf *pf)
2870{
2871	struct i40e_hw *hw = &pf->hw;
2872	struct ixl_vsi *vsi = &pf->vsi;
2873	device_t	dev = pf->dev;
2874	u32 rss_seed[IXL_RSS_KEY_SIZE_REG];
2875	enum i40e_status_code status;
2876
2877#ifdef RSS
2878        /* Fetch the configured RSS key */
2879        rss_getkey((uint8_t *) &rss_seed);
2880#else
2881	ixl_get_default_rss_key(rss_seed);
2882#endif
2883	/* Fill out hash function seed */
2884	if (hw->mac.type == I40E_MAC_X722) {
2885		struct i40e_aqc_get_set_rss_key_data key_data;
2886		bcopy(rss_seed, &key_data, 52);
2887		status = i40e_aq_set_rss_key(hw, vsi->vsi_num, &key_data);
2888		if (status)
2889			device_printf(dev,
2890			    "i40e_aq_set_rss_key status %s, error %s\n",
2891			    i40e_stat_str(hw, status),
2892			    i40e_aq_str(hw, hw->aq.asq_last_status));
2893	} else {
2894		for (int i = 0; i < IXL_RSS_KEY_SIZE_REG; i++)
2895			i40e_write_rx_ctl(hw, I40E_PFQF_HKEY(i), rss_seed[i]);
2896	}
2897}
2898
2899/*
2900 * Configure enabled PCTYPES for RSS.
2901 */
2902void
2903ixl_set_rss_pctypes(struct ixl_pf *pf)
2904{
2905	struct i40e_hw *hw = &pf->hw;
2906	u64		set_hena = 0, hena;
2907
2908#ifdef RSS
2909	u32		rss_hash_config;
2910
2911	rss_hash_config = rss_gethashconfig();
2912	if (rss_hash_config & RSS_HASHTYPE_RSS_IPV4)
2913                set_hena |= ((u64)1 << I40E_FILTER_PCTYPE_NONF_IPV4_OTHER);
2914	if (rss_hash_config & RSS_HASHTYPE_RSS_TCP_IPV4)
2915                set_hena |= ((u64)1 << I40E_FILTER_PCTYPE_NONF_IPV4_TCP);
2916	if (rss_hash_config & RSS_HASHTYPE_RSS_UDP_IPV4)
2917                set_hena |= ((u64)1 << I40E_FILTER_PCTYPE_NONF_IPV4_UDP);
2918	if (rss_hash_config & RSS_HASHTYPE_RSS_IPV6)
2919                set_hena |= ((u64)1 << I40E_FILTER_PCTYPE_NONF_IPV6_OTHER);
2920	if (rss_hash_config & RSS_HASHTYPE_RSS_IPV6_EX)
2921		set_hena |= ((u64)1 << I40E_FILTER_PCTYPE_FRAG_IPV6);
2922	if (rss_hash_config & RSS_HASHTYPE_RSS_TCP_IPV6)
2923                set_hena |= ((u64)1 << I40E_FILTER_PCTYPE_NONF_IPV6_TCP);
2924        if (rss_hash_config & RSS_HASHTYPE_RSS_UDP_IPV6)
2925                set_hena |= ((u64)1 << I40E_FILTER_PCTYPE_NONF_IPV6_UDP);
2926#else
2927	if (hw->mac.type == I40E_MAC_X722)
2928		set_hena = IXL_DEFAULT_RSS_HENA_X722;
2929	else
2930		set_hena = IXL_DEFAULT_RSS_HENA_XL710;
2931#endif
2932	hena = (u64)i40e_read_rx_ctl(hw, I40E_PFQF_HENA(0)) |
2933	    ((u64)i40e_read_rx_ctl(hw, I40E_PFQF_HENA(1)) << 32);
2934	hena |= set_hena;
2935	i40e_write_rx_ctl(hw, I40E_PFQF_HENA(0), (u32)hena);
2936	i40e_write_rx_ctl(hw, I40E_PFQF_HENA(1), (u32)(hena >> 32));
2937
2938}
2939
2940void
2941ixl_set_rss_hlut(struct ixl_pf *pf)
2942{
2943	struct i40e_hw	*hw = &pf->hw;
2944	device_t	dev = pf->dev;
2945	struct ixl_vsi *vsi = &pf->vsi;
2946	int		i, que_id;
2947	int		lut_entry_width;
2948	u32		lut = 0;
2949	enum i40e_status_code status;
2950
2951	lut_entry_width = pf->hw.func_caps.rss_table_entry_width;
2952
2953	/* Populate the LUT with max no. of queues in round robin fashion */
2954	u8 hlut_buf[512];
2955	for (i = 0; i < pf->hw.func_caps.rss_table_size; i++) {
2956#ifdef RSS
2957		/*
2958		 * Fetch the RSS bucket id for the given indirection entry.
2959		 * Cap it at the number of configured buckets (which is
2960		 * num_queues.)
2961		 */
2962		que_id = rss_get_indirection_to_bucket(i);
2963		que_id = que_id % vsi->num_queues;
2964#else
2965		que_id = i % vsi->num_queues;
2966#endif
2967		lut = (que_id & ((0x1 << lut_entry_width) - 1));
2968		hlut_buf[i] = lut;
2969	}
2970
2971	if (hw->mac.type == I40E_MAC_X722) {
2972		status = i40e_aq_set_rss_lut(hw, vsi->vsi_num, TRUE, hlut_buf, sizeof(hlut_buf));
2973		if (status)
2974			device_printf(dev, "i40e_aq_set_rss_lut status %s, error %s\n",
2975			    i40e_stat_str(hw, status), i40e_aq_str(hw, hw->aq.asq_last_status));
2976	} else {
2977		for (i = 0; i < pf->hw.func_caps.rss_table_size >> 2; i++)
2978			wr32(hw, I40E_PFQF_HLUT(i), ((u32 *)hlut_buf)[i]);
2979		ixl_flush(hw);
2980	}
2981}
2982
2983/*
2984** Setup the PF's RSS parameters.
2985*/
2986void
2987ixl_config_rss(struct ixl_pf *pf)
2988{
2989	ixl_set_rss_key(pf);
2990	ixl_set_rss_pctypes(pf);
2991	ixl_set_rss_hlut(pf);
2992}
2993
2994/*
2995** This routine is run via an vlan config EVENT,
2996** it enables us to use the HW Filter table since
2997** we can get the vlan id. This just creates the
2998** entry in the soft version of the VFTA, init will
2999** repopulate the real table.
3000*/
3001void
3002ixl_register_vlan(void *arg, struct ifnet *ifp, u16 vtag)
3003{
3004	struct ixl_vsi	*vsi = ifp->if_softc;
3005	struct i40e_hw	*hw = vsi->hw;
3006	struct ixl_pf	*pf = (struct ixl_pf *)vsi->back;
3007
3008	if (ifp->if_softc !=  arg)   /* Not our event */
3009		return;
3010
3011	if ((vtag == 0) || (vtag > 4095))	/* Invalid */
3012		return;
3013
3014	IXL_PF_LOCK(pf);
3015	++vsi->num_vlans;
3016	ixl_add_filter(vsi, hw->mac.addr, vtag);
3017	IXL_PF_UNLOCK(pf);
3018}
3019
3020/*
3021** This routine is run via an vlan
3022** unconfig EVENT, remove our entry
3023** in the soft vfta.
3024*/
3025void
3026ixl_unregister_vlan(void *arg, struct ifnet *ifp, u16 vtag)
3027{
3028	struct ixl_vsi	*vsi = ifp->if_softc;
3029	struct i40e_hw	*hw = vsi->hw;
3030	struct ixl_pf	*pf = (struct ixl_pf *)vsi->back;
3031
3032	if (ifp->if_softc !=  arg)
3033		return;
3034
3035	if ((vtag == 0) || (vtag > 4095))	/* Invalid */
3036		return;
3037
3038	IXL_PF_LOCK(pf);
3039	--vsi->num_vlans;
3040	ixl_del_filter(vsi, hw->mac.addr, vtag);
3041	IXL_PF_UNLOCK(pf);
3042}
3043
3044/*
3045 * In some firmware versions there is default MAC/VLAN filter
3046 * configured which interferes with filters managed by driver.
3047 * Make sure it's removed.
3048 */
3049void
3050ixl_del_default_hw_filters(struct ixl_vsi *vsi)
3051{
3052	struct i40e_aqc_remove_macvlan_element_data e;
3053
3054	bzero(&e, sizeof(e));
3055	bcopy(vsi->hw->mac.perm_addr, e.mac_addr, ETHER_ADDR_LEN);
3056	e.vlan_tag = 0;
3057	e.flags = I40E_AQC_MACVLAN_DEL_PERFECT_MATCH;
3058	i40e_aq_remove_macvlan(vsi->hw, vsi->seid, &e, 1, NULL);
3059
3060	bzero(&e, sizeof(e));
3061	bcopy(vsi->hw->mac.perm_addr, e.mac_addr, ETHER_ADDR_LEN);
3062	e.vlan_tag = 0;
3063	e.flags = I40E_AQC_MACVLAN_DEL_PERFECT_MATCH |
3064		I40E_AQC_MACVLAN_DEL_IGNORE_VLAN;
3065	i40e_aq_remove_macvlan(vsi->hw, vsi->seid, &e, 1, NULL);
3066}
3067
3068static enum i40e_status_code
3069ixl_set_lla(struct ixl_vsi *vsi)
3070{
3071	struct i40e_hw	*hw = vsi->hw;
3072	u8		tmpaddr[ETHER_ADDR_LEN];
3073	enum i40e_status_code status;
3074
3075	status = I40E_SUCCESS;
3076
3077	bcopy(IF_LLADDR(vsi->ifp), tmpaddr, ETHER_ADDR_LEN);
3078	if (memcmp(hw->mac.addr, tmpaddr, ETHER_ADDR_LEN) == 0)
3079		goto set_lla_exit;
3080
3081	status = i40e_validate_mac_addr(tmpaddr);
3082	if (status != I40E_SUCCESS)
3083		goto set_lla_exit;
3084
3085	ixl_del_filter(vsi, hw->mac.addr, IXL_VLAN_ANY);
3086	bcopy(tmpaddr, hw->mac.addr, ETHER_ADDR_LEN);
3087	status = i40e_aq_mac_address_write(hw,
3088			I40E_AQC_WRITE_TYPE_LAA_ONLY,
3089			hw->mac.addr, NULL);
3090	if (status != I40E_SUCCESS)
3091		goto set_lla_exit;
3092
3093	ixl_add_filter(vsi, hw->mac.addr, IXL_VLAN_ANY);
3094set_lla_exit:
3095	return (status);
3096}
3097
3098/*
3099** Initialize filter list and add filters that the hardware
3100** needs to know about.
3101**
3102** Requires VSI's seid to be set before calling.
3103*/
3104void
3105ixl_init_filters(struct ixl_vsi *vsi)
3106{
3107	struct ixl_pf *pf = (struct ixl_pf *)vsi->back;
3108
3109	/* Initialize mac filter list for VSI */
3110	SLIST_INIT(&vsi->ftl);
3111	vsi->num_hw_filters = 0;
3112
3113	/* Add broadcast address */
3114	ixl_add_filter(vsi, ixl_bcast_addr, IXL_VLAN_ANY);
3115
3116	if (IXL_VSI_IS_VF(vsi))
3117		return;
3118
3119	ixl_del_default_hw_filters(vsi);
3120
3121	ixl_add_filter(vsi, vsi->hw->mac.addr, IXL_VLAN_ANY);
3122
3123	/*
3124	 * Prevent Tx flow control frames from being sent out by
3125	 * non-firmware transmitters.
3126	 * This affects every VSI in the PF.
3127	 */
3128	if (pf->enable_tx_fc_filter)
3129		i40e_add_filter_to_drop_tx_flow_control_frames(vsi->hw, vsi->seid);
3130}
3131
3132/*
3133** This routine adds mulicast filters
3134*/
3135void
3136ixl_add_mc_filter(struct ixl_vsi *vsi, u8 *macaddr)
3137{
3138	struct ixl_mac_filter *f;
3139
3140	/* Does one already exist */
3141	f = ixl_find_filter(vsi, macaddr, IXL_VLAN_ANY);
3142	if (f != NULL)
3143		return;
3144
3145	f = ixl_get_filter(vsi);
3146	if (f == NULL) {
3147		printf("WARNING: no filter available!!\n");
3148		return;
3149	}
3150	bcopy(macaddr, f->macaddr, ETHER_ADDR_LEN);
3151	f->vlan = IXL_VLAN_ANY;
3152	f->flags |= (IXL_FILTER_ADD | IXL_FILTER_USED
3153	    | IXL_FILTER_MC);
3154
3155	return;
3156}
3157
3158void
3159ixl_reconfigure_filters(struct ixl_vsi *vsi)
3160{
3161	ixl_add_hw_filters(vsi, IXL_FILTER_USED, vsi->num_hw_filters);
3162}
3163
3164/*
3165** This routine adds macvlan filters
3166*/
3167void
3168ixl_add_filter(struct ixl_vsi *vsi, const u8 *macaddr, s16 vlan)
3169{
3170	struct ixl_mac_filter	*f, *tmp;
3171	struct ixl_pf		*pf;
3172	device_t		dev;
3173
3174	DEBUGOUT("ixl_add_filter: begin");
3175
3176	pf = vsi->back;
3177	dev = pf->dev;
3178
3179	/* Does one already exist */
3180	f = ixl_find_filter(vsi, macaddr, vlan);
3181	if (f != NULL)
3182		return;
3183	/*
3184	** Is this the first vlan being registered, if so we
3185	** need to remove the ANY filter that indicates we are
3186	** not in a vlan, and replace that with a 0 filter.
3187	*/
3188	if ((vlan != IXL_VLAN_ANY) && (vsi->num_vlans == 1)) {
3189		tmp = ixl_find_filter(vsi, macaddr, IXL_VLAN_ANY);
3190		if (tmp != NULL) {
3191			ixl_del_filter(vsi, macaddr, IXL_VLAN_ANY);
3192			ixl_add_filter(vsi, macaddr, 0);
3193		}
3194	}
3195
3196	f = ixl_get_filter(vsi);
3197	if (f == NULL) {
3198		device_printf(dev, "WARNING: no filter available!!\n");
3199		return;
3200	}
3201	bcopy(macaddr, f->macaddr, ETHER_ADDR_LEN);
3202	f->vlan = vlan;
3203	f->flags |= (IXL_FILTER_ADD | IXL_FILTER_USED);
3204	if (f->vlan != IXL_VLAN_ANY)
3205		f->flags |= IXL_FILTER_VLAN;
3206	else
3207		vsi->num_macs++;
3208
3209	ixl_add_hw_filters(vsi, f->flags, 1);
3210	return;
3211}
3212
3213void
3214ixl_del_filter(struct ixl_vsi *vsi, const u8 *macaddr, s16 vlan)
3215{
3216	struct ixl_mac_filter *f;
3217
3218	f = ixl_find_filter(vsi, macaddr, vlan);
3219	if (f == NULL)
3220		return;
3221
3222	f->flags |= IXL_FILTER_DEL;
3223	ixl_del_hw_filters(vsi, 1);
3224	vsi->num_macs--;
3225
3226	/* Check if this is the last vlan removal */
3227	if (vlan != IXL_VLAN_ANY && vsi->num_vlans == 0) {
3228		/* Switch back to a non-vlan filter */
3229		ixl_del_filter(vsi, macaddr, 0);
3230		ixl_add_filter(vsi, macaddr, IXL_VLAN_ANY);
3231	}
3232	return;
3233}
3234
3235/*
3236** Find the filter with both matching mac addr and vlan id
3237*/
3238struct ixl_mac_filter *
3239ixl_find_filter(struct ixl_vsi *vsi, const u8 *macaddr, s16 vlan)
3240{
3241	struct ixl_mac_filter	*f;
3242	bool			match = FALSE;
3243
3244	SLIST_FOREACH(f, &vsi->ftl, next) {
3245		if (!cmp_etheraddr(f->macaddr, macaddr))
3246			continue;
3247		if (f->vlan == vlan) {
3248			match = TRUE;
3249			break;
3250		}
3251	}
3252
3253	if (!match)
3254		f = NULL;
3255	return (f);
3256}
3257
3258/*
3259** This routine takes additions to the vsi filter
3260** table and creates an Admin Queue call to create
3261** the filters in the hardware.
3262*/
3263void
3264ixl_add_hw_filters(struct ixl_vsi *vsi, int flags, int cnt)
3265{
3266	struct i40e_aqc_add_macvlan_element_data *a, *b;
3267	struct ixl_mac_filter	*f;
3268	struct ixl_pf		*pf;
3269	struct i40e_hw		*hw;
3270	device_t		dev;
3271	int			err, j = 0;
3272
3273	pf = vsi->back;
3274	dev = pf->dev;
3275	hw = &pf->hw;
3276	IXL_PF_LOCK_ASSERT(pf);
3277
3278	a = malloc(sizeof(struct i40e_aqc_add_macvlan_element_data) * cnt,
3279	    M_DEVBUF, M_NOWAIT | M_ZERO);
3280	if (a == NULL) {
3281		device_printf(dev, "add_hw_filters failed to get memory\n");
3282		return;
3283	}
3284
3285	/*
3286	** Scan the filter list, each time we find one
3287	** we add it to the admin queue array and turn off
3288	** the add bit.
3289	*/
3290	SLIST_FOREACH(f, &vsi->ftl, next) {
3291		if ((f->flags & flags) == flags) {
3292			b = &a[j]; // a pox on fvl long names :)
3293			bcopy(f->macaddr, b->mac_addr, ETHER_ADDR_LEN);
3294			if (f->vlan == IXL_VLAN_ANY) {
3295				b->vlan_tag = 0;
3296				b->flags = I40E_AQC_MACVLAN_ADD_IGNORE_VLAN;
3297			} else {
3298				b->vlan_tag = f->vlan;
3299				b->flags = 0;
3300			}
3301			b->flags |= I40E_AQC_MACVLAN_ADD_PERFECT_MATCH;
3302			f->flags &= ~IXL_FILTER_ADD;
3303			j++;
3304		}
3305		if (j == cnt)
3306			break;
3307	}
3308	if (j > 0) {
3309		err = i40e_aq_add_macvlan(hw, vsi->seid, a, j, NULL);
3310		if (err)
3311			device_printf(dev, "aq_add_macvlan err %d, "
3312			    "aq_error %d\n", err, hw->aq.asq_last_status);
3313		else
3314			vsi->num_hw_filters += j;
3315	}
3316	free(a, M_DEVBUF);
3317	return;
3318}
3319
3320/*
3321** This routine takes removals in the vsi filter
3322** table and creates an Admin Queue call to delete
3323** the filters in the hardware.
3324*/
3325void
3326ixl_del_hw_filters(struct ixl_vsi *vsi, int cnt)
3327{
3328	struct i40e_aqc_remove_macvlan_element_data *d, *e;
3329	struct ixl_pf		*pf;
3330	struct i40e_hw		*hw;
3331	device_t		dev;
3332	struct ixl_mac_filter	*f, *f_temp;
3333	int			err, j = 0;
3334
3335	DEBUGOUT("ixl_del_hw_filters: begin\n");
3336
3337	pf = vsi->back;
3338	hw = &pf->hw;
3339	dev = pf->dev;
3340
3341	d = malloc(sizeof(struct i40e_aqc_remove_macvlan_element_data) * cnt,
3342	    M_DEVBUF, M_NOWAIT | M_ZERO);
3343	if (d == NULL) {
3344		printf("del hw filter failed to get memory\n");
3345		return;
3346	}
3347
3348	SLIST_FOREACH_SAFE(f, &vsi->ftl, next, f_temp) {
3349		if (f->flags & IXL_FILTER_DEL) {
3350			e = &d[j]; // a pox on fvl long names :)
3351			bcopy(f->macaddr, e->mac_addr, ETHER_ADDR_LEN);
3352			e->flags = I40E_AQC_MACVLAN_DEL_PERFECT_MATCH;
3353			if (f->vlan == IXL_VLAN_ANY) {
3354				e->vlan_tag = 0;
3355				e->flags |= I40E_AQC_MACVLAN_DEL_IGNORE_VLAN;
3356			} else {
3357				e->vlan_tag = f->vlan;
3358			}
3359			/* delete entry from vsi list */
3360			SLIST_REMOVE(&vsi->ftl, f, ixl_mac_filter, next);
3361			free(f, M_DEVBUF);
3362			j++;
3363		}
3364		if (j == cnt)
3365			break;
3366	}
3367	if (j > 0) {
3368		err = i40e_aq_remove_macvlan(hw, vsi->seid, d, j, NULL);
3369		if (err && hw->aq.asq_last_status != I40E_AQ_RC_ENOENT) {
3370			int sc = 0;
3371			for (int i = 0; i < j; i++)
3372				sc += (!d[i].error_code);
3373			vsi->num_hw_filters -= sc;
3374			device_printf(dev,
3375			    "Failed to remove %d/%d filters, aq error %d\n",
3376			    j - sc, j, hw->aq.asq_last_status);
3377		} else
3378			vsi->num_hw_filters -= j;
3379	}
3380	free(d, M_DEVBUF);
3381
3382	DEBUGOUT("ixl_del_hw_filters: end\n");
3383	return;
3384}
3385
3386int
3387ixl_enable_tx_ring(struct ixl_pf *pf, struct ixl_pf_qtag *qtag, u16 vsi_qidx)
3388{
3389	struct i40e_hw	*hw = &pf->hw;
3390	int		error = 0;
3391	u32		reg;
3392	u16		pf_qidx;
3393
3394	pf_qidx = ixl_pf_qidx_from_vsi_qidx(qtag, vsi_qidx);
3395
3396	ixl_dbg(pf, IXL_DBG_EN_DIS,
3397	    "Enabling PF TX ring %4d / VSI TX ring %4d...\n",
3398	    pf_qidx, vsi_qidx);
3399
3400	i40e_pre_tx_queue_cfg(hw, pf_qidx, TRUE);
3401
3402	reg = rd32(hw, I40E_QTX_ENA(pf_qidx));
3403	reg |= I40E_QTX_ENA_QENA_REQ_MASK |
3404	    I40E_QTX_ENA_QENA_STAT_MASK;
3405	wr32(hw, I40E_QTX_ENA(pf_qidx), reg);
3406	/* Verify the enable took */
3407	for (int j = 0; j < 10; j++) {
3408		reg = rd32(hw, I40E_QTX_ENA(pf_qidx));
3409		if (reg & I40E_QTX_ENA_QENA_STAT_MASK)
3410			break;
3411		i40e_usec_delay(10);
3412	}
3413	if ((reg & I40E_QTX_ENA_QENA_STAT_MASK) == 0) {
3414		device_printf(pf->dev, "TX queue %d still disabled!\n",
3415		    pf_qidx);
3416		error = ETIMEDOUT;
3417	}
3418
3419	return (error);
3420}
3421
3422int
3423ixl_enable_rx_ring(struct ixl_pf *pf, struct ixl_pf_qtag *qtag, u16 vsi_qidx)
3424{
3425	struct i40e_hw	*hw = &pf->hw;
3426	int		error = 0;
3427	u32		reg;
3428	u16		pf_qidx;
3429
3430	pf_qidx = ixl_pf_qidx_from_vsi_qidx(qtag, vsi_qidx);
3431
3432	ixl_dbg(pf, IXL_DBG_EN_DIS,
3433	    "Enabling PF RX ring %4d / VSI RX ring %4d...\n",
3434	    pf_qidx, vsi_qidx);
3435
3436	reg = rd32(hw, I40E_QRX_ENA(pf_qidx));
3437	reg |= I40E_QRX_ENA_QENA_REQ_MASK |
3438	    I40E_QRX_ENA_QENA_STAT_MASK;
3439	wr32(hw, I40E_QRX_ENA(pf_qidx), reg);
3440	/* Verify the enable took */
3441	for (int j = 0; j < 10; j++) {
3442		reg = rd32(hw, I40E_QRX_ENA(pf_qidx));
3443		if (reg & I40E_QRX_ENA_QENA_STAT_MASK)
3444			break;
3445		i40e_usec_delay(10);
3446	}
3447	if ((reg & I40E_QRX_ENA_QENA_STAT_MASK) == 0) {
3448		device_printf(pf->dev, "RX queue %d still disabled!\n",
3449		    pf_qidx);
3450		error = ETIMEDOUT;
3451	}
3452
3453	return (error);
3454}
3455
3456int
3457ixl_enable_ring(struct ixl_pf *pf, struct ixl_pf_qtag *qtag, u16 vsi_qidx)
3458{
3459	int error = 0;
3460
3461	error = ixl_enable_tx_ring(pf, qtag, vsi_qidx);
3462	/* Called function already prints error message */
3463	if (error)
3464		return (error);
3465	error = ixl_enable_rx_ring(pf, qtag, vsi_qidx);
3466	return (error);
3467}
3468
3469/* For PF VSI only */
3470int
3471ixl_enable_rings(struct ixl_vsi *vsi)
3472{
3473	struct ixl_pf	*pf = vsi->back;
3474	int		error = 0;
3475
3476	for (int i = 0; i < vsi->num_queues; i++) {
3477		error = ixl_enable_ring(pf, &pf->qtag, i);
3478		if (error)
3479			return (error);
3480	}
3481
3482	return (error);
3483}
3484
3485/*
3486 * Returns error on first ring that is detected hung.
3487 */
3488int
3489ixl_disable_tx_ring(struct ixl_pf *pf, struct ixl_pf_qtag *qtag, u16 vsi_qidx)
3490{
3491	struct i40e_hw	*hw = &pf->hw;
3492	int		error = 0;
3493	u32		reg;
3494	u16		pf_qidx;
3495
3496	pf_qidx = ixl_pf_qidx_from_vsi_qidx(qtag, vsi_qidx);
3497
3498	i40e_pre_tx_queue_cfg(hw, pf_qidx, FALSE);
3499	i40e_usec_delay(500);
3500
3501	reg = rd32(hw, I40E_QTX_ENA(pf_qidx));
3502	reg &= ~I40E_QTX_ENA_QENA_REQ_MASK;
3503	wr32(hw, I40E_QTX_ENA(pf_qidx), reg);
3504	/* Verify the disable took */
3505	for (int j = 0; j < 10; j++) {
3506		reg = rd32(hw, I40E_QTX_ENA(pf_qidx));
3507		if (!(reg & I40E_QTX_ENA_QENA_STAT_MASK))
3508			break;
3509		i40e_msec_delay(10);
3510	}
3511	if (reg & I40E_QTX_ENA_QENA_STAT_MASK) {
3512		device_printf(pf->dev, "TX queue %d still enabled!\n",
3513		    pf_qidx);
3514		error = ETIMEDOUT;
3515	}
3516
3517	return (error);
3518}
3519
3520/*
3521 * Returns error on first ring that is detected hung.
3522 */
3523int
3524ixl_disable_rx_ring(struct ixl_pf *pf, struct ixl_pf_qtag *qtag, u16 vsi_qidx)
3525{
3526	struct i40e_hw	*hw = &pf->hw;
3527	int		error = 0;
3528	u32		reg;
3529	u16		pf_qidx;
3530
3531	pf_qidx = ixl_pf_qidx_from_vsi_qidx(qtag, vsi_qidx);
3532
3533	reg = rd32(hw, I40E_QRX_ENA(pf_qidx));
3534	reg &= ~I40E_QRX_ENA_QENA_REQ_MASK;
3535	wr32(hw, I40E_QRX_ENA(pf_qidx), reg);
3536	/* Verify the disable took */
3537	for (int j = 0; j < 10; j++) {
3538		reg = rd32(hw, I40E_QRX_ENA(pf_qidx));
3539		if (!(reg & I40E_QRX_ENA_QENA_STAT_MASK))
3540			break;
3541		i40e_msec_delay(10);
3542	}
3543	if (reg & I40E_QRX_ENA_QENA_STAT_MASK) {
3544		device_printf(pf->dev, "RX queue %d still enabled!\n",
3545		    pf_qidx);
3546		error = ETIMEDOUT;
3547	}
3548
3549	return (error);
3550}
3551
3552int
3553ixl_disable_ring(struct ixl_pf *pf, struct ixl_pf_qtag *qtag, u16 vsi_qidx)
3554{
3555	int error = 0;
3556
3557	error = ixl_disable_tx_ring(pf, qtag, vsi_qidx);
3558	/* Called function already prints error message */
3559	if (error)
3560		return (error);
3561	error = ixl_disable_rx_ring(pf, qtag, vsi_qidx);
3562	return (error);
3563}
3564
3565/* For PF VSI only */
3566int
3567ixl_disable_rings(struct ixl_vsi *vsi)
3568{
3569	struct ixl_pf	*pf = vsi->back;
3570	int		error = 0;
3571
3572	for (int i = 0; i < vsi->num_queues; i++) {
3573		error = ixl_disable_ring(pf, &pf->qtag, i);
3574		if (error)
3575			return (error);
3576	}
3577
3578	return (error);
3579}
3580
3581/**
3582 * ixl_handle_mdd_event
3583 *
3584 * Called from interrupt handler to identify possibly malicious vfs
3585 * (But also detects events from the PF, as well)
3586 **/
3587void
3588ixl_handle_mdd_event(struct ixl_pf *pf)
3589{
3590	struct i40e_hw *hw = &pf->hw;
3591	device_t dev = pf->dev;
3592	bool mdd_detected = false;
3593	bool pf_mdd_detected = false;
3594	u32 reg;
3595
3596	/* find what triggered the MDD event */
3597	reg = rd32(hw, I40E_GL_MDET_TX);
3598	if (reg & I40E_GL_MDET_TX_VALID_MASK) {
3599		u8 pf_num = (reg & I40E_GL_MDET_TX_PF_NUM_MASK) >>
3600				I40E_GL_MDET_TX_PF_NUM_SHIFT;
3601		u8 event = (reg & I40E_GL_MDET_TX_EVENT_MASK) >>
3602				I40E_GL_MDET_TX_EVENT_SHIFT;
3603		u16 queue = (reg & I40E_GL_MDET_TX_QUEUE_MASK) >>
3604				I40E_GL_MDET_TX_QUEUE_SHIFT;
3605		device_printf(dev,
3606		    "Malicious Driver Detection event %d"
3607		    " on TX queue %d, pf number %d\n",
3608		    event, queue, pf_num);
3609		wr32(hw, I40E_GL_MDET_TX, 0xffffffff);
3610		mdd_detected = true;
3611	}
3612	reg = rd32(hw, I40E_GL_MDET_RX);
3613	if (reg & I40E_GL_MDET_RX_VALID_MASK) {
3614		u8 pf_num = (reg & I40E_GL_MDET_RX_FUNCTION_MASK) >>
3615				I40E_GL_MDET_RX_FUNCTION_SHIFT;
3616		u8 event = (reg & I40E_GL_MDET_RX_EVENT_MASK) >>
3617				I40E_GL_MDET_RX_EVENT_SHIFT;
3618		u16 queue = (reg & I40E_GL_MDET_RX_QUEUE_MASK) >>
3619				I40E_GL_MDET_RX_QUEUE_SHIFT;
3620		device_printf(dev,
3621		    "Malicious Driver Detection event %d"
3622		    " on RX queue %d, pf number %d\n",
3623		    event, queue, pf_num);
3624		wr32(hw, I40E_GL_MDET_RX, 0xffffffff);
3625		mdd_detected = true;
3626	}
3627
3628	if (mdd_detected) {
3629		reg = rd32(hw, I40E_PF_MDET_TX);
3630		if (reg & I40E_PF_MDET_TX_VALID_MASK) {
3631			wr32(hw, I40E_PF_MDET_TX, 0xFFFF);
3632			device_printf(dev,
3633			    "MDD TX event is for this function!\n");
3634			pf_mdd_detected = true;
3635		}
3636		reg = rd32(hw, I40E_PF_MDET_RX);
3637		if (reg & I40E_PF_MDET_RX_VALID_MASK) {
3638			wr32(hw, I40E_PF_MDET_RX, 0xFFFF);
3639			device_printf(dev,
3640			    "MDD RX event is for this function!\n");
3641			pf_mdd_detected = true;
3642		}
3643	}
3644
3645	/* re-enable mdd interrupt cause */
3646	reg = rd32(hw, I40E_PFINT_ICR0_ENA);
3647	reg |= I40E_PFINT_ICR0_ENA_MAL_DETECT_MASK;
3648	wr32(hw, I40E_PFINT_ICR0_ENA, reg);
3649	ixl_flush(hw);
3650}
3651
3652void
3653ixl_enable_intr(struct ixl_vsi *vsi)
3654{
3655	struct ixl_pf		*pf = (struct ixl_pf *)vsi->back;
3656	struct i40e_hw		*hw = vsi->hw;
3657	struct ixl_queue	*que = vsi->queues;
3658
3659	if (pf->msix > 1) {
3660		for (int i = 0; i < vsi->num_queues; i++, que++)
3661			ixl_enable_queue(hw, que->me);
3662	} else
3663		ixl_enable_intr0(hw);
3664}
3665
3666void
3667ixl_disable_rings_intr(struct ixl_vsi *vsi)
3668{
3669	struct i40e_hw		*hw = vsi->hw;
3670	struct ixl_queue	*que = vsi->queues;
3671
3672	for (int i = 0; i < vsi->num_queues; i++, que++)
3673		ixl_disable_queue(hw, que->me);
3674}
3675
3676void
3677ixl_enable_intr0(struct i40e_hw *hw)
3678{
3679	u32		reg;
3680
3681	/* Use IXL_ITR_NONE so ITR isn't updated here */
3682	reg = I40E_PFINT_DYN_CTL0_INTENA_MASK |
3683	    I40E_PFINT_DYN_CTL0_CLEARPBA_MASK |
3684	    (IXL_ITR_NONE << I40E_PFINT_DYN_CTL0_ITR_INDX_SHIFT);
3685	wr32(hw, I40E_PFINT_DYN_CTL0, reg);
3686}
3687
3688void
3689ixl_disable_intr0(struct i40e_hw *hw)
3690{
3691	u32		reg;
3692
3693	reg = IXL_ITR_NONE << I40E_PFINT_DYN_CTL0_ITR_INDX_SHIFT;
3694	wr32(hw, I40E_PFINT_DYN_CTL0, reg);
3695	ixl_flush(hw);
3696}
3697
3698void
3699ixl_enable_queue(struct i40e_hw *hw, int id)
3700{
3701	u32		reg;
3702
3703	reg = I40E_PFINT_DYN_CTLN_INTENA_MASK |
3704	    I40E_PFINT_DYN_CTLN_CLEARPBA_MASK |
3705	    (IXL_ITR_NONE << I40E_PFINT_DYN_CTLN_ITR_INDX_SHIFT);
3706	wr32(hw, I40E_PFINT_DYN_CTLN(id), reg);
3707}
3708
3709void
3710ixl_disable_queue(struct i40e_hw *hw, int id)
3711{
3712	u32		reg;
3713
3714	reg = IXL_ITR_NONE << I40E_PFINT_DYN_CTLN_ITR_INDX_SHIFT;
3715	wr32(hw, I40E_PFINT_DYN_CTLN(id), reg);
3716}
3717
3718void
3719ixl_update_stats_counters(struct ixl_pf *pf)
3720{
3721	struct i40e_hw	*hw = &pf->hw;
3722	struct ixl_vsi	*vsi = &pf->vsi;
3723	struct ixl_vf	*vf;
3724
3725	struct i40e_hw_port_stats *nsd = &pf->stats;
3726	struct i40e_hw_port_stats *osd = &pf->stats_offsets;
3727
3728	/* Update hw stats */
3729	ixl_stat_update32(hw, I40E_GLPRT_CRCERRS(hw->port),
3730			   pf->stat_offsets_loaded,
3731			   &osd->crc_errors, &nsd->crc_errors);
3732	ixl_stat_update32(hw, I40E_GLPRT_ILLERRC(hw->port),
3733			   pf->stat_offsets_loaded,
3734			   &osd->illegal_bytes, &nsd->illegal_bytes);
3735	ixl_stat_update48(hw, I40E_GLPRT_GORCH(hw->port),
3736			   I40E_GLPRT_GORCL(hw->port),
3737			   pf->stat_offsets_loaded,
3738			   &osd->eth.rx_bytes, &nsd->eth.rx_bytes);
3739	ixl_stat_update48(hw, I40E_GLPRT_GOTCH(hw->port),
3740			   I40E_GLPRT_GOTCL(hw->port),
3741			   pf->stat_offsets_loaded,
3742			   &osd->eth.tx_bytes, &nsd->eth.tx_bytes);
3743	ixl_stat_update32(hw, I40E_GLPRT_RDPC(hw->port),
3744			   pf->stat_offsets_loaded,
3745			   &osd->eth.rx_discards,
3746			   &nsd->eth.rx_discards);
3747	ixl_stat_update48(hw, I40E_GLPRT_UPRCH(hw->port),
3748			   I40E_GLPRT_UPRCL(hw->port),
3749			   pf->stat_offsets_loaded,
3750			   &osd->eth.rx_unicast,
3751			   &nsd->eth.rx_unicast);
3752	ixl_stat_update48(hw, I40E_GLPRT_UPTCH(hw->port),
3753			   I40E_GLPRT_UPTCL(hw->port),
3754			   pf->stat_offsets_loaded,
3755			   &osd->eth.tx_unicast,
3756			   &nsd->eth.tx_unicast);
3757	ixl_stat_update48(hw, I40E_GLPRT_MPRCH(hw->port),
3758			   I40E_GLPRT_MPRCL(hw->port),
3759			   pf->stat_offsets_loaded,
3760			   &osd->eth.rx_multicast,
3761			   &nsd->eth.rx_multicast);
3762	ixl_stat_update48(hw, I40E_GLPRT_MPTCH(hw->port),
3763			   I40E_GLPRT_MPTCL(hw->port),
3764			   pf->stat_offsets_loaded,
3765			   &osd->eth.tx_multicast,
3766			   &nsd->eth.tx_multicast);
3767	ixl_stat_update48(hw, I40E_GLPRT_BPRCH(hw->port),
3768			   I40E_GLPRT_BPRCL(hw->port),
3769			   pf->stat_offsets_loaded,
3770			   &osd->eth.rx_broadcast,
3771			   &nsd->eth.rx_broadcast);
3772	ixl_stat_update48(hw, I40E_GLPRT_BPTCH(hw->port),
3773			   I40E_GLPRT_BPTCL(hw->port),
3774			   pf->stat_offsets_loaded,
3775			   &osd->eth.tx_broadcast,
3776			   &nsd->eth.tx_broadcast);
3777
3778	ixl_stat_update32(hw, I40E_GLPRT_TDOLD(hw->port),
3779			   pf->stat_offsets_loaded,
3780			   &osd->tx_dropped_link_down,
3781			   &nsd->tx_dropped_link_down);
3782	ixl_stat_update32(hw, I40E_GLPRT_MLFC(hw->port),
3783			   pf->stat_offsets_loaded,
3784			   &osd->mac_local_faults,
3785			   &nsd->mac_local_faults);
3786	ixl_stat_update32(hw, I40E_GLPRT_MRFC(hw->port),
3787			   pf->stat_offsets_loaded,
3788			   &osd->mac_remote_faults,
3789			   &nsd->mac_remote_faults);
3790	ixl_stat_update32(hw, I40E_GLPRT_RLEC(hw->port),
3791			   pf->stat_offsets_loaded,
3792			   &osd->rx_length_errors,
3793			   &nsd->rx_length_errors);
3794
3795	/* Flow control (LFC) stats */
3796	ixl_stat_update32(hw, I40E_GLPRT_LXONRXC(hw->port),
3797			   pf->stat_offsets_loaded,
3798			   &osd->link_xon_rx, &nsd->link_xon_rx);
3799	ixl_stat_update32(hw, I40E_GLPRT_LXONTXC(hw->port),
3800			   pf->stat_offsets_loaded,
3801			   &osd->link_xon_tx, &nsd->link_xon_tx);
3802	ixl_stat_update32(hw, I40E_GLPRT_LXOFFRXC(hw->port),
3803			   pf->stat_offsets_loaded,
3804			   &osd->link_xoff_rx, &nsd->link_xoff_rx);
3805	ixl_stat_update32(hw, I40E_GLPRT_LXOFFTXC(hw->port),
3806			   pf->stat_offsets_loaded,
3807			   &osd->link_xoff_tx, &nsd->link_xoff_tx);
3808
3809	/* Packet size stats rx */
3810	ixl_stat_update48(hw, I40E_GLPRT_PRC64H(hw->port),
3811			   I40E_GLPRT_PRC64L(hw->port),
3812			   pf->stat_offsets_loaded,
3813			   &osd->rx_size_64, &nsd->rx_size_64);
3814	ixl_stat_update48(hw, I40E_GLPRT_PRC127H(hw->port),
3815			   I40E_GLPRT_PRC127L(hw->port),
3816			   pf->stat_offsets_loaded,
3817			   &osd->rx_size_127, &nsd->rx_size_127);
3818	ixl_stat_update48(hw, I40E_GLPRT_PRC255H(hw->port),
3819			   I40E_GLPRT_PRC255L(hw->port),
3820			   pf->stat_offsets_loaded,
3821			   &osd->rx_size_255, &nsd->rx_size_255);
3822	ixl_stat_update48(hw, I40E_GLPRT_PRC511H(hw->port),
3823			   I40E_GLPRT_PRC511L(hw->port),
3824			   pf->stat_offsets_loaded,
3825			   &osd->rx_size_511, &nsd->rx_size_511);
3826	ixl_stat_update48(hw, I40E_GLPRT_PRC1023H(hw->port),
3827			   I40E_GLPRT_PRC1023L(hw->port),
3828			   pf->stat_offsets_loaded,
3829			   &osd->rx_size_1023, &nsd->rx_size_1023);
3830	ixl_stat_update48(hw, I40E_GLPRT_PRC1522H(hw->port),
3831			   I40E_GLPRT_PRC1522L(hw->port),
3832			   pf->stat_offsets_loaded,
3833			   &osd->rx_size_1522, &nsd->rx_size_1522);
3834	ixl_stat_update48(hw, I40E_GLPRT_PRC9522H(hw->port),
3835			   I40E_GLPRT_PRC9522L(hw->port),
3836			   pf->stat_offsets_loaded,
3837			   &osd->rx_size_big, &nsd->rx_size_big);
3838
3839	/* Packet size stats tx */
3840	ixl_stat_update48(hw, I40E_GLPRT_PTC64H(hw->port),
3841			   I40E_GLPRT_PTC64L(hw->port),
3842			   pf->stat_offsets_loaded,
3843			   &osd->tx_size_64, &nsd->tx_size_64);
3844	ixl_stat_update48(hw, I40E_GLPRT_PTC127H(hw->port),
3845			   I40E_GLPRT_PTC127L(hw->port),
3846			   pf->stat_offsets_loaded,
3847			   &osd->tx_size_127, &nsd->tx_size_127);
3848	ixl_stat_update48(hw, I40E_GLPRT_PTC255H(hw->port),
3849			   I40E_GLPRT_PTC255L(hw->port),
3850			   pf->stat_offsets_loaded,
3851			   &osd->tx_size_255, &nsd->tx_size_255);
3852	ixl_stat_update48(hw, I40E_GLPRT_PTC511H(hw->port),
3853			   I40E_GLPRT_PTC511L(hw->port),
3854			   pf->stat_offsets_loaded,
3855			   &osd->tx_size_511, &nsd->tx_size_511);
3856	ixl_stat_update48(hw, I40E_GLPRT_PTC1023H(hw->port),
3857			   I40E_GLPRT_PTC1023L(hw->port),
3858			   pf->stat_offsets_loaded,
3859			   &osd->tx_size_1023, &nsd->tx_size_1023);
3860	ixl_stat_update48(hw, I40E_GLPRT_PTC1522H(hw->port),
3861			   I40E_GLPRT_PTC1522L(hw->port),
3862			   pf->stat_offsets_loaded,
3863			   &osd->tx_size_1522, &nsd->tx_size_1522);
3864	ixl_stat_update48(hw, I40E_GLPRT_PTC9522H(hw->port),
3865			   I40E_GLPRT_PTC9522L(hw->port),
3866			   pf->stat_offsets_loaded,
3867			   &osd->tx_size_big, &nsd->tx_size_big);
3868
3869	ixl_stat_update32(hw, I40E_GLPRT_RUC(hw->port),
3870			   pf->stat_offsets_loaded,
3871			   &osd->rx_undersize, &nsd->rx_undersize);
3872	ixl_stat_update32(hw, I40E_GLPRT_RFC(hw->port),
3873			   pf->stat_offsets_loaded,
3874			   &osd->rx_fragments, &nsd->rx_fragments);
3875	ixl_stat_update32(hw, I40E_GLPRT_ROC(hw->port),
3876			   pf->stat_offsets_loaded,
3877			   &osd->rx_oversize, &nsd->rx_oversize);
3878	ixl_stat_update32(hw, I40E_GLPRT_RJC(hw->port),
3879			   pf->stat_offsets_loaded,
3880			   &osd->rx_jabber, &nsd->rx_jabber);
3881	/* EEE */
3882	i40e_get_phy_lpi_status(hw, nsd);
3883
3884	ixl_stat_update32(hw, I40E_PRTPM_TLPIC,
3885			  pf->stat_offsets_loaded,
3886			  &osd->tx_lpi_count, &nsd->tx_lpi_count);
3887	ixl_stat_update32(hw, I40E_PRTPM_RLPIC,
3888			  pf->stat_offsets_loaded,
3889			  &osd->rx_lpi_count, &nsd->rx_lpi_count);
3890
3891	pf->stat_offsets_loaded = true;
3892	/* End hw stats */
3893
3894	/* Update vsi stats */
3895	ixl_update_vsi_stats(vsi);
3896
3897	for (int i = 0; i < pf->num_vfs; i++) {
3898		vf = &pf->vfs[i];
3899		if (vf->vf_flags & VF_FLAG_ENABLED)
3900			ixl_update_eth_stats(&pf->vfs[i].vsi);
3901	}
3902}
3903
3904int
3905ixl_prepare_for_reset(struct ixl_pf *pf, bool is_up)
3906{
3907	struct i40e_hw *hw = &pf->hw;
3908	struct ixl_vsi *vsi = &pf->vsi;
3909	device_t dev = pf->dev;
3910	int error = 0;
3911
3912	/* Teardown */
3913	if (is_up)
3914		ixl_stop(pf);
3915
3916	ixl_teardown_queue_msix(vsi);
3917
3918	if (hw->hmc.hmc_obj) {
3919		error = i40e_shutdown_lan_hmc(hw);
3920		if (error)
3921			device_printf(dev,
3922			    "Shutdown LAN HMC failed with code %d\n", error);
3923	}
3924
3925	callout_drain(&pf->timer);
3926
3927	ixl_disable_intr0(hw);
3928	ixl_teardown_adminq_msix(pf);
3929
3930	error = i40e_shutdown_adminq(hw);
3931	if (error)
3932		device_printf(dev,
3933		    "Shutdown Admin queue failed with code %d\n", error);
3934
3935	/* Free ring buffers, locks and filters */
3936	ixl_vsi_free_queues(vsi);
3937
3938	ixl_pf_qmgr_release(&pf->qmgr, &pf->qtag);
3939
3940	return (error);
3941}
3942
3943int
3944ixl_rebuild_hw_structs_after_reset(struct ixl_pf *pf, bool is_up)
3945{
3946	struct i40e_hw *hw = &pf->hw;
3947	struct ixl_vsi *vsi = &pf->vsi;
3948	device_t dev = pf->dev;
3949	enum i40e_get_fw_lldp_status_resp lldp_status;
3950	int error = 0;
3951
3952	device_printf(dev, "Rebuilding driver state...\n");
3953
3954	if (!(atomic_load_acq_int(&pf->state) & IXL_PF_STATE_RECOVERY_MODE)) {
3955		if (ixl_fw_recovery_mode(pf)) {
3956			atomic_set_int(&pf->state, IXL_PF_STATE_RECOVERY_MODE);
3957			pf->link_up = FALSE;
3958			ixl_update_link_status(pf);
3959		}
3960	}
3961
3962
3963	/* Setup */
3964	error = i40e_init_adminq(hw);
3965	if (error != 0 && error != I40E_ERR_FIRMWARE_API_VERSION) {
3966		device_printf(dev, "Unable to initialize Admin Queue, error %d\n",
3967		    error);
3968		goto ixl_rebuild_hw_structs_after_reset_err;
3969	}
3970
3971	i40e_clear_pxe_mode(hw);
3972
3973	error = ixl_get_hw_capabilities(pf);
3974	if (error) {
3975		device_printf(dev, "ixl_get_hw_capabilities failed: %d\n", error);
3976		goto ixl_rebuild_hw_structs_after_reset_err;
3977	}
3978	ixl_configure_intr0_msix(pf);
3979	ixl_enable_intr0(hw);
3980
3981	/* Do not init LAN HMC and bring interface up in recovery mode */
3982	if ((pf->state & IXL_PF_STATE_RECOVERY_MODE) == 0) {
3983		error = i40e_init_lan_hmc(hw, hw->func_caps.num_tx_qp,
3984		    hw->func_caps.num_rx_qp, 0, 0);
3985		if (error) {
3986			device_printf(dev, "init_lan_hmc failed: %d\n", error);
3987			goto ixl_rebuild_hw_structs_after_reset_err;
3988		}
3989
3990		error = i40e_configure_lan_hmc(hw, I40E_HMC_MODEL_DIRECT_ONLY);
3991		if (error) {
3992			device_printf(dev, "configure_lan_hmc failed: %d\n", error);
3993			goto ixl_rebuild_hw_structs_after_reset_err;
3994		}
3995
3996		if (!pf->qmgr.qinfo) {
3997			/* Init queue allocation manager */
3998			error = ixl_pf_qmgr_init(&pf->qmgr, hw->func_caps.num_rx_qp);
3999			if (error) {
4000				device_printf(dev, "Failed to init queue manager for PF queues, error %d\n",
4001				    error);
4002				goto ixl_rebuild_hw_structs_after_reset_err;
4003			}
4004		}
4005		/* reserve a contiguous allocation for the PF's VSI */
4006		error = ixl_pf_qmgr_alloc_contiguous(&pf->qmgr, vsi->num_queues, &pf->qtag);
4007		if (error) {
4008			device_printf(dev, "Failed to reserve queues for PF LAN VSI, error %d\n",
4009			    error);
4010			/* TODO: error handling */
4011		} else
4012			device_printf(dev, "Allocating %d queues for PF LAN VSI; %d queues active\n",
4013			    pf->qtag.num_allocated, pf->qtag.num_active);
4014
4015		error = ixl_switch_config(pf);
4016		if (error) {
4017			device_printf(dev, "ixl_rebuild_hw_structs_after_reset: ixl_switch_config() failed: %d\n",
4018			     error);
4019			goto ixl_rebuild_hw_structs_after_reset_err;
4020		}
4021	} /* not in recovery mode */
4022
4023	/* Remove default filters reinstalled by FW on reset */
4024	ixl_del_default_hw_filters(vsi);
4025
4026	if (ixl_vsi_setup_queues(vsi)) {
4027		device_printf(dev, "setup queues failed!\n");
4028		error = ENOMEM;
4029		goto ixl_rebuild_hw_structs_after_reset_err;
4030	}
4031
4032	ixl_vsi_add_sysctls(vsi, "pf", true);
4033
4034	if (pf->msix > 1) {
4035		error = ixl_setup_adminq_msix(pf);
4036		if (error) {
4037			device_printf(dev, "ixl_setup_adminq_msix() error: %d\n",
4038			    error);
4039			goto ixl_rebuild_hw_structs_after_reset_err;
4040		}
4041
4042		ixl_configure_intr0_msix(pf);
4043		ixl_enable_intr0(hw);
4044
4045		error = ixl_setup_queue_msix(vsi);
4046		if (error) {
4047			device_printf(dev, "ixl_setup_queue_msix() error: %d\n",
4048			    error);
4049			goto ixl_rebuild_hw_structs_after_reset_err;
4050		}
4051		error = ixl_setup_queue_tqs(vsi);
4052		if (error) {
4053			device_printf(dev, "ixl_setup_queue_tqs() error: %d\n",
4054			    error);
4055			goto ixl_rebuild_hw_structs_after_reset_err;
4056		}
4057	} else {
4058		error = ixl_setup_legacy(pf);
4059		if (error) {
4060			device_printf(dev, "ixl_setup_legacy() error: %d\n",
4061			    error);
4062			goto ixl_rebuild_hw_structs_after_reset_err;
4063		}
4064	}
4065
4066	/* Do not bring interface up in recovery mode */
4067	if ((pf->state & IXL_PF_STATE_RECOVERY_MODE) != 0)
4068		return (error);
4069
4070	/* Determine link state */
4071	if (ixl_attach_get_link_status(pf)) {
4072		error = EINVAL;
4073		/* TODO: error handling */
4074	}
4075
4076	i40e_aq_set_dcb_parameters(hw, TRUE, NULL);
4077
4078	/* Query device FW LLDP status */
4079	if (i40e_get_fw_lldp_status(hw, &lldp_status) == I40E_SUCCESS) {
4080		if (lldp_status == I40E_GET_FW_LLDP_STATUS_DISABLED) {
4081			atomic_set_int(&pf->state,
4082			    IXL_PF_STATE_FW_LLDP_DISABLED);
4083		} else {
4084			atomic_clear_int(&pf->state,
4085			    IXL_PF_STATE_FW_LLDP_DISABLED);
4086		}
4087	}
4088
4089	if (is_up)
4090		ixl_init(pf);
4091
4092	device_printf(dev, "Rebuilding driver state done.\n");
4093	IXL_PF_LOCK(pf);
4094	callout_reset(&pf->timer, hz, ixl_local_timer, pf);
4095	IXL_PF_UNLOCK(pf);
4096	return (0);
4097
4098ixl_rebuild_hw_structs_after_reset_err:
4099	device_printf(dev, "Reload the driver to recover\n");
4100	return (error);
4101}
4102
4103void
4104ixl_handle_empr_reset(struct ixl_pf *pf)
4105{
4106	struct ixl_vsi	*vsi = &pf->vsi;
4107	struct i40e_hw	*hw = &pf->hw;
4108	bool is_up = !!(vsi->ifp->if_drv_flags & IFF_DRV_RUNNING);
4109	int error = 0;
4110
4111	ixl_prepare_for_reset(pf, is_up);
4112	/*
4113	 * i40e_pf_reset checks the type of reset and acts
4114	 * accordingly. If EMP or Core reset was performed
4115	 * doing PF reset is not necessary and it sometimes
4116	 * fails.
4117	 */
4118	error = i40e_pf_reset(hw);
4119	if (error) {
4120		device_printf(pf->dev, "PF reset failure %s\n",
4121				i40e_stat_str(hw, error));
4122	}
4123
4124	ixl_rebuild_hw_structs_after_reset(pf, is_up);
4125
4126	atomic_clear_int(&pf->state, IXL_PF_STATE_EMPR_RESETTING);
4127}
4128
4129/*
4130** Tasklet handler for MSIX Adminq interrupts
4131**  - do outside interrupt since it might sleep
4132*/
4133void
4134ixl_do_adminq(void *context, int pending)
4135{
4136	struct ixl_pf			*pf = context;
4137	struct i40e_hw			*hw = &pf->hw;
4138	struct i40e_arq_event_info	event;
4139	i40e_status			ret;
4140	device_t			dev = pf->dev;
4141	u32				loop = 0;
4142	u16				opcode, arq_pending;
4143
4144	if (pf->state & IXL_PF_STATE_EMPR_RESETTING) {
4145		/* Flag cleared at end of this function */
4146		ixl_handle_empr_reset(pf);
4147		return;
4148	}
4149
4150	/* Admin Queue handling */
4151	event.buf_len = IXL_AQ_BUF_SZ;
4152	event.msg_buf = malloc(event.buf_len,
4153	    M_DEVBUF, M_NOWAIT | M_ZERO);
4154	if (!event.msg_buf) {
4155		device_printf(dev, "%s: Unable to allocate memory for Admin"
4156		    " Queue event!\n", __func__);
4157		return;
4158	}
4159
4160	IXL_PF_LOCK(pf);
4161	/* clean and process any events */
4162	do {
4163		ret = i40e_clean_arq_element(hw, &event, &arq_pending);
4164		if (ret)
4165			break;
4166		opcode = LE16_TO_CPU(event.desc.opcode);
4167		ixl_dbg(pf, IXL_DBG_AQ,
4168		    "Admin Queue event: %#06x\n", opcode);
4169		switch (opcode) {
4170		case i40e_aqc_opc_get_link_status:
4171			ixl_link_event(pf, &event);
4172			break;
4173		case i40e_aqc_opc_send_msg_to_pf:
4174#ifdef PCI_IOV
4175			ixl_handle_vf_msg(pf, &event);
4176#endif
4177			break;
4178		case i40e_aqc_opc_event_lan_overflow:
4179		default:
4180			break;
4181		}
4182
4183	} while (arq_pending && (loop++ < IXL_ADM_LIMIT));
4184
4185	free(event.msg_buf, M_DEVBUF);
4186
4187	/* If there are still messages to process, reschedule. */
4188	if (arq_pending > 0)
4189		taskqueue_enqueue(pf->tq, &pf->adminq);
4190	else
4191		ixl_enable_intr0(hw);
4192
4193	IXL_PF_UNLOCK(pf);
4194}
4195
4196/**
4197 * Update VSI-specific ethernet statistics counters.
4198 **/
4199void
4200ixl_update_eth_stats(struct ixl_vsi *vsi)
4201{
4202	struct ixl_pf *pf = (struct ixl_pf *)vsi->back;
4203	struct i40e_hw *hw = &pf->hw;
4204	struct i40e_eth_stats *es;
4205	struct i40e_eth_stats *oes;
4206	u16 stat_idx = vsi->info.stat_counter_idx;
4207
4208	es = &vsi->eth_stats;
4209	oes = &vsi->eth_stats_offsets;
4210
4211	/* Gather up the stats that the hw collects */
4212	ixl_stat_update32(hw, I40E_GLV_TEPC(stat_idx),
4213			   vsi->stat_offsets_loaded,
4214			   &oes->tx_errors, &es->tx_errors);
4215	ixl_stat_update32(hw, I40E_GLV_RDPC(stat_idx),
4216			   vsi->stat_offsets_loaded,
4217			   &oes->rx_discards, &es->rx_discards);
4218
4219	ixl_stat_update48(hw, I40E_GLV_GORCH(stat_idx),
4220			   I40E_GLV_GORCL(stat_idx),
4221			   vsi->stat_offsets_loaded,
4222			   &oes->rx_bytes, &es->rx_bytes);
4223	ixl_stat_update48(hw, I40E_GLV_UPRCH(stat_idx),
4224			   I40E_GLV_UPRCL(stat_idx),
4225			   vsi->stat_offsets_loaded,
4226			   &oes->rx_unicast, &es->rx_unicast);
4227	ixl_stat_update48(hw, I40E_GLV_MPRCH(stat_idx),
4228			   I40E_GLV_MPRCL(stat_idx),
4229			   vsi->stat_offsets_loaded,
4230			   &oes->rx_multicast, &es->rx_multicast);
4231	ixl_stat_update48(hw, I40E_GLV_BPRCH(stat_idx),
4232			   I40E_GLV_BPRCL(stat_idx),
4233			   vsi->stat_offsets_loaded,
4234			   &oes->rx_broadcast, &es->rx_broadcast);
4235
4236	ixl_stat_update48(hw, I40E_GLV_GOTCH(stat_idx),
4237			   I40E_GLV_GOTCL(stat_idx),
4238			   vsi->stat_offsets_loaded,
4239			   &oes->tx_bytes, &es->tx_bytes);
4240	ixl_stat_update48(hw, I40E_GLV_UPTCH(stat_idx),
4241			   I40E_GLV_UPTCL(stat_idx),
4242			   vsi->stat_offsets_loaded,
4243			   &oes->tx_unicast, &es->tx_unicast);
4244	ixl_stat_update48(hw, I40E_GLV_MPTCH(stat_idx),
4245			   I40E_GLV_MPTCL(stat_idx),
4246			   vsi->stat_offsets_loaded,
4247			   &oes->tx_multicast, &es->tx_multicast);
4248	ixl_stat_update48(hw, I40E_GLV_BPTCH(stat_idx),
4249			   I40E_GLV_BPTCL(stat_idx),
4250			   vsi->stat_offsets_loaded,
4251			   &oes->tx_broadcast, &es->tx_broadcast);
4252	vsi->stat_offsets_loaded = true;
4253}
4254
4255void
4256ixl_update_vsi_stats(struct ixl_vsi *vsi)
4257{
4258	struct ixl_pf		*pf;
4259	struct ifnet		*ifp;
4260	struct i40e_eth_stats	*es;
4261	u64			tx_discards;
4262
4263	struct i40e_hw_port_stats *nsd;
4264
4265	pf = vsi->back;
4266	ifp = vsi->ifp;
4267	es = &vsi->eth_stats;
4268	nsd = &pf->stats;
4269
4270	ixl_update_eth_stats(vsi);
4271
4272	tx_discards = es->tx_discards + nsd->tx_dropped_link_down;
4273	for (int i = 0; i < vsi->num_queues; i++)
4274		tx_discards += vsi->queues[i].txr.br->br_drops;
4275
4276	/* Update ifnet stats */
4277	IXL_SET_IPACKETS(vsi, es->rx_unicast +
4278	                   es->rx_multicast +
4279			   es->rx_broadcast);
4280	IXL_SET_OPACKETS(vsi, es->tx_unicast +
4281	                   es->tx_multicast +
4282			   es->tx_broadcast);
4283	IXL_SET_IBYTES(vsi, es->rx_bytes);
4284	IXL_SET_OBYTES(vsi, es->tx_bytes);
4285	IXL_SET_IMCASTS(vsi, es->rx_multicast);
4286	IXL_SET_OMCASTS(vsi, es->tx_multicast);
4287
4288	IXL_SET_IERRORS(vsi, nsd->crc_errors + nsd->illegal_bytes +
4289	    nsd->rx_undersize + nsd->rx_oversize + nsd->rx_fragments +
4290	    nsd->rx_jabber);
4291	IXL_SET_OERRORS(vsi, es->tx_errors);
4292	IXL_SET_IQDROPS(vsi, es->rx_discards + nsd->eth.rx_discards);
4293	IXL_SET_OQDROPS(vsi, tx_discards);
4294	IXL_SET_NOPROTO(vsi, es->rx_unknown_protocol);
4295	IXL_SET_COLLISIONS(vsi, 0);
4296}
4297
4298/**
4299 * Reset all of the stats for the given pf
4300 **/
4301void
4302ixl_pf_reset_stats(struct ixl_pf *pf)
4303{
4304	bzero(&pf->stats, sizeof(struct i40e_hw_port_stats));
4305	bzero(&pf->stats_offsets, sizeof(struct i40e_hw_port_stats));
4306	pf->stat_offsets_loaded = false;
4307}
4308
4309/**
4310 * Resets all stats of the given vsi
4311 **/
4312void
4313ixl_vsi_reset_stats(struct ixl_vsi *vsi)
4314{
4315	bzero(&vsi->eth_stats, sizeof(struct i40e_eth_stats));
4316	bzero(&vsi->eth_stats_offsets, sizeof(struct i40e_eth_stats));
4317	vsi->stat_offsets_loaded = false;
4318}
4319
4320/**
4321 * Read and update a 48 bit stat from the hw
4322 *
4323 * Since the device stats are not reset at PFReset, they likely will not
4324 * be zeroed when the driver starts.  We'll save the first values read
4325 * and use them as offsets to be subtracted from the raw values in order
4326 * to report stats that count from zero.
4327 **/
4328void
4329ixl_stat_update48(struct i40e_hw *hw, u32 hireg, u32 loreg,
4330	bool offset_loaded, u64 *offset, u64 *stat)
4331{
4332	u64 new_data;
4333
4334#if defined(__FreeBSD__) && (__FreeBSD_version >= 1000000) && defined(__amd64__)
4335	new_data = rd64(hw, loreg);
4336#else
4337	/*
4338	 * Use two rd32's instead of one rd64; FreeBSD versions before
4339	 * 10 don't support 64-bit bus reads/writes.
4340	 */
4341	new_data = rd32(hw, loreg);
4342	new_data |= ((u64)(rd32(hw, hireg) & 0xFFFF)) << 32;
4343#endif
4344
4345	if (!offset_loaded)
4346		*offset = new_data;
4347	if (new_data >= *offset)
4348		*stat = new_data - *offset;
4349	else
4350		*stat = (new_data + ((u64)1 << 48)) - *offset;
4351	*stat &= 0xFFFFFFFFFFFFULL;
4352}
4353
4354/**
4355 * Read and update a 32 bit stat from the hw
4356 **/
4357void
4358ixl_stat_update32(struct i40e_hw *hw, u32 reg,
4359	bool offset_loaded, u64 *offset, u64 *stat)
4360{
4361	u32 new_data;
4362
4363	new_data = rd32(hw, reg);
4364	if (!offset_loaded)
4365		*offset = new_data;
4366	if (new_data >= *offset)
4367		*stat = (u32)(new_data - *offset);
4368	else
4369		*stat = (u32)((new_data + ((u64)1 << 32)) - *offset);
4370}
4371
4372void
4373ixl_add_device_sysctls(struct ixl_pf *pf)
4374{
4375	device_t dev = pf->dev;
4376	struct i40e_hw *hw = &pf->hw;
4377
4378	struct sysctl_ctx_list *ctx = device_get_sysctl_ctx(dev);
4379	struct sysctl_oid_list *ctx_list =
4380	    SYSCTL_CHILDREN(device_get_sysctl_tree(dev));
4381
4382	struct sysctl_oid *debug_node;
4383	struct sysctl_oid_list *debug_list;
4384
4385	struct sysctl_oid *fec_node;
4386	struct sysctl_oid_list *fec_list;
4387
4388	struct sysctl_oid *eee_node;
4389	struct sysctl_oid_list *eee_list;
4390
4391	/* Set up sysctls */
4392	SYSCTL_ADD_PROC(ctx, ctx_list,
4393	    OID_AUTO, "fc", CTLTYPE_INT | CTLFLAG_RW,
4394	    pf, 0, ixl_sysctl_set_flowcntl, "I", IXL_SYSCTL_HELP_FC);
4395
4396	SYSCTL_ADD_PROC(ctx, ctx_list,
4397	    OID_AUTO, "advertise_speed", CTLTYPE_INT | CTLFLAG_RW,
4398	    pf, 0, ixl_sysctl_set_advertise, "I", IXL_SYSCTL_HELP_SET_ADVERTISE);
4399
4400	SYSCTL_ADD_PROC(ctx, ctx_list,
4401	    OID_AUTO, "supported_speeds", CTLTYPE_INT | CTLFLAG_RD,
4402	    pf, 0, ixl_sysctl_supported_speeds, "I", IXL_SYSCTL_HELP_SUPPORTED_SPEED);
4403
4404	SYSCTL_ADD_PROC(ctx, ctx_list,
4405	    OID_AUTO, "current_speed", CTLTYPE_STRING | CTLFLAG_RD,
4406	    pf, 0, ixl_sysctl_current_speed, "A", "Current Port Speed");
4407
4408	SYSCTL_ADD_PROC(ctx, ctx_list,
4409	    OID_AUTO, "fw_version", CTLTYPE_STRING | CTLFLAG_RD,
4410	    pf, 0, ixl_sysctl_show_fw, "A", "Firmware version");
4411
4412	SYSCTL_ADD_PROC(ctx, ctx_list,
4413	    OID_AUTO, "unallocated_queues", CTLTYPE_INT | CTLFLAG_RD,
4414	    pf, 0, ixl_sysctl_unallocated_queues, "I",
4415	    "Queues not allocated to a PF or VF");
4416
4417	SYSCTL_ADD_PROC(ctx, ctx_list,
4418	    OID_AUTO, "tx_itr", CTLTYPE_INT | CTLFLAG_RW,
4419	    pf, 0, ixl_sysctl_pf_tx_itr, "I",
4420	    "Immediately set TX ITR value for all queues");
4421
4422	SYSCTL_ADD_PROC(ctx, ctx_list,
4423	    OID_AUTO, "rx_itr", CTLTYPE_INT | CTLFLAG_RW,
4424	    pf, 0, ixl_sysctl_pf_rx_itr, "I",
4425	    "Immediately set RX ITR value for all queues");
4426
4427	SYSCTL_ADD_INT(ctx, ctx_list,
4428	    OID_AUTO, "dynamic_rx_itr", CTLFLAG_RW,
4429	    &pf->dynamic_rx_itr, 0, "Enable dynamic RX ITR");
4430
4431	SYSCTL_ADD_INT(ctx, ctx_list,
4432	    OID_AUTO, "dynamic_tx_itr", CTLFLAG_RW,
4433	    &pf->dynamic_tx_itr, 0, "Enable dynamic TX ITR");
4434
4435	SYSCTL_ADD_INT(ctx, ctx_list,
4436	    OID_AUTO, "tx_ring_size", CTLFLAG_RD,
4437	    &pf->vsi.num_tx_desc, 0, "TX ring size");
4438
4439	SYSCTL_ADD_INT(ctx, ctx_list,
4440	    OID_AUTO, "rx_ring_size", CTLFLAG_RD,
4441	    &pf->vsi.num_rx_desc, 0, "RX ring size");
4442
4443	/* Add FEC sysctls for 25G adapters */
4444	if (i40e_is_25G_device(hw->device_id)) {
4445		fec_node = SYSCTL_ADD_NODE(ctx, ctx_list,
4446		    OID_AUTO, "fec", CTLFLAG_RD, NULL, "FEC Sysctls");
4447		fec_list = SYSCTL_CHILDREN(fec_node);
4448
4449		SYSCTL_ADD_PROC(ctx, fec_list,
4450		    OID_AUTO, "fc_ability", CTLTYPE_INT | CTLFLAG_RW,
4451		    pf, 0, ixl_sysctl_fec_fc_ability, "I", "FC FEC ability enabled");
4452
4453		SYSCTL_ADD_PROC(ctx, fec_list,
4454		    OID_AUTO, "rs_ability", CTLTYPE_INT | CTLFLAG_RW,
4455		    pf, 0, ixl_sysctl_fec_rs_ability, "I", "RS FEC ability enabled");
4456
4457		SYSCTL_ADD_PROC(ctx, fec_list,
4458		    OID_AUTO, "fc_requested", CTLTYPE_INT | CTLFLAG_RW,
4459		    pf, 0, ixl_sysctl_fec_fc_request, "I", "FC FEC mode requested on link");
4460
4461		SYSCTL_ADD_PROC(ctx, fec_list,
4462		    OID_AUTO, "rs_requested", CTLTYPE_INT | CTLFLAG_RW,
4463		    pf, 0, ixl_sysctl_fec_rs_request, "I", "RS FEC mode requested on link");
4464
4465		SYSCTL_ADD_PROC(ctx, fec_list,
4466		    OID_AUTO, "auto_fec_enabled", CTLTYPE_INT | CTLFLAG_RW,
4467		    pf, 0, ixl_sysctl_fec_auto_enable, "I", "Let FW decide FEC ability/request modes");
4468	}
4469
4470	SYSCTL_ADD_PROC(ctx, ctx_list,
4471	    OID_AUTO, "fw_lldp", CTLTYPE_INT | CTLFLAG_RW,
4472	    pf, 0, ixl_sysctl_fw_lldp, "I", IXL_SYSCTL_HELP_FW_LLDP);
4473
4474	eee_node = SYSCTL_ADD_NODE(ctx, ctx_list,
4475	    OID_AUTO, "eee", CTLFLAG_RD, NULL,
4476	    "Energy Efficient Ethernet (EEE) Sysctls");
4477	eee_list = SYSCTL_CHILDREN(eee_node);
4478
4479	SYSCTL_ADD_PROC(ctx, eee_list,
4480	    OID_AUTO, "enable", CTLTYPE_INT | CTLFLAG_RW,
4481	    pf, 0, ixl_sysctl_eee_enable, "I",
4482	    "Enable Energy Efficient Ethernet (EEE)");
4483
4484	SYSCTL_ADD_UINT(ctx, eee_list, OID_AUTO, "tx_lpi_status",
4485	    CTLFLAG_RD, &pf->stats.tx_lpi_status, 0,
4486	    "TX LPI status");
4487
4488	SYSCTL_ADD_UINT(ctx, eee_list, OID_AUTO, "rx_lpi_status",
4489	    CTLFLAG_RD, &pf->stats.rx_lpi_status, 0,
4490	    "RX LPI status");
4491
4492	SYSCTL_ADD_UQUAD(ctx, eee_list, OID_AUTO, "tx_lpi_count",
4493	    CTLFLAG_RD, &pf->stats.tx_lpi_count,
4494	    "TX LPI count");
4495
4496	SYSCTL_ADD_UQUAD(ctx, eee_list, OID_AUTO, "rx_lpi_count",
4497	    CTLFLAG_RD, &pf->stats.rx_lpi_count,
4498	    "RX LPI count");
4499	/* Add sysctls meant to print debug information, but don't list them
4500	 * in "sysctl -a" output. */
4501	debug_node = SYSCTL_ADD_NODE(ctx, ctx_list,
4502	    OID_AUTO, "debug", CTLFLAG_RD | CTLFLAG_SKIP, NULL, "Debug Sysctls");
4503	debug_list = SYSCTL_CHILDREN(debug_node);
4504
4505	SYSCTL_ADD_UINT(ctx, debug_list,
4506	    OID_AUTO, "shared_debug_mask", CTLFLAG_RW,
4507	    &pf->hw.debug_mask, 0, "Shared code debug message level");
4508
4509	SYSCTL_ADD_UINT(ctx, debug_list,
4510	    OID_AUTO, "core_debug_mask", CTLFLAG_RW,
4511	    &pf->dbg_mask, 0, "Non-hared code debug message level");
4512
4513	SYSCTL_ADD_PROC(ctx, debug_list,
4514	    OID_AUTO, "link_status", CTLTYPE_STRING | CTLFLAG_RD,
4515	    pf, 0, ixl_sysctl_link_status, "A", IXL_SYSCTL_HELP_LINK_STATUS);
4516
4517	SYSCTL_ADD_PROC(ctx, debug_list,
4518	    OID_AUTO, "phy_abilities", CTLTYPE_STRING | CTLFLAG_RD,
4519	    pf, 0, ixl_sysctl_phy_abilities, "A", "PHY Abilities");
4520
4521	SYSCTL_ADD_PROC(ctx, debug_list,
4522	    OID_AUTO, "filter_list", CTLTYPE_STRING | CTLFLAG_RD,
4523	    pf, 0, ixl_sysctl_sw_filter_list, "A", "SW Filter List");
4524
4525	SYSCTL_ADD_PROC(ctx, debug_list,
4526	    OID_AUTO, "hw_res_alloc", CTLTYPE_STRING | CTLFLAG_RD,
4527	    pf, 0, ixl_sysctl_hw_res_alloc, "A", "HW Resource Allocation");
4528
4529	SYSCTL_ADD_PROC(ctx, debug_list,
4530	    OID_AUTO, "switch_config", CTLTYPE_STRING | CTLFLAG_RD,
4531	    pf, 0, ixl_sysctl_switch_config, "A", "HW Switch Configuration");
4532
4533	SYSCTL_ADD_PROC(ctx, debug_list,
4534	    OID_AUTO, "switch_vlans", CTLTYPE_INT | CTLFLAG_WR,
4535	    pf, 0, ixl_sysctl_switch_vlans, "I", "HW Switch VLAN Configuration");
4536
4537	SYSCTL_ADD_PROC(ctx, debug_list,
4538	    OID_AUTO, "rss_key", CTLTYPE_STRING | CTLFLAG_RD,
4539	    pf, 0, ixl_sysctl_hkey, "A", "View RSS key");
4540
4541	SYSCTL_ADD_PROC(ctx, debug_list,
4542	    OID_AUTO, "rss_lut", CTLTYPE_STRING | CTLFLAG_RD,
4543	    pf, 0, ixl_sysctl_hlut, "A", "View RSS lookup table");
4544
4545	SYSCTL_ADD_PROC(ctx, debug_list,
4546	    OID_AUTO, "rss_hena", CTLTYPE_ULONG | CTLFLAG_RD,
4547	    pf, 0, ixl_sysctl_hena, "LU", "View enabled packet types for RSS");
4548
4549	SYSCTL_ADD_PROC(ctx, debug_list,
4550	    OID_AUTO, "disable_fw_link_management", CTLTYPE_INT | CTLFLAG_WR,
4551	    pf, 0, ixl_sysctl_fw_link_management, "I", "Disable FW Link Management");
4552
4553	SYSCTL_ADD_PROC(ctx, debug_list,
4554	    OID_AUTO, "dump_debug_data", CTLTYPE_STRING | CTLFLAG_RD,
4555	    pf, 0, ixl_sysctl_dump_debug_data, "A", "Dump Debug Data from FW");
4556
4557	if (pf->has_i2c) {
4558		SYSCTL_ADD_PROC(ctx, debug_list,
4559		    OID_AUTO, "read_i2c_byte", CTLTYPE_INT | CTLFLAG_RW,
4560		    pf, 0, ixl_sysctl_read_i2c_byte, "I", "Read byte from I2C bus");
4561
4562		SYSCTL_ADD_PROC(ctx, debug_list,
4563		    OID_AUTO, "write_i2c_byte", CTLTYPE_INT | CTLFLAG_RW,
4564		    pf, 0, ixl_sysctl_write_i2c_byte, "I", "Write byte to I2C bus");
4565
4566		SYSCTL_ADD_PROC(ctx, debug_list,
4567		    OID_AUTO, "read_i2c_diag_data", CTLTYPE_STRING | CTLFLAG_RD,
4568		    pf, 0, ixl_sysctl_read_i2c_diag_data, "A", "Dump selected diagnostic data from FW");
4569	}
4570
4571#ifdef PCI_IOV
4572	SYSCTL_ADD_UINT(ctx, debug_list,
4573	    OID_AUTO, "vc_debug_level", CTLFLAG_RW, &pf->vc_debug_lvl,
4574	    0, "PF/VF Virtual Channel debug level");
4575#endif
4576}
4577
4578/*
4579 * Primarily for finding out how many queues can be assigned to VFs,
4580 * at runtime.
4581 */
4582static int
4583ixl_sysctl_unallocated_queues(SYSCTL_HANDLER_ARGS)
4584{
4585	struct ixl_pf *pf = (struct ixl_pf *)arg1;
4586	int queues;
4587
4588	IXL_PF_LOCK(pf);
4589	queues = (int)ixl_pf_qmgr_get_num_free(&pf->qmgr);
4590	IXL_PF_UNLOCK(pf);
4591
4592	return sysctl_handle_int(oidp, NULL, queues, req);
4593}
4594
4595/*
4596** Set flow control using sysctl:
4597** 	0 - off
4598**	1 - rx pause
4599**	2 - tx pause
4600**	3 - full
4601*/
4602int
4603ixl_sysctl_set_flowcntl(SYSCTL_HANDLER_ARGS)
4604{
4605	struct ixl_pf *pf = (struct ixl_pf *)arg1;
4606	struct i40e_hw *hw = &pf->hw;
4607	device_t dev = pf->dev;
4608	int requested_fc, error = 0;
4609	enum i40e_status_code aq_error = 0;
4610	u8 fc_aq_err = 0;
4611
4612	/* Get request */
4613	requested_fc = pf->fc;
4614	error = sysctl_handle_int(oidp, &requested_fc, 0, req);
4615	if ((error) || (req->newptr == NULL))
4616		return (error);
4617	if ((pf->state & IXL_PF_STATE_RECOVERY_MODE) != 0) {
4618		device_printf(dev, "Interface is currently in FW recovery mode. "
4619				"Setting flow control not supported\n");
4620		return (EINVAL);
4621	}
4622	if (requested_fc < 0 || requested_fc > 3) {
4623		device_printf(dev,
4624		    "Invalid fc mode; valid modes are 0 through 3\n");
4625		return (EINVAL);
4626	}
4627
4628	/* Set fc ability for port */
4629	hw->fc.requested_mode = requested_fc;
4630	aq_error = i40e_set_fc(hw, &fc_aq_err, TRUE);
4631	if (aq_error) {
4632		device_printf(dev,
4633		    "%s: Error setting new fc mode %d; fc_err %#x\n",
4634		    __func__, aq_error, fc_aq_err);
4635		return (EIO);
4636	}
4637	pf->fc = requested_fc;
4638
4639	/* Get new link state */
4640	i40e_msec_delay(250);
4641	hw->phy.get_link_info = TRUE;
4642	i40e_get_link_status(hw, &pf->link_up);
4643
4644	return (0);
4645}
4646
4647
4648static const char *
4649ixl_link_speed_string(u8 link_speed)
4650{
4651	const char * link_speed_str[] = {
4652		"Unknown",
4653		"100 Mbps",
4654		"1 Gbps",
4655		"10 Gbps",
4656		"40 Gbps",
4657		"20 Gbps",
4658		"25 Gbps",
4659		"2.5 Gbps",
4660		"5 Gbps"
4661	};
4662	int index;
4663
4664	switch (link_speed) {
4665		case I40E_LINK_SPEED_100MB:
4666			index = 1;
4667			break;
4668		case I40E_LINK_SPEED_1GB:
4669			index = 2;
4670			break;
4671		case I40E_LINK_SPEED_10GB:
4672			index = 3;
4673			break;
4674		case I40E_LINK_SPEED_40GB:
4675			index = 4;
4676			break;
4677		case I40E_LINK_SPEED_20GB:
4678			index = 5;
4679			break;
4680		case I40E_LINK_SPEED_25GB:
4681			index = 6;
4682			break;
4683		case I40E_LINK_SPEED_2_5GB:
4684			index = 7;
4685			break;
4686		case I40E_LINK_SPEED_5GB:
4687			index = 8;
4688			break;
4689		case I40E_LINK_SPEED_UNKNOWN:
4690		default:
4691			index = 0;
4692			break;
4693	}
4694
4695	return (link_speed_str[index]);
4696}
4697
4698int
4699ixl_sysctl_current_speed(SYSCTL_HANDLER_ARGS)
4700{
4701	struct ixl_pf *pf = (struct ixl_pf *)arg1;
4702	struct i40e_hw *hw = &pf->hw;
4703	int error = 0;
4704
4705	ixl_update_link_status(pf);
4706
4707	error = sysctl_handle_string(oidp,
4708	    __DECONST(void *,
4709		ixl_link_speed_string(hw->phy.link_info.link_speed)),
4710	    8, req);
4711
4712	return (error);
4713}
4714
4715/*
4716 * Converts 8-bit speeds value to and from sysctl flags and
4717 * Admin Queue flags.
4718 */
4719static u8
4720ixl_convert_sysctl_aq_link_speed(u8 speeds, bool to_aq)
4721{
4722#define SPEED_MAP_SIZE 8
4723	static u16 speedmap[SPEED_MAP_SIZE] = {
4724		(I40E_LINK_SPEED_100MB | (0x1 << 8)),
4725		(I40E_LINK_SPEED_1GB   | (0x2 << 8)),
4726		(I40E_LINK_SPEED_10GB  | (0x4 << 8)),
4727		(I40E_LINK_SPEED_20GB  | (0x8 << 8)),
4728		(I40E_LINK_SPEED_25GB  | (0x10 << 8)),
4729		(I40E_LINK_SPEED_40GB  | (0x20 << 8)),
4730		(I40E_LINK_SPEED_2_5GB | (0x40 << 8)),
4731		(I40E_LINK_SPEED_5GB   | (0x80 << 8)),
4732	};
4733	u8 retval = 0;
4734
4735	for (int i = 0; i < SPEED_MAP_SIZE; i++) {
4736		if (to_aq)
4737			retval |= (speeds & (speedmap[i] >> 8)) ? (speedmap[i] & 0xff) : 0;
4738		else
4739			retval |= (speeds & speedmap[i]) ? (speedmap[i] >> 8) : 0;
4740	}
4741
4742	return (retval);
4743}
4744
4745int
4746ixl_set_advertised_speeds(struct ixl_pf *pf, int speeds, bool from_aq)
4747{
4748	struct i40e_hw *hw = &pf->hw;
4749	device_t dev = pf->dev;
4750	struct i40e_aq_get_phy_abilities_resp abilities;
4751	struct i40e_aq_set_phy_config config;
4752	enum i40e_status_code aq_error = 0;
4753
4754	/* Get current capability information */
4755	aq_error = i40e_aq_get_phy_capabilities(hw,
4756	    FALSE, FALSE, &abilities, NULL);
4757	if (aq_error) {
4758		device_printf(dev,
4759		    "%s: Error getting phy capabilities %d,"
4760		    " aq error: %d\n", __func__, aq_error,
4761		    hw->aq.asq_last_status);
4762		return (EIO);
4763	}
4764
4765	/* Prepare new config */
4766	bzero(&config, sizeof(config));
4767	if (from_aq)
4768		config.link_speed = speeds;
4769	else
4770		config.link_speed = ixl_convert_sysctl_aq_link_speed(speeds, true);
4771	config.phy_type = abilities.phy_type;
4772	config.phy_type_ext = abilities.phy_type_ext;
4773	config.abilities = abilities.abilities
4774	    | I40E_AQ_PHY_ENABLE_ATOMIC_LINK;
4775	config.eee_capability = abilities.eee_capability;
4776	config.eeer = abilities.eeer_val;
4777	config.low_power_ctrl = abilities.d3_lpan;
4778	config.fec_config = abilities.fec_cfg_curr_mod_ext_info
4779	    & I40E_AQ_PHY_FEC_CONFIG_MASK;
4780
4781	/* Do aq command & restart link */
4782	aq_error = i40e_aq_set_phy_config(hw, &config, NULL);
4783	if (aq_error) {
4784		device_printf(dev,
4785		    "%s: Error setting new phy config %d,"
4786		    " aq error: %d\n", __func__, aq_error,
4787		    hw->aq.asq_last_status);
4788		return (EIO);
4789	}
4790
4791	return (0);
4792}
4793
4794/*
4795** Supported link speeds
4796**	Flags:
4797**	 0x1 - 100 Mb
4798**	 0x2 - 1G
4799**	 0x4 - 10G
4800**	 0x8 - 20G
4801**	0x10 - 25G
4802**	0x20 - 40G
4803**	0x40 - 2.5G
4804**	0x80 - 5G
4805*/
4806static int
4807ixl_sysctl_supported_speeds(SYSCTL_HANDLER_ARGS)
4808{
4809	struct ixl_pf *pf = (struct ixl_pf *)arg1;
4810	int supported = ixl_convert_sysctl_aq_link_speed(pf->supported_speeds, false);
4811
4812	return sysctl_handle_int(oidp, NULL, supported, req);
4813}
4814
4815/*
4816** Control link advertise speed:
4817**	Flags:
4818**	 0x1 - advertise 100 Mb
4819**	 0x2 - advertise 1G
4820**	 0x4 - advertise 10G
4821**	 0x8 - advertise 20G
4822**	0x10 - advertise 25G
4823**	0x20 - advertise 40G
4824**	0x40 - advertise 2.5G
4825**	0x80 - advertise 5G
4826**
4827**	Set to 0 to disable link
4828*/
4829int
4830ixl_sysctl_set_advertise(SYSCTL_HANDLER_ARGS)
4831{
4832	struct ixl_pf *pf = (struct ixl_pf *)arg1;
4833	device_t dev = pf->dev;
4834	u8 converted_speeds;
4835	int requested_ls = 0;
4836	int error = 0;
4837
4838	/* Read in new mode */
4839	requested_ls = pf->advertised_speed;
4840	error = sysctl_handle_int(oidp, &requested_ls, 0, req);
4841	if ((error) || (req->newptr == NULL))
4842		return (error);
4843	if ((pf->state & IXL_PF_STATE_RECOVERY_MODE) != 0) {
4844		device_printf(dev, "Interface is currently in FW recovery mode. "
4845				"Setting advertise speed not supported\n");
4846		return (EINVAL);
4847	}
4848
4849	/* Error out if bits outside of possible flag range are set */
4850	if ((requested_ls & ~((u8)0xFF)) != 0) {
4851		device_printf(dev, "Input advertised speed out of range; "
4852		    "valid flags are: 0x%02x\n",
4853		    ixl_convert_sysctl_aq_link_speed(pf->supported_speeds, false));
4854		return (EINVAL);
4855	}
4856
4857	/* Check if adapter supports input value */
4858	converted_speeds = ixl_convert_sysctl_aq_link_speed((u8)requested_ls, true);
4859	if ((converted_speeds | pf->supported_speeds) != pf->supported_speeds) {
4860		device_printf(dev, "Invalid advertised speed; "
4861		    "valid flags are: 0x%02x\n",
4862		    ixl_convert_sysctl_aq_link_speed(pf->supported_speeds, false));
4863		return (EINVAL);
4864	}
4865
4866	error = ixl_set_advertised_speeds(pf, requested_ls, false);
4867	if (error)
4868		return (error);
4869
4870	pf->advertised_speed = requested_ls;
4871	ixl_update_link_status(pf);
4872	return (0);
4873}
4874
4875/*
4876 * Input: bitmap of enum i40e_aq_link_speed
4877 */
4878static u64
4879ixl_max_aq_speed_to_value(u8 link_speeds)
4880{
4881	if (link_speeds & I40E_LINK_SPEED_40GB)
4882		return IF_Gbps(40);
4883	if (link_speeds & I40E_LINK_SPEED_25GB)
4884		return IF_Gbps(25);
4885	if (link_speeds & I40E_LINK_SPEED_20GB)
4886		return IF_Gbps(20);
4887	if (link_speeds & I40E_LINK_SPEED_10GB)
4888		return IF_Gbps(10);
4889	if (link_speeds & I40E_LINK_SPEED_5GB)
4890		return IF_Gbps(5);
4891	if (link_speeds & I40E_LINK_SPEED_2_5GB)
4892		return IF_Mbps(2500);
4893	if (link_speeds & I40E_LINK_SPEED_1GB)
4894		return IF_Gbps(1);
4895	if (link_speeds & I40E_LINK_SPEED_100MB)
4896		return IF_Mbps(100);
4897	else
4898		/* Minimum supported link speed */
4899		return IF_Mbps(100);
4900}
4901
4902/*
4903** Get the width and transaction speed of
4904** the bus this adapter is plugged into.
4905*/
4906void
4907ixl_get_bus_info(struct ixl_pf *pf)
4908{
4909	struct i40e_hw *hw = &pf->hw;
4910	device_t dev = pf->dev;
4911        u16 link;
4912        u32 offset, num_ports;
4913	u64 max_speed;
4914
4915	/* Some devices don't use PCIE */
4916	if (hw->mac.type == I40E_MAC_X722)
4917		return;
4918
4919        /* Read PCI Express Capabilities Link Status Register */
4920        pci_find_cap(dev, PCIY_EXPRESS, &offset);
4921        link = pci_read_config(dev, offset + PCIER_LINK_STA, 2);
4922
4923	/* Fill out hw struct with PCIE info */
4924	i40e_set_pci_config_data(hw, link);
4925
4926	/* Use info to print out bandwidth messages */
4927        device_printf(dev,"PCI Express Bus: Speed %s %s\n",
4928            ((hw->bus.speed == i40e_bus_speed_8000) ? "8.0GT/s":
4929            (hw->bus.speed == i40e_bus_speed_5000) ? "5.0GT/s":
4930            (hw->bus.speed == i40e_bus_speed_2500) ? "2.5GT/s":"Unknown"),
4931            (hw->bus.width == i40e_bus_width_pcie_x8) ? "Width x8" :
4932            (hw->bus.width == i40e_bus_width_pcie_x4) ? "Width x4" :
4933            (hw->bus.width == i40e_bus_width_pcie_x2) ? "Width x2" :
4934            (hw->bus.width == i40e_bus_width_pcie_x1) ? "Width x1" :
4935            ("Unknown"));
4936
4937	/*
4938	 * If adapter is in slot with maximum supported speed,
4939	 * no warning message needs to be printed out.
4940	 */
4941	if (hw->bus.speed >= i40e_bus_speed_8000
4942	    && hw->bus.width >= i40e_bus_width_pcie_x8)
4943		return;
4944
4945	num_ports = bitcount32(hw->func_caps.valid_functions);
4946	max_speed = ixl_max_aq_speed_to_value(pf->supported_speeds) / 1000000;
4947
4948	if ((num_ports * max_speed) > hw->bus.speed * hw->bus.width) {
4949                device_printf(dev, "PCI-Express bandwidth available"
4950                    " for this device may be insufficient for"
4951                    " optimal performance.\n");
4952                device_printf(dev, "Please move the device to a different"
4953		    " PCI-e link with more lanes and/or higher"
4954		    " transfer rate.\n");
4955        }
4956}
4957
4958static int
4959ixl_sysctl_show_fw(SYSCTL_HANDLER_ARGS)
4960{
4961	struct ixl_pf	*pf = (struct ixl_pf *)arg1;
4962	struct i40e_hw	*hw = &pf->hw;
4963	struct sbuf	*sbuf;
4964
4965	sbuf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
4966	ixl_nvm_version_str(hw, sbuf);
4967	sbuf_finish(sbuf);
4968	sbuf_delete(sbuf);
4969
4970	return (0);
4971}
4972
4973void
4974ixl_print_nvm_cmd(device_t dev, struct i40e_nvm_access *nvma)
4975{
4976	if ((nvma->command == I40E_NVM_READ) &&
4977	    ((nvma->config & 0xFF) == 0xF) &&
4978	    (((nvma->config & 0xF00) >> 8) == 0xF) &&
4979	    (nvma->offset == 0) &&
4980	    (nvma->data_size == 1)) {
4981		// device_printf(dev, "- Get Driver Status Command\n");
4982	}
4983	else if (nvma->command == I40E_NVM_READ) {
4984
4985	}
4986	else {
4987		switch (nvma->command) {
4988		case 0xB:
4989			device_printf(dev, "- command: I40E_NVM_READ\n");
4990			break;
4991		case 0xC:
4992			device_printf(dev, "- command: I40E_NVM_WRITE\n");
4993			break;
4994		default:
4995			device_printf(dev, "- command: unknown 0x%08x\n", nvma->command);
4996			break;
4997		}
4998
4999		device_printf(dev, "- config (ptr)  : 0x%02x\n", nvma->config & 0xFF);
5000		device_printf(dev, "- config (flags): 0x%01x\n", (nvma->config & 0xF00) >> 8);
5001		device_printf(dev, "- offset : 0x%08x\n", nvma->offset);
5002		device_printf(dev, "- data_s : 0x%08x\n", nvma->data_size);
5003	}
5004}
5005
5006int
5007ixl_handle_nvmupd_cmd(struct ixl_pf *pf, struct ifdrv *ifd)
5008{
5009	struct i40e_hw *hw = &pf->hw;
5010	struct i40e_nvm_access *nvma;
5011	device_t dev = pf->dev;
5012	enum i40e_status_code status = 0;
5013	size_t nvma_size, ifd_len, exp_len;
5014	int err, perrno;
5015
5016	DEBUGFUNC("ixl_handle_nvmupd_cmd");
5017
5018	/* Sanity checks */
5019	nvma_size = sizeof(struct i40e_nvm_access);
5020	ifd_len = ifd->ifd_len;
5021
5022	if (ifd_len < nvma_size ||
5023	    ifd->ifd_data == NULL) {
5024		device_printf(dev, "%s: incorrect ifdrv length or data pointer\n",
5025		    __func__);
5026		device_printf(dev, "%s: ifdrv length: %zu, sizeof(struct i40e_nvm_access): %zu\n",
5027		    __func__, ifd_len, nvma_size);
5028		device_printf(dev, "%s: data pointer: %p\n", __func__,
5029		    ifd->ifd_data);
5030		return (EINVAL);
5031	}
5032
5033	nvma = malloc(ifd_len, M_DEVBUF, M_WAITOK);
5034	err = copyin(ifd->ifd_data, nvma, ifd_len);
5035	if (err) {
5036		device_printf(dev, "%s: Cannot get request from user space\n",
5037		    __func__);
5038		free(nvma, M_DEVBUF);
5039		return (err);
5040	}
5041
5042	if (pf->dbg_mask & IXL_DBG_NVMUPD)
5043		ixl_print_nvm_cmd(dev, nvma);
5044
5045	if (pf->state & IXL_PF_STATE_EMPR_RESETTING) {
5046		int count = 0;
5047		while (count++ < 100) {
5048			i40e_msec_delay(100);
5049			if (!(pf->state & IXL_PF_STATE_EMPR_RESETTING))
5050				break;
5051		}
5052	}
5053
5054	if (pf->state & IXL_PF_STATE_EMPR_RESETTING) {
5055		free(nvma, M_DEVBUF);
5056		return (-EBUSY);
5057	}
5058
5059	if (nvma->data_size < 1 || nvma->data_size > 4096) {
5060		device_printf(dev, "%s: invalid request, data size not in supported range\n",
5061		    __func__);
5062		free(nvma, M_DEVBUF);
5063		return (EINVAL);
5064	}
5065
5066	/*
5067	 * Older versions of the NVM update tool don't set ifd_len to the size
5068	 * of the entire buffer passed to the ioctl. Check the data_size field
5069	 * in the contained i40e_nvm_access struct and ensure everything is
5070	 * copied in from userspace.
5071	 */
5072	exp_len = nvma_size + nvma->data_size - 1; /* One byte is kept in struct */
5073
5074	if (ifd_len < exp_len) {
5075		ifd_len = exp_len;
5076		nvma = realloc(nvma, ifd_len, M_DEVBUF, M_WAITOK);
5077		err = copyin(ifd->ifd_data, nvma, ifd_len);
5078		if (err) {
5079			device_printf(dev, "%s: Cannot get request from user space\n",
5080					__func__);
5081			free(nvma, M_DEVBUF);
5082			return (err);
5083		}
5084	}
5085
5086	IXL_PF_LOCK(pf);
5087	status = i40e_nvmupd_command(hw, nvma, nvma->data, &perrno);
5088	IXL_PF_UNLOCK(pf);
5089
5090	err = copyout(nvma, ifd->ifd_data, ifd_len);
5091	free(nvma, M_DEVBUF);
5092	if (err) {
5093		device_printf(dev, "%s: Cannot return data to user space\n",
5094				__func__);
5095		return (err);
5096	}
5097
5098	/* Let the nvmupdate report errors, show them only when debug is enabled */
5099	if (status != 0 && (pf->dbg_mask & IXL_DBG_NVMUPD) != 0)
5100		device_printf(dev, "i40e_nvmupd_command status %s, perrno %d\n",
5101		    i40e_stat_str(hw, status), perrno);
5102
5103	/*
5104	 * -EPERM is actually ERESTART, which the kernel interprets as it needing
5105	 * to run this ioctl again. So use -EACCES for -EPERM instead.
5106	 */
5107	if (perrno == -EPERM)
5108		return (-EACCES);
5109	else
5110		return (perrno);
5111}
5112
5113int
5114ixl_handle_i2c_eeprom_read_cmd(struct ixl_pf *pf, struct ifreq *ifr)
5115{
5116	struct ifi2creq i2c;
5117	int error = 0;
5118	int i;
5119
5120	if (pf->read_i2c_byte == NULL)
5121		return (EINVAL);
5122
5123#ifdef ifr_data
5124	error = copyin(ifr->ifr_data, &i2c, sizeof(i2c));
5125#else
5126	error = copyin(ifr_data_get_ptr(ifr), &i2c, sizeof(i2c));
5127#endif
5128
5129	if (error != 0)
5130		return (error);
5131	if (i2c.dev_addr != 0xA0 && i2c.dev_addr != 0xA2) {
5132		error = EINVAL;
5133		return (error);
5134	}
5135	if (i2c.len > sizeof(i2c.data)) {
5136		error = EINVAL;
5137		return (error);
5138	}
5139
5140	for (i = 0; i < i2c.len; ++i) {
5141		if (pf->read_i2c_byte(pf, i2c.offset + i,
5142		    i2c.dev_addr, &i2c.data[i]))
5143		return (EIO);
5144	}
5145
5146#ifdef ifr_data
5147	error = copyout(&i2c, ifr->ifr_data, sizeof(i2c));
5148#else
5149	error = copyout(&i2c, ifr_data_get_ptr(ifr), sizeof(i2c));
5150#endif
5151
5152	return (error);
5153}
5154
5155/*********************************************************************
5156 *
5157 *  Media Ioctl callback
5158 *
5159 *  This routine is called whenever the user queries the status of
5160 *  the interface using ifconfig.
5161 *
5162 *  When adding new media types here, make sure to add them to
5163 *  ixl_add_ifmedia(), too.
5164 *
5165 **********************************************************************/
5166void
5167ixl_media_status(struct ifnet * ifp, struct ifmediareq * ifmr)
5168{
5169	struct ixl_vsi	*vsi = ifp->if_softc;
5170	struct ixl_pf	*pf = vsi->back;
5171	struct i40e_hw  *hw = &pf->hw;
5172
5173	INIT_DEBUGOUT("ixl_media_status: begin");
5174
5175	/* Don't touch PF during reset */
5176	if (atomic_load_acq_int(&pf->state) & IXL_PF_STATE_EMPR_RESETTING)
5177		return;
5178
5179	IXL_PF_LOCK(pf);
5180
5181	i40e_get_link_status(hw, &pf->link_up);
5182	ixl_update_link_status(pf);
5183
5184	ifmr->ifm_status = IFM_AVALID;
5185	ifmr->ifm_active = IFM_ETHER;
5186
5187	if (!pf->link_up) {
5188		IXL_PF_UNLOCK(pf);
5189		return;
5190	}
5191
5192	ifmr->ifm_status |= IFM_ACTIVE;
5193
5194	/* Hardware always does full-duplex */
5195	ifmr->ifm_active |= IFM_FDX;
5196
5197	switch (hw->phy.link_info.phy_type) {
5198		/* 100 M */
5199		case I40E_PHY_TYPE_100BASE_TX:
5200			ifmr->ifm_active |= IFM_100_TX;
5201			break;
5202		/* 1 G */
5203		case I40E_PHY_TYPE_1000BASE_T:
5204			ifmr->ifm_active |= IFM_1000_T;
5205			break;
5206		case I40E_PHY_TYPE_1000BASE_SX:
5207			ifmr->ifm_active |= IFM_1000_SX;
5208			break;
5209		case I40E_PHY_TYPE_1000BASE_LX:
5210			ifmr->ifm_active |= IFM_1000_LX;
5211			break;
5212		case I40E_PHY_TYPE_1000BASE_T_OPTICAL:
5213			ifmr->ifm_active |= IFM_1000_T;
5214			break;
5215		/* 2.5 G */
5216		case I40E_PHY_TYPE_2_5GBASE_T:
5217			ifmr->ifm_active |= IFM_2500_T;
5218			break;
5219		/* 5 G */
5220		case I40E_PHY_TYPE_5GBASE_T:
5221			ifmr->ifm_active |= IFM_5000_T;
5222			break;
5223		/* 10 G */
5224		case I40E_PHY_TYPE_10GBASE_SFPP_CU:
5225			ifmr->ifm_active |= IFM_10G_TWINAX;
5226			break;
5227		case I40E_PHY_TYPE_10GBASE_SR:
5228			ifmr->ifm_active |= IFM_10G_SR;
5229			break;
5230		case I40E_PHY_TYPE_10GBASE_LR:
5231			ifmr->ifm_active |= IFM_10G_LR;
5232			break;
5233		case I40E_PHY_TYPE_10GBASE_T:
5234			ifmr->ifm_active |= IFM_10G_T;
5235			break;
5236		case I40E_PHY_TYPE_XAUI:
5237		case I40E_PHY_TYPE_XFI:
5238			ifmr->ifm_active |= IFM_10G_TWINAX;
5239			break;
5240		case I40E_PHY_TYPE_10GBASE_AOC:
5241			ifmr->ifm_active |= IFM_10G_AOC;
5242			break;
5243		/* 25 G */
5244		case I40E_PHY_TYPE_25GBASE_KR:
5245			ifmr->ifm_active |= IFM_25G_KR;
5246			break;
5247		case I40E_PHY_TYPE_25GBASE_CR:
5248			ifmr->ifm_active |= IFM_25G_CR;
5249			break;
5250		case I40E_PHY_TYPE_25GBASE_SR:
5251			ifmr->ifm_active |= IFM_25G_SR;
5252			break;
5253		case I40E_PHY_TYPE_25GBASE_LR:
5254			ifmr->ifm_active |= IFM_25G_LR;
5255			break;
5256		case I40E_PHY_TYPE_25GBASE_AOC:
5257			ifmr->ifm_active |= IFM_25G_AOC;
5258			break;
5259		case I40E_PHY_TYPE_25GBASE_ACC:
5260			ifmr->ifm_active |= IFM_25G_ACC;
5261			break;
5262		/* 40 G */
5263		case I40E_PHY_TYPE_40GBASE_CR4:
5264		case I40E_PHY_TYPE_40GBASE_CR4_CU:
5265			ifmr->ifm_active |= IFM_40G_CR4;
5266			break;
5267		case I40E_PHY_TYPE_40GBASE_SR4:
5268			ifmr->ifm_active |= IFM_40G_SR4;
5269			break;
5270		case I40E_PHY_TYPE_40GBASE_LR4:
5271			ifmr->ifm_active |= IFM_40G_LR4;
5272			break;
5273		case I40E_PHY_TYPE_XLAUI:
5274			ifmr->ifm_active |= IFM_OTHER;
5275			break;
5276		case I40E_PHY_TYPE_1000BASE_KX:
5277			ifmr->ifm_active |= IFM_1000_KX;
5278			break;
5279		case I40E_PHY_TYPE_SGMII:
5280			ifmr->ifm_active |= IFM_1000_SGMII;
5281			break;
5282		/* ERJ: What's the difference between these? */
5283		case I40E_PHY_TYPE_10GBASE_CR1_CU:
5284		case I40E_PHY_TYPE_10GBASE_CR1:
5285			ifmr->ifm_active |= IFM_10G_CR1;
5286			break;
5287		case I40E_PHY_TYPE_10GBASE_KX4:
5288			ifmr->ifm_active |= IFM_10G_KX4;
5289			break;
5290		case I40E_PHY_TYPE_10GBASE_KR:
5291			ifmr->ifm_active |= IFM_10G_KR;
5292			break;
5293		case I40E_PHY_TYPE_SFI:
5294			ifmr->ifm_active |= IFM_10G_SFI;
5295			break;
5296		/* Our single 20G media type */
5297		case I40E_PHY_TYPE_20GBASE_KR2:
5298			ifmr->ifm_active |= IFM_20G_KR2;
5299			break;
5300		case I40E_PHY_TYPE_40GBASE_KR4:
5301			ifmr->ifm_active |= IFM_40G_KR4;
5302			break;
5303		case I40E_PHY_TYPE_XLPPI:
5304		case I40E_PHY_TYPE_40GBASE_AOC:
5305			ifmr->ifm_active |= IFM_40G_XLPPI;
5306			break;
5307		/* Unknown to driver */
5308		default:
5309			ifmr->ifm_active |= IFM_UNKNOWN;
5310			break;
5311	}
5312	/* Report flow control status as well */
5313	if (hw->phy.link_info.an_info & I40E_AQ_LINK_PAUSE_TX)
5314		ifmr->ifm_active |= IFM_ETH_TXPAUSE;
5315	if (hw->phy.link_info.an_info & I40E_AQ_LINK_PAUSE_RX)
5316		ifmr->ifm_active |= IFM_ETH_RXPAUSE;
5317
5318	IXL_PF_UNLOCK(pf);
5319}
5320
5321void
5322ixl_init(void *arg)
5323{
5324	struct ixl_pf *pf = arg;
5325
5326	IXL_PF_LOCK(pf);
5327	ixl_init_locked(pf);
5328	IXL_PF_UNLOCK(pf);
5329}
5330
5331/*
5332 * NOTE: Fortville does not support forcing media speeds. Instead,
5333 * use the set_advertise sysctl to set the speeds Fortville
5334 * will advertise or be allowed to operate at.
5335 */
5336int
5337ixl_media_change(struct ifnet * ifp)
5338{
5339	struct ixl_vsi *vsi = ifp->if_softc;
5340	struct ifmedia *ifm = &vsi->media;
5341
5342	INIT_DEBUGOUT("ixl_media_change: begin");
5343
5344	if (IFM_TYPE(ifm->ifm_media) != IFM_ETHER)
5345		return (EINVAL);
5346
5347	if_printf(ifp, "Use 'advertise_speed' sysctl to change advertised speeds\n");
5348
5349	return (ENODEV);
5350}
5351
5352/*********************************************************************
5353 *  Ioctl entry point
5354 *
5355 *  ixl_ioctl is called when the user wants to configure the
5356 *  interface.
5357 *
5358 *  return 0 on success, positive on failure
5359 **********************************************************************/
5360
5361int
5362ixl_ioctl(struct ifnet * ifp, u_long command, caddr_t data)
5363{
5364	struct ixl_vsi	*vsi = ifp->if_softc;
5365	struct ixl_pf	*pf = vsi->back;
5366	struct ifreq	*ifr = (struct ifreq *)data;
5367	struct ifdrv	*ifd = (struct ifdrv *)data;
5368#if defined(INET) || defined(INET6)
5369	struct ifaddr *ifa = (struct ifaddr *)data;
5370	bool		avoid_reset = FALSE;
5371#endif
5372	int             error = 0;
5373
5374	if ((atomic_load_acq_int(&pf->state) & IXL_PF_STATE_RECOVERY_MODE) != 0) {
5375		/* We are in recovery mode supporting only NVM update */
5376		switch (command) {
5377		case SIOCSDRVSPEC:
5378		case SIOCGDRVSPEC:
5379			IOCTL_DEBUGOUT("ioctl: SIOCxDRVSPEC (Get/Set Driver-specific "
5380			    "Info)\n");
5381
5382			/* NVM update command */
5383			if (ifd->ifd_cmd == I40E_NVM_ACCESS)
5384				error = ixl_handle_nvmupd_cmd(pf, ifd);
5385			else
5386				error = EINVAL;
5387			break;
5388		default:
5389			error = EINVAL;
5390			break;
5391		}
5392
5393		return (error);
5394	}
5395
5396	switch (command) {
5397
5398        case SIOCSIFADDR:
5399		IOCTL_DEBUGOUT("ioctl: SIOCSIFADDR (Set Interface Address)");
5400#ifdef INET
5401		if (ifa->ifa_addr->sa_family == AF_INET)
5402			avoid_reset = TRUE;
5403#endif
5404#ifdef INET6
5405		if (ifa->ifa_addr->sa_family == AF_INET6)
5406			avoid_reset = TRUE;
5407#endif
5408#if defined(INET) || defined(INET6)
5409		/*
5410		** Calling init results in link renegotiation,
5411		** so we avoid doing it when possible.
5412		*/
5413		if (avoid_reset) {
5414			ifp->if_flags |= IFF_UP;
5415			if (!(ifp->if_drv_flags & IFF_DRV_RUNNING))
5416				ixl_init(pf);
5417#ifdef INET
5418			if (!(ifp->if_flags & IFF_NOARP))
5419				arp_ifinit(ifp, ifa);
5420#endif
5421		} else
5422			error = ether_ioctl(ifp, command, data);
5423		break;
5424#endif
5425	case SIOCSIFMTU:
5426		IOCTL_DEBUGOUT("ioctl: SIOCSIFMTU (Set Interface MTU)");
5427		if (ifr->ifr_mtu > IXL_MAX_FRAME -
5428		   ETHER_HDR_LEN - ETHER_CRC_LEN - ETHER_VLAN_ENCAP_LEN) {
5429			error = EINVAL;
5430		} else {
5431			IXL_PF_LOCK(pf);
5432			ifp->if_mtu = ifr->ifr_mtu;
5433			vsi->max_frame_size =
5434				ifp->if_mtu + ETHER_HDR_LEN + ETHER_CRC_LEN
5435			    + ETHER_VLAN_ENCAP_LEN;
5436			ixl_init_locked(pf);
5437			IXL_PF_UNLOCK(pf);
5438		}
5439		break;
5440	case SIOCSIFFLAGS:
5441		IOCTL_DEBUGOUT("ioctl: SIOCSIFFLAGS (Set Interface Flags)");
5442		IXL_PF_LOCK(pf);
5443		if (ifp->if_flags & IFF_UP) {
5444			if ((ifp->if_drv_flags & IFF_DRV_RUNNING)) {
5445				if ((ifp->if_flags ^ pf->if_flags) &
5446				    (IFF_PROMISC | IFF_ALLMULTI)) {
5447					ixl_set_promisc(vsi);
5448				}
5449			} else
5450				ixl_init_locked(pf);
5451		} else if (ifp->if_drv_flags & IFF_DRV_RUNNING)
5452			ixl_stop_locked(pf);
5453
5454		pf->if_flags = ifp->if_flags;
5455		IXL_PF_UNLOCK(pf);
5456		break;
5457	case SIOCSDRVSPEC:
5458	case SIOCGDRVSPEC:
5459		IOCTL_DEBUGOUT("ioctl: SIOCxDRVSPEC (Get/Set Driver-specific "
5460		    "Info)\n");
5461
5462		/* NVM update command */
5463		if (ifd->ifd_cmd == I40E_NVM_ACCESS)
5464			error = ixl_handle_nvmupd_cmd(pf, ifd);
5465		else
5466			error = EINVAL;
5467		break;
5468	case SIOCADDMULTI:
5469		IOCTL_DEBUGOUT("ioctl: SIOCADDMULTI");
5470		if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
5471			IXL_PF_LOCK(pf);
5472			ixl_disable_rings_intr(vsi);
5473			ixl_add_multi(vsi);
5474			ixl_enable_intr(vsi);
5475			IXL_PF_UNLOCK(pf);
5476		}
5477		break;
5478	case SIOCDELMULTI:
5479		IOCTL_DEBUGOUT("ioctl: SIOCDELMULTI");
5480		if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
5481			IXL_PF_LOCK(pf);
5482			ixl_disable_rings_intr(vsi);
5483			ixl_del_multi(vsi);
5484			ixl_enable_intr(vsi);
5485			IXL_PF_UNLOCK(pf);
5486		}
5487		break;
5488	case SIOCSIFMEDIA:
5489	case SIOCGIFMEDIA:
5490	case SIOCGIFXMEDIA:
5491		IOCTL_DEBUGOUT("ioctl: SIOCxIFMEDIA (Get/Set Interface Media)");
5492		error = ifmedia_ioctl(ifp, ifr, &vsi->media, command);
5493		break;
5494	case SIOCSIFCAP:
5495	{
5496		int mask = ifr->ifr_reqcap ^ ifp->if_capenable;
5497		IOCTL_DEBUGOUT("ioctl: SIOCSIFCAP (Set Capabilities)");
5498
5499		ixl_cap_txcsum_tso(vsi, ifp, mask);
5500
5501		if (mask & IFCAP_RXCSUM)
5502			ifp->if_capenable ^= IFCAP_RXCSUM;
5503		if (mask & IFCAP_RXCSUM_IPV6)
5504			ifp->if_capenable ^= IFCAP_RXCSUM_IPV6;
5505		if (mask & IFCAP_LRO)
5506			ifp->if_capenable ^= IFCAP_LRO;
5507		if (mask & IFCAP_VLAN_HWTAGGING)
5508			ifp->if_capenable ^= IFCAP_VLAN_HWTAGGING;
5509		if (mask & IFCAP_VLAN_HWFILTER)
5510			ifp->if_capenable ^= IFCAP_VLAN_HWFILTER;
5511		if (mask & IFCAP_VLAN_HWTSO)
5512			ifp->if_capenable ^= IFCAP_VLAN_HWTSO;
5513		if (ifp->if_drv_flags & IFF_DRV_RUNNING) {
5514			IXL_PF_LOCK(pf);
5515			ixl_init_locked(pf);
5516			IXL_PF_UNLOCK(pf);
5517		}
5518		VLAN_CAPABILITIES(ifp);
5519
5520		break;
5521	}
5522#if __FreeBSD_version >= 1003000
5523	case SIOCGI2C:
5524	{
5525		IOCTL_DEBUGOUT("ioctl: SIOCGI2C (Get I2C Data)");
5526		if (!pf->has_i2c)
5527			return (ENOTTY);
5528
5529		error = ixl_handle_i2c_eeprom_read_cmd(pf, ifr);
5530		break;
5531	}
5532#endif
5533	default:
5534		IOCTL_DEBUGOUT("ioctl: UNKNOWN (0x%X)\n", (int)command);
5535		error = ether_ioctl(ifp, command, data);
5536		break;
5537	}
5538
5539	return (error);
5540}
5541
5542int
5543ixl_find_i2c_interface(struct ixl_pf *pf)
5544{
5545	struct i40e_hw *hw = &pf->hw;
5546	bool i2c_en, port_matched;
5547	u32 reg;
5548
5549	for (int i = 0; i < 4; i++) {
5550		reg = rd32(hw, I40E_GLGEN_MDIO_I2C_SEL(i));
5551		i2c_en = (reg & I40E_GLGEN_MDIO_I2C_SEL_MDIO_I2C_SEL_MASK);
5552		port_matched = ((reg & I40E_GLGEN_MDIO_I2C_SEL_PHY_PORT_NUM_MASK)
5553		    >> I40E_GLGEN_MDIO_I2C_SEL_PHY_PORT_NUM_SHIFT)
5554		    & BIT(hw->port);
5555		if (i2c_en && port_matched)
5556			return (i);
5557	}
5558
5559	return (-1);
5560}
5561
5562static char *
5563ixl_phy_type_string(u32 bit_pos, bool ext)
5564{
5565	static char * phy_types_str[32] = {
5566		"SGMII",
5567		"1000BASE-KX",
5568		"10GBASE-KX4",
5569		"10GBASE-KR",
5570		"40GBASE-KR4",
5571		"XAUI",
5572		"XFI",
5573		"SFI",
5574		"XLAUI",
5575		"XLPPI",
5576		"40GBASE-CR4",
5577		"10GBASE-CR1",
5578		"SFP+ Active DA",
5579		"QSFP+ Active DA",
5580		"Reserved (14)",
5581		"Reserved (15)",
5582		"Reserved (16)",
5583		"100BASE-TX",
5584		"1000BASE-T",
5585		"10GBASE-T",
5586		"10GBASE-SR",
5587		"10GBASE-LR",
5588		"10GBASE-SFP+Cu",
5589		"10GBASE-CR1",
5590		"40GBASE-CR4",
5591		"40GBASE-SR4",
5592		"40GBASE-LR4",
5593		"1000BASE-SX",
5594		"1000BASE-LX",
5595		"1000BASE-T Optical",
5596		"20GBASE-KR2",
5597		"Reserved (31)"
5598	};
5599	static char * ext_phy_types_str[8] = {
5600		"25GBASE-KR",
5601		"25GBASE-CR",
5602		"25GBASE-SR",
5603		"25GBASE-LR",
5604		"25GBASE-AOC",
5605		"25GBASE-ACC",
5606		"2.5GBASE-T",
5607		"5GBASE-T"
5608	};
5609
5610	if (ext && bit_pos > 7) return "Invalid_Ext";
5611	if (bit_pos > 31) return "Invalid";
5612
5613	return (ext) ? ext_phy_types_str[bit_pos] : phy_types_str[bit_pos];
5614}
5615
5616static char *
5617ixl_phy_type_string_ls(u8 val)
5618{
5619	if (val >= 0x1F)
5620		return ixl_phy_type_string(val - 0x1F, true);
5621	else
5622		return ixl_phy_type_string(val, false);
5623}
5624
5625int
5626ixl_aq_get_link_status(struct ixl_pf *pf, struct i40e_aqc_get_link_status *link_status)
5627{
5628	device_t dev = pf->dev;
5629	struct i40e_hw *hw = &pf->hw;
5630	struct i40e_aq_desc desc;
5631	enum i40e_status_code status;
5632
5633	struct i40e_aqc_get_link_status *aq_link_status =
5634		(struct i40e_aqc_get_link_status *)&desc.params.raw;
5635
5636	i40e_fill_default_direct_cmd_desc(&desc, i40e_aqc_opc_get_link_status);
5637	link_status->command_flags = CPU_TO_LE16(I40E_AQ_LSE_ENABLE);
5638	status = i40e_asq_send_command(hw, &desc, NULL, 0, NULL);
5639	if (status) {
5640		device_printf(dev,
5641		    "%s: i40e_aqc_opc_get_link_status status %s, aq error %s\n",
5642		    __func__, i40e_stat_str(hw, status),
5643		    i40e_aq_str(hw, hw->aq.asq_last_status));
5644		return (EIO);
5645	}
5646
5647	bcopy(aq_link_status, link_status, sizeof(struct i40e_aqc_get_link_status));
5648	return (0);
5649}
5650
5651static int
5652ixl_sysctl_link_status(SYSCTL_HANDLER_ARGS)
5653{
5654	struct ixl_pf *pf = (struct ixl_pf *)arg1;
5655	device_t dev = pf->dev;
5656	struct sbuf *buf;
5657	int error = 0;
5658
5659	buf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
5660	if (!buf) {
5661		device_printf(dev, "Could not allocate sbuf for sysctl output.\n");
5662		return (ENOMEM);
5663	}
5664
5665	struct i40e_aqc_get_link_status link_status;
5666	error = ixl_aq_get_link_status(pf, &link_status);
5667	if (error) {
5668		sbuf_delete(buf);
5669		return (error);
5670	}
5671
5672	sbuf_printf(buf, "\n"
5673	    "PHY Type : 0x%02x<%s>\n"
5674	    "Speed    : 0x%02x\n"
5675	    "Link info: 0x%02x\n"
5676	    "AN info  : 0x%02x\n"
5677	    "Ext info : 0x%02x\n"
5678	    "Loopback : 0x%02x\n"
5679	    "Max Frame: %d\n"
5680	    "Config   : 0x%02x\n"
5681	    "Power    : 0x%02x",
5682	    link_status.phy_type,
5683	    ixl_phy_type_string_ls(link_status.phy_type),
5684	    link_status.link_speed,
5685	    link_status.link_info,
5686	    link_status.an_info,
5687	    link_status.ext_info,
5688	    link_status.loopback,
5689	    link_status.max_frame_size,
5690	    link_status.config,
5691	    link_status.power_desc);
5692
5693	error = sbuf_finish(buf);
5694	if (error)
5695		device_printf(dev, "Error finishing sbuf: %d\n", error);
5696
5697	sbuf_delete(buf);
5698	return (error);
5699}
5700
5701static int
5702ixl_sysctl_phy_abilities(SYSCTL_HANDLER_ARGS)
5703{
5704	struct ixl_pf *pf = (struct ixl_pf *)arg1;
5705	struct i40e_hw *hw = &pf->hw;
5706	device_t dev = pf->dev;
5707	enum i40e_status_code status;
5708	struct i40e_aq_get_phy_abilities_resp abilities;
5709	struct sbuf *buf;
5710	int error = 0;
5711
5712	buf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
5713	if (!buf) {
5714		device_printf(dev, "Could not allocate sbuf for sysctl output.\n");
5715		return (ENOMEM);
5716	}
5717
5718	status = i40e_aq_get_phy_capabilities(hw,
5719	    FALSE, FALSE, &abilities, NULL);
5720	if (status) {
5721		device_printf(dev,
5722		    "%s: i40e_aq_get_phy_capabilities() status %s, aq error %s\n",
5723		    __func__, i40e_stat_str(hw, status),
5724		    i40e_aq_str(hw, hw->aq.asq_last_status));
5725		sbuf_delete(buf);
5726		return (EIO);
5727	}
5728
5729	sbuf_printf(buf, "\n"
5730	    "PHY Type : %08x",
5731	    abilities.phy_type);
5732
5733	if (abilities.phy_type != 0) {
5734		sbuf_printf(buf, "<");
5735		for (int i = 0; i < 32; i++)
5736			if ((1 << i) & abilities.phy_type)
5737				sbuf_printf(buf, "%s,", ixl_phy_type_string(i, false));
5738		sbuf_printf(buf, ">");
5739	}
5740
5741	sbuf_printf(buf, "\nPHY Ext  : %02x",
5742	    abilities.phy_type_ext);
5743
5744	if (abilities.phy_type_ext != 0) {
5745		sbuf_printf(buf, "<");
5746		for (int i = 0; i < 4; i++)
5747			if ((1 << i) & abilities.phy_type_ext)
5748				sbuf_printf(buf, "%s,",
5749				    ixl_phy_type_string(i, true));
5750		sbuf_printf(buf, ">");
5751	}
5752
5753	sbuf_printf(buf, "\nSpeed    : %02x", abilities.link_speed);
5754	if (abilities.link_speed != 0) {
5755		u8 link_speed;
5756		sbuf_printf(buf, " <");
5757		for (int i = 0; i < 8; i++) {
5758			link_speed = (1 << i) & abilities.link_speed;
5759			if (link_speed)
5760				sbuf_printf(buf, "%s, ",
5761				    ixl_link_speed_string(link_speed));
5762		}
5763		sbuf_printf(buf, ">");
5764	}
5765
5766	sbuf_printf(buf, "\n"
5767	    "Abilities: %02x\n"
5768	    "EEE cap  : %04x\n"
5769	    "EEER reg : %08x\n"
5770	    "D3 Lpan  : %02x\n"
5771	    "ID       : %02x %02x %02x %02x\n"
5772	    "ModType  : %02x %02x %02x\n"
5773	    "ModType E: %01x\n"
5774	    "FEC Cfg  : %02x\n"
5775	    "Ext CC   : %02x",
5776	    abilities.abilities, abilities.eee_capability,
5777	    abilities.eeer_val, abilities.d3_lpan,
5778	    abilities.phy_id[0], abilities.phy_id[1],
5779	    abilities.phy_id[2], abilities.phy_id[3],
5780	    abilities.module_type[0], abilities.module_type[1],
5781	    abilities.module_type[2], (abilities.fec_cfg_curr_mod_ext_info & 0xe0) >> 5,
5782	    abilities.fec_cfg_curr_mod_ext_info & 0x1F,
5783	    abilities.ext_comp_code);
5784
5785	error = sbuf_finish(buf);
5786	if (error)
5787		device_printf(dev, "Error finishing sbuf: %d\n", error);
5788
5789	sbuf_delete(buf);
5790	return (error);
5791}
5792
5793static int
5794ixl_sysctl_sw_filter_list(SYSCTL_HANDLER_ARGS)
5795{
5796	struct ixl_pf *pf = (struct ixl_pf *)arg1;
5797	struct ixl_vsi *vsi = &pf->vsi;
5798	struct ixl_mac_filter *f;
5799	char *buf, *buf_i;
5800
5801	int error = 0;
5802	int ftl_len = 0;
5803	int ftl_counter = 0;
5804	int buf_len = 0;
5805	int entry_len = 42;
5806
5807	SLIST_FOREACH(f, &vsi->ftl, next) {
5808		ftl_len++;
5809	}
5810
5811	if (ftl_len < 1) {
5812		sysctl_handle_string(oidp, "(none)", 6, req);
5813		return (0);
5814	}
5815
5816	buf_len = sizeof(char) * (entry_len + 1) * ftl_len + 2;
5817	buf = buf_i = malloc(buf_len, M_DEVBUF, M_NOWAIT);
5818
5819	sprintf(buf_i++, "\n");
5820	SLIST_FOREACH(f, &vsi->ftl, next) {
5821		sprintf(buf_i,
5822		    MAC_FORMAT ", vlan %4d, flags %#06x",
5823		    MAC_FORMAT_ARGS(f->macaddr), f->vlan, f->flags);
5824		buf_i += entry_len;
5825		/* don't print '\n' for last entry */
5826		if (++ftl_counter != ftl_len) {
5827			sprintf(buf_i, "\n");
5828			buf_i++;
5829		}
5830	}
5831
5832	error = sysctl_handle_string(oidp, buf, strlen(buf), req);
5833	if (error)
5834		printf("sysctl error: %d\n", error);
5835	free(buf, M_DEVBUF);
5836	return error;
5837}
5838
5839#define IXL_SW_RES_SIZE 0x14
5840int
5841ixl_res_alloc_cmp(const void *a, const void *b)
5842{
5843	const struct i40e_aqc_switch_resource_alloc_element_resp *one, *two;
5844	one = (const struct i40e_aqc_switch_resource_alloc_element_resp *)a;
5845	two = (const struct i40e_aqc_switch_resource_alloc_element_resp *)b;
5846
5847	return ((int)one->resource_type - (int)two->resource_type);
5848}
5849
5850/*
5851 * Longest string length: 25
5852 */
5853char *
5854ixl_switch_res_type_string(u8 type)
5855{
5856	static char * ixl_switch_res_type_strings[0x14] = {
5857		"VEB",
5858		"VSI",
5859		"Perfect Match MAC address",
5860		"S-tag",
5861		"(Reserved)",
5862		"Multicast hash entry",
5863		"Unicast hash entry",
5864		"VLAN",
5865		"VSI List entry",
5866		"(Reserved)",
5867		"VLAN Statistic Pool",
5868		"Mirror Rule",
5869		"Queue Set",
5870		"Inner VLAN Forward filter",
5871		"(Reserved)",
5872		"Inner MAC",
5873		"IP",
5874		"GRE/VN1 Key",
5875		"VN2 Key",
5876		"Tunneling Port"
5877	};
5878
5879	if (type < 0x14)
5880		return ixl_switch_res_type_strings[type];
5881	else
5882		return "(Reserved)";
5883}
5884
5885static int
5886ixl_sysctl_hw_res_alloc(SYSCTL_HANDLER_ARGS)
5887{
5888	struct ixl_pf *pf = (struct ixl_pf *)arg1;
5889	struct i40e_hw *hw = &pf->hw;
5890	device_t dev = pf->dev;
5891	struct sbuf *buf;
5892	enum i40e_status_code status;
5893	int error = 0;
5894
5895	u8 num_entries;
5896	struct i40e_aqc_switch_resource_alloc_element_resp resp[IXL_SW_RES_SIZE];
5897
5898	buf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
5899	if (!buf) {
5900		device_printf(dev, "Could not allocate sbuf for output.\n");
5901		return (ENOMEM);
5902	}
5903
5904	bzero(resp, sizeof(resp));
5905	status = i40e_aq_get_switch_resource_alloc(hw, &num_entries,
5906				resp,
5907				IXL_SW_RES_SIZE,
5908				NULL);
5909	if (status) {
5910		device_printf(dev,
5911		    "%s: get_switch_resource_alloc() error %s, aq error %s\n",
5912		    __func__, i40e_stat_str(hw, status),
5913		    i40e_aq_str(hw, hw->aq.asq_last_status));
5914		sbuf_delete(buf);
5915		return (error);
5916	}
5917
5918	/* Sort entries by type for display */
5919	qsort(resp, num_entries,
5920	    sizeof(struct i40e_aqc_switch_resource_alloc_element_resp),
5921	    &ixl_res_alloc_cmp);
5922
5923	sbuf_cat(buf, "\n");
5924	sbuf_printf(buf, "# of entries: %d\n", num_entries);
5925	sbuf_printf(buf,
5926	    "                     Type | Guaranteed | Total | Used   | Un-allocated\n"
5927	    "                          | (this)     | (all) | (this) | (all)       \n");
5928	for (int i = 0; i < num_entries; i++) {
5929		sbuf_printf(buf,
5930		    "%25s | %10d   %5d   %6d   %12d",
5931		    ixl_switch_res_type_string(resp[i].resource_type),
5932		    resp[i].guaranteed,
5933		    resp[i].total,
5934		    resp[i].used,
5935		    resp[i].total_unalloced);
5936		if (i < num_entries - 1)
5937			sbuf_cat(buf, "\n");
5938	}
5939
5940	error = sbuf_finish(buf);
5941	if (error)
5942		device_printf(dev, "Error finishing sbuf: %d\n", error);
5943
5944	sbuf_delete(buf);
5945	return (error);
5946}
5947
5948/*
5949** Caller must init and delete sbuf; this function will clear and
5950** finish it for caller.
5951**
5952** XXX: Cannot use the SEID for this, since there is no longer a
5953** fixed mapping between SEID and element type.
5954*/
5955char *
5956ixl_switch_element_string(struct sbuf *s,
5957    struct i40e_aqc_switch_config_element_resp *element)
5958{
5959	sbuf_clear(s);
5960
5961	switch (element->element_type) {
5962	case I40E_AQ_SW_ELEM_TYPE_MAC:
5963		sbuf_printf(s, "MAC %3d", element->element_info);
5964		break;
5965	case I40E_AQ_SW_ELEM_TYPE_PF:
5966		sbuf_printf(s, "PF  %3d", element->element_info);
5967		break;
5968	case I40E_AQ_SW_ELEM_TYPE_VF:
5969		sbuf_printf(s, "VF  %3d", element->element_info);
5970		break;
5971	case I40E_AQ_SW_ELEM_TYPE_EMP:
5972		sbuf_cat(s, "EMP");
5973		break;
5974	case I40E_AQ_SW_ELEM_TYPE_BMC:
5975		sbuf_cat(s, "BMC");
5976		break;
5977	case I40E_AQ_SW_ELEM_TYPE_PV:
5978		sbuf_cat(s, "PV");
5979		break;
5980	case I40E_AQ_SW_ELEM_TYPE_VEB:
5981		sbuf_cat(s, "VEB");
5982		break;
5983	case I40E_AQ_SW_ELEM_TYPE_PA:
5984		sbuf_cat(s, "PA");
5985		break;
5986	case I40E_AQ_SW_ELEM_TYPE_VSI:
5987		sbuf_printf(s, "VSI %3d", element->element_info);
5988		break;
5989	default:
5990		sbuf_cat(s, "?");
5991		break;
5992	}
5993
5994	sbuf_finish(s);
5995	return sbuf_data(s);
5996}
5997
5998static int
5999ixl_sysctl_switch_config(SYSCTL_HANDLER_ARGS)
6000{
6001	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6002	struct i40e_hw *hw = &pf->hw;
6003	device_t dev = pf->dev;
6004	struct sbuf *buf;
6005	struct sbuf *nmbuf;
6006	enum i40e_status_code status;
6007	int error = 0;
6008	u16 next = 0;
6009	u8 aq_buf[I40E_AQ_LARGE_BUF];
6010
6011	struct i40e_aqc_get_switch_config_resp *sw_config;
6012	sw_config = (struct i40e_aqc_get_switch_config_resp *)aq_buf;
6013
6014	buf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
6015	if (!buf) {
6016		device_printf(dev, "Could not allocate sbuf for sysctl output.\n");
6017		return (ENOMEM);
6018	}
6019
6020	status = i40e_aq_get_switch_config(hw, sw_config,
6021	    sizeof(aq_buf), &next, NULL);
6022	if (status) {
6023		device_printf(dev,
6024		    "%s: aq_get_switch_config() error %s, aq error %s\n",
6025		    __func__, i40e_stat_str(hw, status),
6026		    i40e_aq_str(hw, hw->aq.asq_last_status));
6027		sbuf_delete(buf);
6028		return error;
6029	}
6030	if (next)
6031		device_printf(dev, "%s: TODO: get more config with SEID %d\n",
6032		    __func__, next);
6033
6034	nmbuf = sbuf_new_auto();
6035	if (!nmbuf) {
6036		device_printf(dev, "Could not allocate sbuf for name output.\n");
6037		sbuf_delete(buf);
6038		return (ENOMEM);
6039	}
6040
6041	sbuf_cat(buf, "\n");
6042	/* Assuming <= 255 elements in switch */
6043	sbuf_printf(buf, "# of reported elements: %d\n", sw_config->header.num_reported);
6044	sbuf_printf(buf, "total # of elements: %d\n", sw_config->header.num_total);
6045	/* Exclude:
6046	** Revision -- all elements are revision 1 for now
6047	*/
6048	sbuf_printf(buf,
6049	    "SEID (  Name  ) |  Uplink  | Downlink | Conn Type\n"
6050	    "                |          |          | (uplink)\n");
6051	for (int i = 0; i < sw_config->header.num_reported; i++) {
6052		// "%4d (%8s) | %8s   %8s   %#8x",
6053		sbuf_printf(buf, "%4d", sw_config->element[i].seid);
6054		sbuf_cat(buf, " ");
6055		sbuf_printf(buf, "(%8s)", ixl_switch_element_string(nmbuf,
6056		    &sw_config->element[i]));
6057		sbuf_cat(buf, " | ");
6058		sbuf_printf(buf, "%8d", sw_config->element[i].uplink_seid);
6059		sbuf_cat(buf, "   ");
6060		sbuf_printf(buf, "%8d", sw_config->element[i].downlink_seid);
6061		sbuf_cat(buf, "   ");
6062		sbuf_printf(buf, "%#8x", sw_config->element[i].connection_type);
6063		if (i < sw_config->header.num_reported - 1)
6064			sbuf_cat(buf, "\n");
6065	}
6066	sbuf_delete(nmbuf);
6067
6068	error = sbuf_finish(buf);
6069	if (error)
6070		device_printf(dev, "Error finishing sbuf: %d\n", error);
6071
6072	sbuf_delete(buf);
6073
6074	return (error);
6075}
6076
6077static int
6078ixl_sysctl_switch_vlans(SYSCTL_HANDLER_ARGS)
6079{
6080	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6081	struct i40e_hw *hw = &pf->hw;
6082	device_t dev = pf->dev;
6083	int requested_vlan = -1;
6084	enum i40e_status_code status = 0;
6085	int error = 0;
6086
6087	error = sysctl_handle_int(oidp, &requested_vlan, 0, req);
6088	if ((error) || (req->newptr == NULL))
6089	    return (error);
6090
6091	if ((hw->flags & I40E_HW_FLAG_802_1AD_CAPABLE) == 0) {
6092		device_printf(dev, "Flags disallow setting of vlans\n");
6093		return (ENODEV);
6094	}
6095
6096	hw->switch_tag = requested_vlan;
6097	device_printf(dev,
6098	    "Setting switch config to switch_tag=%04x, first_tag=%04x, second_tag=%04x\n",
6099	    hw->switch_tag, hw->first_tag, hw->second_tag);
6100	status = i40e_aq_set_switch_config(hw, 0, 0, 0, NULL);
6101	if (status) {
6102		device_printf(dev,
6103		    "%s: aq_set_switch_config() error %s, aq error %s\n",
6104		    __func__, i40e_stat_str(hw, status),
6105		    i40e_aq_str(hw, hw->aq.asq_last_status));
6106		return (status);
6107	}
6108	return (0);
6109}
6110
6111static int
6112ixl_sysctl_hkey(SYSCTL_HANDLER_ARGS)
6113{
6114	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6115	struct i40e_hw *hw = &pf->hw;
6116	device_t dev = pf->dev;
6117	struct sbuf *buf;
6118	int error = 0;
6119	enum i40e_status_code status;
6120	u32 reg;
6121
6122	struct i40e_aqc_get_set_rss_key_data key_data;
6123
6124	buf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
6125	if (!buf) {
6126		device_printf(dev, "Could not allocate sbuf for output.\n");
6127		return (ENOMEM);
6128	}
6129
6130	bzero(key_data.standard_rss_key, sizeof(key_data.standard_rss_key));
6131
6132	sbuf_cat(buf, "\n");
6133	if (hw->mac.type == I40E_MAC_X722) {
6134		status = i40e_aq_get_rss_key(hw, pf->vsi.vsi_num, &key_data);
6135		if (status)
6136			device_printf(dev, "i40e_aq_get_rss_key status %s, error %s\n",
6137			    i40e_stat_str(hw, status), i40e_aq_str(hw, hw->aq.asq_last_status));
6138	} else {
6139		for (int i = 0; i < IXL_RSS_KEY_SIZE_REG; i++) {
6140			reg = i40e_read_rx_ctl(hw, I40E_PFQF_HKEY(i));
6141			bcopy(&reg, ((caddr_t)&key_data) + (i << 2), 4);
6142		}
6143	}
6144
6145	ixl_sbuf_print_bytes(buf, (u8 *)&key_data, sizeof(key_data), 0, true);
6146
6147	error = sbuf_finish(buf);
6148	if (error)
6149		device_printf(dev, "Error finishing sbuf: %d\n", error);
6150	sbuf_delete(buf);
6151
6152	return (error);
6153}
6154
6155static void
6156ixl_sbuf_print_bytes(struct sbuf *sb, u8 *buf, int length, int label_offset, bool text)
6157{
6158	int i, j, k, width;
6159	char c;
6160
6161	if (length < 1 || buf == NULL) return;
6162
6163	int byte_stride = 16;
6164	int lines = length / byte_stride;
6165	int rem = length % byte_stride;
6166	if (rem > 0)
6167		lines++;
6168
6169	for (i = 0; i < lines; i++) {
6170		width = (rem > 0 && i == lines - 1)
6171		    ? rem : byte_stride;
6172
6173		sbuf_printf(sb, "%4d | ", label_offset + i * byte_stride);
6174
6175		for (j = 0; j < width; j++)
6176			sbuf_printf(sb, "%02x ", buf[i * byte_stride + j]);
6177
6178		if (width < byte_stride) {
6179			for (k = 0; k < (byte_stride - width); k++)
6180				sbuf_printf(sb, "   ");
6181		}
6182
6183		if (!text) {
6184			sbuf_printf(sb, "\n");
6185			continue;
6186		}
6187
6188		for (j = 0; j < width; j++) {
6189			c = (char)buf[i * byte_stride + j];
6190			if (c < 32 || c > 126)
6191				sbuf_printf(sb, ".");
6192			else
6193				sbuf_printf(sb, "%c", c);
6194
6195			if (j == width - 1)
6196				sbuf_printf(sb, "\n");
6197		}
6198	}
6199}
6200
6201static int
6202ixl_sysctl_hlut(SYSCTL_HANDLER_ARGS)
6203{
6204	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6205	struct i40e_hw *hw = &pf->hw;
6206	device_t dev = pf->dev;
6207	struct sbuf *buf;
6208	int error = 0;
6209	enum i40e_status_code status;
6210	u8 hlut[512];
6211	u32 reg;
6212
6213	buf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
6214	if (!buf) {
6215		device_printf(dev, "Could not allocate sbuf for output.\n");
6216		return (ENOMEM);
6217	}
6218
6219	bzero(hlut, sizeof(hlut));
6220	sbuf_cat(buf, "\n");
6221	if (hw->mac.type == I40E_MAC_X722) {
6222		status = i40e_aq_get_rss_lut(hw, pf->vsi.vsi_num, TRUE, hlut, sizeof(hlut));
6223		if (status)
6224			device_printf(dev, "i40e_aq_get_rss_lut status %s, error %s\n",
6225			    i40e_stat_str(hw, status), i40e_aq_str(hw, hw->aq.asq_last_status));
6226	} else {
6227		for (int i = 0; i < hw->func_caps.rss_table_size >> 2; i++) {
6228			reg = rd32(hw, I40E_PFQF_HLUT(i));
6229			bcopy(&reg, &hlut[i << 2], 4);
6230		}
6231	}
6232	ixl_sbuf_print_bytes(buf, hlut, 512, 0, false);
6233
6234	error = sbuf_finish(buf);
6235	if (error)
6236		device_printf(dev, "Error finishing sbuf: %d\n", error);
6237	sbuf_delete(buf);
6238
6239	return (error);
6240}
6241
6242static int
6243ixl_sysctl_hena(SYSCTL_HANDLER_ARGS)
6244{
6245	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6246	struct i40e_hw *hw = &pf->hw;
6247	u64 hena;
6248
6249	hena = (u64)i40e_read_rx_ctl(hw, I40E_PFQF_HENA(0)) |
6250	    ((u64)i40e_read_rx_ctl(hw, I40E_PFQF_HENA(1)) << 32);
6251
6252	return sysctl_handle_long(oidp, NULL, hena, req);
6253}
6254
6255/*
6256 * Sysctl to disable firmware's link management
6257 *
6258 * 1 - Disable link management on this port
6259 * 0 - Re-enable link management
6260 *
6261 * On normal NVMs, firmware manages link by default.
6262 */
6263static int
6264ixl_sysctl_fw_link_management(SYSCTL_HANDLER_ARGS)
6265{
6266	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6267	struct i40e_hw *hw = &pf->hw;
6268	device_t dev = pf->dev;
6269	int requested_mode = -1;
6270	enum i40e_status_code status = 0;
6271	int error = 0;
6272
6273	/* Read in new mode */
6274	error = sysctl_handle_int(oidp, &requested_mode, 0, req);
6275	if ((error) || (req->newptr == NULL))
6276		return (error);
6277	/* Check for sane value */
6278	if (requested_mode < 0 || requested_mode > 1) {
6279		device_printf(dev, "Valid modes are 0 or 1\n");
6280		return (EINVAL);
6281	}
6282
6283	/* Set new mode */
6284	status = i40e_aq_set_phy_debug(hw, !!(requested_mode) << 4, NULL);
6285	if (status) {
6286		device_printf(dev,
6287		    "%s: Error setting new phy debug mode %s,"
6288		    " aq error: %s\n", __func__, i40e_stat_str(hw, status),
6289		    i40e_aq_str(hw, hw->aq.asq_last_status));
6290		return (EIO);
6291	}
6292
6293	return (0);
6294}
6295
6296/*
6297 * Read some diagnostic data from a (Q)SFP+ module
6298 *
6299 *             SFP A2   QSFP Lower Page
6300 * Temperature 96-97	22-23
6301 * Vcc         98-99    26-27
6302 * TX power    102-103  34-35..40-41
6303 * RX power    104-105  50-51..56-57
6304 */
6305static int
6306ixl_sysctl_read_i2c_diag_data(SYSCTL_HANDLER_ARGS)
6307{
6308	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6309	device_t dev = pf->dev;
6310	struct sbuf *sbuf;
6311	int error = 0;
6312	u8 output;
6313
6314	if (req->oldptr == NULL) {
6315		error = SYSCTL_OUT(req, 0, 128);
6316		return (0);
6317	}
6318
6319	error = pf->read_i2c_byte(pf, 0, 0xA0, &output);
6320	if (error) {
6321		device_printf(dev, "Error reading from i2c\n");
6322		return (error);
6323	}
6324
6325	/* 0x3 for SFP; 0xD/0x11 for QSFP+/QSFP28 */
6326	if (output == 0x3) {
6327		/*
6328		 * Check for:
6329		 * - Internally calibrated data
6330		 * - Diagnostic monitoring is implemented
6331		 */
6332		pf->read_i2c_byte(pf, 92, 0xA0, &output);
6333		if (!(output & 0x60)) {
6334			device_printf(dev, "Module doesn't support diagnostics: %02X\n", output);
6335			return (0);
6336		}
6337
6338		sbuf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
6339
6340		for (u8 offset = 96; offset < 100; offset++) {
6341			pf->read_i2c_byte(pf, offset, 0xA2, &output);
6342			sbuf_printf(sbuf, "%02X ", output);
6343		}
6344		for (u8 offset = 102; offset < 106; offset++) {
6345			pf->read_i2c_byte(pf, offset, 0xA2, &output);
6346			sbuf_printf(sbuf, "%02X ", output);
6347		}
6348	} else if (output == 0xD || output == 0x11) {
6349		/*
6350		 * QSFP+ modules are always internally calibrated, and must indicate
6351		 * what types of diagnostic monitoring are implemented
6352		 */
6353		sbuf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
6354
6355		for (u8 offset = 22; offset < 24; offset++) {
6356			pf->read_i2c_byte(pf, offset, 0xA0, &output);
6357			sbuf_printf(sbuf, "%02X ", output);
6358		}
6359		for (u8 offset = 26; offset < 28; offset++) {
6360			pf->read_i2c_byte(pf, offset, 0xA0, &output);
6361			sbuf_printf(sbuf, "%02X ", output);
6362		}
6363		/* Read the data from the first lane */
6364		for (u8 offset = 34; offset < 36; offset++) {
6365			pf->read_i2c_byte(pf, offset, 0xA0, &output);
6366			sbuf_printf(sbuf, "%02X ", output);
6367		}
6368		for (u8 offset = 50; offset < 52; offset++) {
6369			pf->read_i2c_byte(pf, offset, 0xA0, &output);
6370			sbuf_printf(sbuf, "%02X ", output);
6371		}
6372	} else {
6373		device_printf(dev, "Module is not SFP/SFP+/SFP28/QSFP+ (%02X)\n", output);
6374		return (0);
6375	}
6376
6377	sbuf_finish(sbuf);
6378	sbuf_delete(sbuf);
6379
6380	return (0);
6381}
6382
6383/*
6384 * Sysctl to read a byte from I2C bus.
6385 *
6386 * Input: 32-bit value:
6387 * 	bits 0-7:   device address (0xA0 or 0xA2)
6388 * 	bits 8-15:  offset (0-255)
6389 *	bits 16-31: unused
6390 * Output: 8-bit value read
6391 */
6392static int
6393ixl_sysctl_read_i2c_byte(SYSCTL_HANDLER_ARGS)
6394{
6395	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6396	device_t dev = pf->dev;
6397	int input = -1, error = 0;
6398
6399	u8 dev_addr, offset, output;
6400
6401	/* Read in I2C read parameters */
6402	error = sysctl_handle_int(oidp, &input, 0, req);
6403	if ((error) || (req->newptr == NULL))
6404		return (error);
6405	/* Validate device address */
6406	dev_addr = input & 0xFF;
6407	if (dev_addr != 0xA0 && dev_addr != 0xA2) {
6408		return (EINVAL);
6409	}
6410	offset = (input >> 8) & 0xFF;
6411
6412	error = pf->read_i2c_byte(pf, offset, dev_addr, &output);
6413	if (error)
6414		return (error);
6415
6416	device_printf(dev, "%02X\n", output);
6417	return (0);
6418}
6419
6420/*
6421 * Sysctl to write a byte to the I2C bus.
6422 *
6423 * Input: 32-bit value:
6424 * 	bits 0-7:   device address (0xA0 or 0xA2)
6425 * 	bits 8-15:  offset (0-255)
6426 *	bits 16-23: value to write
6427 *	bits 24-31: unused
6428 * Output: 8-bit value written
6429 */
6430static int
6431ixl_sysctl_write_i2c_byte(SYSCTL_HANDLER_ARGS)
6432{
6433	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6434	device_t dev = pf->dev;
6435	int input = -1, error = 0;
6436
6437	u8 dev_addr, offset, value;
6438
6439	/* Read in I2C write parameters */
6440	error = sysctl_handle_int(oidp, &input, 0, req);
6441	if ((error) || (req->newptr == NULL))
6442		return (error);
6443	/* Validate device address */
6444	dev_addr = input & 0xFF;
6445	if (dev_addr != 0xA0 && dev_addr != 0xA2) {
6446		return (EINVAL);
6447	}
6448	offset = (input >> 8) & 0xFF;
6449	value = (input >> 16) & 0xFF;
6450
6451	error = pf->write_i2c_byte(pf, offset, dev_addr, value);
6452	if (error)
6453		return (error);
6454
6455	device_printf(dev, "%02X written\n", value);
6456	return (0);
6457}
6458
6459static int
6460ixl_get_fec_config(struct ixl_pf *pf, struct i40e_aq_get_phy_abilities_resp *abilities,
6461    u8 bit_pos, int *is_set)
6462{
6463	device_t dev = pf->dev;
6464	struct i40e_hw *hw = &pf->hw;
6465	enum i40e_status_code status;
6466
6467	status = i40e_aq_get_phy_capabilities(hw,
6468	    FALSE, FALSE, abilities, NULL);
6469	if (status) {
6470		device_printf(dev,
6471		    "%s: i40e_aq_get_phy_capabilities() status %s, aq error %s\n",
6472		    __func__, i40e_stat_str(hw, status),
6473		    i40e_aq_str(hw, hw->aq.asq_last_status));
6474		return (EIO);
6475	}
6476
6477	*is_set = !!(abilities->fec_cfg_curr_mod_ext_info & bit_pos);
6478	return (0);
6479}
6480
6481static int
6482ixl_set_fec_config(struct ixl_pf *pf, struct i40e_aq_get_phy_abilities_resp *abilities,
6483    u8 bit_pos, int set)
6484{
6485	device_t dev = pf->dev;
6486	struct i40e_hw *hw = &pf->hw;
6487	struct i40e_aq_set_phy_config config;
6488	enum i40e_status_code status;
6489
6490	/* Set new PHY config */
6491	memset(&config, 0, sizeof(config));
6492	config.fec_config = abilities->fec_cfg_curr_mod_ext_info & ~(bit_pos);
6493	if (set)
6494		config.fec_config |= bit_pos;
6495	if (config.fec_config != abilities->fec_cfg_curr_mod_ext_info) {
6496		config.abilities |= I40E_AQ_PHY_ENABLE_ATOMIC_LINK;
6497		config.phy_type = abilities->phy_type;
6498		config.phy_type_ext = abilities->phy_type_ext;
6499		config.link_speed = abilities->link_speed;
6500		config.eee_capability = abilities->eee_capability;
6501		config.eeer = abilities->eeer_val;
6502		config.low_power_ctrl = abilities->d3_lpan;
6503		status = i40e_aq_set_phy_config(hw, &config, NULL);
6504
6505		if (status) {
6506			device_printf(dev,
6507			    "%s: i40e_aq_set_phy_config() status %s, aq error %s\n",
6508			    __func__, i40e_stat_str(hw, status),
6509			    i40e_aq_str(hw, hw->aq.asq_last_status));
6510			return (EIO);
6511		}
6512	}
6513
6514	return (0);
6515}
6516
6517static int
6518ixl_sysctl_fec_fc_ability(SYSCTL_HANDLER_ARGS)
6519{
6520	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6521	int mode, error = 0;
6522
6523	struct i40e_aq_get_phy_abilities_resp abilities;
6524	error = ixl_get_fec_config(pf, &abilities, I40E_AQ_ENABLE_FEC_KR, &mode);
6525	if (error)
6526		return (error);
6527	/* Read in new mode */
6528	error = sysctl_handle_int(oidp, &mode, 0, req);
6529	if ((error) || (req->newptr == NULL))
6530		return (error);
6531
6532	return ixl_set_fec_config(pf, &abilities, I40E_AQ_SET_FEC_ABILITY_KR, !!(mode));
6533}
6534
6535static int
6536ixl_sysctl_fec_rs_ability(SYSCTL_HANDLER_ARGS)
6537{
6538	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6539	int mode, error = 0;
6540
6541	struct i40e_aq_get_phy_abilities_resp abilities;
6542	error = ixl_get_fec_config(pf, &abilities, I40E_AQ_ENABLE_FEC_RS, &mode);
6543	if (error)
6544		return (error);
6545	/* Read in new mode */
6546	error = sysctl_handle_int(oidp, &mode, 0, req);
6547	if ((error) || (req->newptr == NULL))
6548		return (error);
6549
6550	return ixl_set_fec_config(pf, &abilities, I40E_AQ_SET_FEC_ABILITY_RS, !!(mode));
6551}
6552
6553static int
6554ixl_sysctl_fec_fc_request(SYSCTL_HANDLER_ARGS)
6555{
6556	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6557	int mode, error = 0;
6558
6559	struct i40e_aq_get_phy_abilities_resp abilities;
6560	error = ixl_get_fec_config(pf, &abilities, I40E_AQ_REQUEST_FEC_KR, &mode);
6561	if (error)
6562		return (error);
6563	/* Read in new mode */
6564	error = sysctl_handle_int(oidp, &mode, 0, req);
6565	if ((error) || (req->newptr == NULL))
6566		return (error);
6567
6568	return ixl_set_fec_config(pf, &abilities, I40E_AQ_SET_FEC_REQUEST_KR, !!(mode));
6569}
6570
6571static int
6572ixl_sysctl_fec_rs_request(SYSCTL_HANDLER_ARGS)
6573{
6574	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6575	int mode, error = 0;
6576
6577	struct i40e_aq_get_phy_abilities_resp abilities;
6578	error = ixl_get_fec_config(pf, &abilities, I40E_AQ_REQUEST_FEC_RS, &mode);
6579	if (error)
6580		return (error);
6581	/* Read in new mode */
6582	error = sysctl_handle_int(oidp, &mode, 0, req);
6583	if ((error) || (req->newptr == NULL))
6584		return (error);
6585
6586	return ixl_set_fec_config(pf, &abilities, I40E_AQ_SET_FEC_REQUEST_RS, !!(mode));
6587}
6588
6589static int
6590ixl_sysctl_fec_auto_enable(SYSCTL_HANDLER_ARGS)
6591{
6592	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6593	int mode, error = 0;
6594
6595	struct i40e_aq_get_phy_abilities_resp abilities;
6596	error = ixl_get_fec_config(pf, &abilities, I40E_AQ_ENABLE_FEC_AUTO, &mode);
6597	if (error)
6598		return (error);
6599	/* Read in new mode */
6600	error = sysctl_handle_int(oidp, &mode, 0, req);
6601	if ((error) || (req->newptr == NULL))
6602		return (error);
6603
6604	return ixl_set_fec_config(pf, &abilities, I40E_AQ_SET_FEC_AUTO, !!(mode));
6605}
6606
6607static int
6608ixl_sysctl_dump_debug_data(SYSCTL_HANDLER_ARGS)
6609{
6610	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6611	struct i40e_hw *hw = &pf->hw;
6612	device_t dev = pf->dev;
6613	struct sbuf *buf;
6614	int error = 0;
6615	enum i40e_status_code status;
6616
6617	buf = sbuf_new_for_sysctl(NULL, NULL, 128, req);
6618	if (!buf) {
6619		device_printf(dev, "Could not allocate sbuf for output.\n");
6620		return (ENOMEM);
6621	}
6622
6623	u8 *final_buff;
6624	/* This amount is only necessary if reading the entire cluster into memory */
6625#define IXL_FINAL_BUFF_SIZE	(1280 * 1024)
6626	final_buff = malloc(IXL_FINAL_BUFF_SIZE, M_DEVBUF, M_WAITOK);
6627	int final_buff_len = 0;
6628
6629	u8 cluster_id = 1;
6630	bool more = true;
6631
6632	u8 dump_buf[4096];
6633	u16 curr_buff_size = 4096;
6634	u8 curr_next_table = 0;
6635	u32 curr_next_index = 0;
6636
6637	u16 ret_buff_size;
6638	u8 ret_next_table;
6639	u32 ret_next_index;
6640
6641	sbuf_cat(buf, "\n");
6642
6643	while (more) {
6644		status = i40e_aq_debug_dump(hw, cluster_id, curr_next_table, curr_next_index, curr_buff_size,
6645		    dump_buf, &ret_buff_size, &ret_next_table, &ret_next_index, NULL);
6646		if (status) {
6647			device_printf(dev, "i40e_aq_debug_dump status %s, error %s\n",
6648			    i40e_stat_str(hw, status), i40e_aq_str(hw, hw->aq.asq_last_status));
6649			goto free_out;
6650		}
6651
6652		/* copy info out of temp buffer */
6653		bcopy(dump_buf, (caddr_t)final_buff + final_buff_len, ret_buff_size);
6654		final_buff_len += ret_buff_size;
6655
6656		if (ret_next_table != curr_next_table) {
6657			/* We're done with the current table; we can dump out read data. */
6658			sbuf_printf(buf, "%d:", curr_next_table);
6659			int bytes_printed = 0;
6660			while (bytes_printed <= final_buff_len) {
6661				sbuf_printf(buf, "%16D", ((caddr_t)final_buff + bytes_printed), "");
6662				bytes_printed += 16;
6663			}
6664				sbuf_cat(buf, "\n");
6665
6666			/* The entire cluster has been read; we're finished */
6667			if (ret_next_table == 0xFF)
6668				break;
6669
6670			/* Otherwise clear the output buffer and continue reading */
6671			bzero(final_buff, IXL_FINAL_BUFF_SIZE);
6672			final_buff_len = 0;
6673		}
6674
6675		if (ret_next_index == 0xFFFFFFFF)
6676			ret_next_index = 0;
6677
6678		bzero(dump_buf, sizeof(dump_buf));
6679		curr_next_table = ret_next_table;
6680		curr_next_index = ret_next_index;
6681	}
6682
6683free_out:
6684	free(final_buff, M_DEVBUF);
6685	error = sbuf_finish(buf);
6686	if (error)
6687		device_printf(dev, "Error finishing sbuf: %d\n", error);
6688	sbuf_delete(buf);
6689
6690	return (error);
6691}
6692
6693static int
6694ixl_start_fw_lldp(struct ixl_pf *pf)
6695{
6696	struct i40e_hw *hw = &pf->hw;
6697	enum i40e_status_code status;
6698
6699	status = i40e_aq_start_lldp(hw, false, NULL);
6700	if (status != I40E_SUCCESS) {
6701		switch (hw->aq.asq_last_status) {
6702		case I40E_AQ_RC_EEXIST:
6703			device_printf(pf->dev,
6704			    "FW LLDP agent is already running\n");
6705			break;
6706		case I40E_AQ_RC_EPERM:
6707			device_printf(pf->dev,
6708			    "Device configuration forbids SW from starting "
6709			    "the LLDP agent. Set the \"LLDP Agent\" UEFI HII "
6710			    "attribute to \"Enabled\" to use this sysctl\n");
6711			return (EINVAL);
6712		default:
6713			device_printf(pf->dev,
6714			    "Starting FW LLDP agent failed: error: %s, %s\n",
6715			    i40e_stat_str(hw, status),
6716			    i40e_aq_str(hw, hw->aq.asq_last_status));
6717			return (EINVAL);
6718		}
6719	}
6720
6721	atomic_clear_int(&pf->state, IXL_PF_STATE_FW_LLDP_DISABLED);
6722	return (0);
6723}
6724
6725static int
6726ixl_stop_fw_lldp(struct ixl_pf *pf)
6727{
6728	struct i40e_hw *hw = &pf->hw;
6729	device_t dev = pf->dev;
6730	enum i40e_status_code status;
6731
6732	if (hw->func_caps.npar_enable != 0) {
6733		device_printf(dev,
6734		    "Disabling FW LLDP agent is not supported on this device\n");
6735		return (EINVAL);
6736	}
6737
6738	if ((hw->flags & I40E_HW_FLAG_FW_LLDP_STOPPABLE) == 0) {
6739		device_printf(dev,
6740		    "Disabling FW LLDP agent is not supported in this FW version. Please update FW to enable this feature.\n");
6741		return (EINVAL);
6742	}
6743
6744	status = i40e_aq_stop_lldp(hw, true, false, NULL);
6745	if (status != I40E_SUCCESS) {
6746		if (hw->aq.asq_last_status != I40E_AQ_RC_EPERM) {
6747			device_printf(dev,
6748			    "Disabling FW LLDP agent failed: error: %s, %s\n",
6749			    i40e_stat_str(hw, status),
6750			    i40e_aq_str(hw, hw->aq.asq_last_status));
6751			return (EINVAL);
6752		}
6753
6754		device_printf(dev, "FW LLDP agent is already stopped\n");
6755	}
6756
6757	i40e_aq_set_dcb_parameters(hw, true, NULL);
6758	atomic_set_int(&pf->state, IXL_PF_STATE_FW_LLDP_DISABLED);
6759	return (0);
6760}
6761
6762static int
6763ixl_sysctl_fw_lldp(SYSCTL_HANDLER_ARGS)
6764{
6765	struct ixl_pf *pf = (struct ixl_pf *)arg1;
6766	int state, new_state, error = 0;
6767
6768	state = new_state = ((pf->state & IXL_PF_STATE_FW_LLDP_DISABLED) == 0);
6769
6770	/* Read in new mode */
6771	error = sysctl_handle_int(oidp, &new_state, 0, req);
6772	if ((error) || (req->newptr == NULL))
6773		return (error);
6774
6775	/* Already in requested state */
6776	if (new_state == state)
6777		return (error);
6778
6779	if (new_state == 0)
6780		return ixl_stop_fw_lldp(pf);
6781
6782	return ixl_start_fw_lldp(pf);
6783}
6784
6785static int
6786ixl_sysctl_eee_enable(SYSCTL_HANDLER_ARGS)
6787{
6788	struct ixl_pf         *pf = (struct ixl_pf *)arg1;
6789	int                   state, new_state;
6790	int                   sysctl_handle_status = 0;
6791	enum i40e_status_code cmd_status;
6792
6793	/* Init states' values */
6794	state = new_state = (!!(pf->state & IXL_PF_STATE_EEE_ENABLED));
6795
6796	/* Get requested mode */
6797	sysctl_handle_status = sysctl_handle_int(oidp, &new_state, 0, req);
6798	if ((sysctl_handle_status) || (req->newptr == NULL))
6799		return (sysctl_handle_status);
6800
6801	/* Check if state has changed */
6802	if (new_state == state)
6803		return (0);
6804
6805	/* Set new state */
6806	cmd_status = i40e_enable_eee(&pf->hw, (bool)(!!new_state));
6807
6808	/* Save new state or report error */
6809	if (!cmd_status) {
6810		if (new_state == 0)
6811			atomic_clear_int(&pf->state, IXL_PF_STATE_EEE_ENABLED);
6812		else
6813			atomic_set_int(&pf->state, IXL_PF_STATE_EEE_ENABLED);
6814	} else if (cmd_status == I40E_ERR_CONFIG)
6815		return (EPERM);
6816	else
6817		return (EIO);
6818
6819	return (0);
6820}
6821
6822int
6823ixl_attach_get_link_status(struct ixl_pf *pf)
6824{
6825	struct i40e_hw *hw = &pf->hw;
6826	device_t dev = pf->dev;
6827	int error = 0;
6828
6829	if (((hw->aq.fw_maj_ver == 4) && (hw->aq.fw_min_ver < 33)) ||
6830	    (hw->aq.fw_maj_ver < 4)) {
6831		i40e_msec_delay(75);
6832		error = i40e_aq_set_link_restart_an(hw, TRUE, NULL);
6833		if (error) {
6834			device_printf(dev, "link restart failed, aq_err=%d\n",
6835			    pf->hw.aq.asq_last_status);
6836			return error;
6837		}
6838	}
6839
6840	/* Determine link state */
6841	hw->phy.get_link_info = TRUE;
6842	i40e_get_link_status(hw, &pf->link_up);
6843	return (0);
6844}
6845