siena_nic.c revision 311481
1/*-
2 * Copyright (c) 2009-2016 Solarflare Communications Inc.
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 *
8 * 1. Redistributions of source code must retain the above copyright notice,
9 *    this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright notice,
11 *    this list of conditions and the following disclaimer in the documentation
12 *    and/or other materials provided with the distribution.
13 *
14 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
16 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
18 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
19 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
20 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
21 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
22 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
23 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
24 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25 *
26 * The views and conclusions contained in the software and documentation are
27 * those of the authors and should not be interpreted as representing official
28 * policies, either expressed or implied, of the FreeBSD Project.
29 */
30
31#include <sys/cdefs.h>
32__FBSDID("$FreeBSD: stable/11/sys/dev/sfxge/common/siena_nic.c 311481 2017-01-06 07:05:02Z arybchik $");
33
34#include "efx.h"
35#include "efx_impl.h"
36#include "mcdi_mon.h"
37
38#if EFSYS_OPT_SIENA
39
40#if EFSYS_OPT_VPD || EFSYS_OPT_NVRAM
41
42static	__checkReturn		efx_rc_t
43siena_nic_get_partn_mask(
44	__in			efx_nic_t *enp,
45	__out			unsigned int *maskp)
46{
47	efx_mcdi_req_t req;
48	uint8_t payload[MAX(MC_CMD_NVRAM_TYPES_IN_LEN,
49			    MC_CMD_NVRAM_TYPES_OUT_LEN)];
50	efx_rc_t rc;
51
52	(void) memset(payload, 0, sizeof (payload));
53	req.emr_cmd = MC_CMD_NVRAM_TYPES;
54	req.emr_in_buf = payload;
55	req.emr_in_length = MC_CMD_NVRAM_TYPES_IN_LEN;
56	req.emr_out_buf = payload;
57	req.emr_out_length = MC_CMD_NVRAM_TYPES_OUT_LEN;
58
59	efx_mcdi_execute(enp, &req);
60
61	if (req.emr_rc != 0) {
62		rc = req.emr_rc;
63		goto fail1;
64	}
65
66	if (req.emr_out_length_used < MC_CMD_NVRAM_TYPES_OUT_LEN) {
67		rc = EMSGSIZE;
68		goto fail2;
69	}
70
71	*maskp = MCDI_OUT_DWORD(req, NVRAM_TYPES_OUT_TYPES);
72
73	return (0);
74
75fail2:
76	EFSYS_PROBE(fail2);
77fail1:
78	EFSYS_PROBE1(fail1, efx_rc_t, rc);
79
80	return (rc);
81}
82
83#endif /* EFSYS_OPT_VPD || EFSYS_OPT_NVRAM */
84
85static	__checkReturn	efx_rc_t
86siena_board_cfg(
87	__in		efx_nic_t *enp)
88{
89	efx_nic_cfg_t *encp = &(enp->en_nic_cfg);
90	uint8_t mac_addr[6];
91	efx_dword_t capabilities;
92	uint32_t board_type;
93	uint32_t nevq, nrxq, ntxq;
94	efx_rc_t rc;
95
96	/* External port identifier using one-based port numbering */
97	encp->enc_external_port = (uint8_t)enp->en_mcdi.em_emip.emi_port;
98
99	/* Board configuration */
100	if ((rc = efx_mcdi_get_board_cfg(enp, &board_type,
101		    &capabilities, mac_addr)) != 0)
102		goto fail1;
103
104	EFX_MAC_ADDR_COPY(encp->enc_mac_addr, mac_addr);
105
106	encp->enc_board_type = board_type;
107
108	/*
109	 * There is no possibility to determine the number of PFs on Siena
110	 * by issuing MCDI request, and it is not an easy task to find the
111	 * value based on the board type, so 'enc_hw_pf_count' is set to 1
112	 */
113	encp->enc_hw_pf_count = 1;
114
115	/* Additional capabilities */
116	encp->enc_clk_mult = 1;
117	if (EFX_DWORD_FIELD(capabilities, MC_CMD_CAPABILITIES_TURBO)) {
118		enp->en_features |= EFX_FEATURE_TURBO;
119
120		if (EFX_DWORD_FIELD(capabilities,
121			MC_CMD_CAPABILITIES_TURBO_ACTIVE)) {
122			encp->enc_clk_mult = 2;
123		}
124	}
125
126	encp->enc_evq_timer_quantum_ns =
127		EFX_EVQ_SIENA_TIMER_QUANTUM_NS / encp->enc_clk_mult;
128	encp->enc_evq_timer_max_us = (encp->enc_evq_timer_quantum_ns <<
129		FRF_CZ_TC_TIMER_VAL_WIDTH) / 1000;
130
131	/* When hash header insertion is enabled, Siena inserts 16 bytes */
132	encp->enc_rx_prefix_size = 16;
133
134	/* Alignment for receive packet DMA buffers */
135	encp->enc_rx_buf_align_start = 1;
136	encp->enc_rx_buf_align_end = 1;
137
138	/* Alignment for WPTR updates */
139	encp->enc_rx_push_align = 1;
140
141	/* Resource limits */
142	rc = efx_mcdi_get_resource_limits(enp, &nevq, &nrxq, &ntxq);
143	if (rc != 0) {
144		if (rc != ENOTSUP)
145			goto fail2;
146
147		nevq = 1024;
148		nrxq = EFX_RXQ_LIMIT_TARGET;
149		ntxq = EFX_TXQ_LIMIT_TARGET;
150	}
151	encp->enc_evq_limit = nevq;
152	encp->enc_rxq_limit = MIN(EFX_RXQ_LIMIT_TARGET, nrxq);
153	encp->enc_txq_limit = MIN(EFX_TXQ_LIMIT_TARGET, ntxq);
154
155	encp->enc_buftbl_limit = SIENA_SRAM_ROWS -
156	    (encp->enc_txq_limit * EFX_TXQ_DC_NDESCS(EFX_TXQ_DC_SIZE)) -
157	    (encp->enc_rxq_limit * EFX_RXQ_DC_NDESCS(EFX_RXQ_DC_SIZE));
158
159	encp->enc_hw_tx_insert_vlan_enabled = B_FALSE;
160	encp->enc_fw_assisted_tso_enabled = B_FALSE;
161	encp->enc_fw_assisted_tso_v2_enabled = B_FALSE;
162	encp->enc_fw_assisted_tso_v2_n_contexts = 0;
163	encp->enc_allow_set_mac_with_installed_filters = B_TRUE;
164
165	/* Siena supports two 10G ports, and 8 lanes of PCIe Gen2 */
166	encp->enc_required_pcie_bandwidth_mbps = 2 * 10000;
167	encp->enc_max_pcie_link_gen = EFX_PCIE_LINK_SPEED_GEN2;
168
169	encp->enc_fw_verified_nvram_update_required = B_FALSE;
170
171	return (0);
172
173fail2:
174	EFSYS_PROBE(fail2);
175fail1:
176	EFSYS_PROBE1(fail1, efx_rc_t, rc);
177
178	return (rc);
179}
180
181static	__checkReturn	efx_rc_t
182siena_phy_cfg(
183	__in		efx_nic_t *enp)
184{
185	efx_nic_cfg_t *encp = &(enp->en_nic_cfg);
186	efx_rc_t rc;
187
188	/* Fill out fields in enp->en_port and enp->en_nic_cfg from MCDI */
189	if ((rc = efx_mcdi_get_phy_cfg(enp)) != 0)
190		goto fail1;
191
192#if EFSYS_OPT_PHY_STATS
193	/* Convert the MCDI statistic mask into the EFX_PHY_STAT mask */
194	siena_phy_decode_stats(enp, encp->enc_mcdi_phy_stat_mask,
195			    NULL, &encp->enc_phy_stat_mask, NULL);
196#endif	/* EFSYS_OPT_PHY_STATS */
197
198	return (0);
199
200fail1:
201	EFSYS_PROBE1(fail1, efx_rc_t, rc);
202
203	return (rc);
204}
205
206	__checkReturn	efx_rc_t
207siena_nic_probe(
208	__in		efx_nic_t *enp)
209{
210	efx_port_t *epp = &(enp->en_port);
211	efx_nic_cfg_t *encp = &(enp->en_nic_cfg);
212	siena_link_state_t sls;
213	unsigned int mask;
214	efx_oword_t oword;
215	efx_rc_t rc;
216
217	EFSYS_ASSERT3U(enp->en_family, ==, EFX_FAMILY_SIENA);
218
219	/* Test BIU */
220	if ((rc = efx_nic_biu_test(enp)) != 0)
221		goto fail1;
222
223	/* Clear the region register */
224	EFX_POPULATE_OWORD_4(oword,
225	    FRF_AZ_ADR_REGION0, 0,
226	    FRF_AZ_ADR_REGION1, (1 << 16),
227	    FRF_AZ_ADR_REGION2, (2 << 16),
228	    FRF_AZ_ADR_REGION3, (3 << 16));
229	EFX_BAR_WRITEO(enp, FR_AZ_ADR_REGION_REG, &oword);
230
231	/* Read clear any assertion state */
232	if ((rc = efx_mcdi_read_assertion(enp)) != 0)
233		goto fail2;
234
235	/* Exit the assertion handler */
236	if ((rc = efx_mcdi_exit_assertion_handler(enp)) != 0)
237		goto fail3;
238
239	/* Wrestle control from the BMC */
240	if ((rc = efx_mcdi_drv_attach(enp, B_TRUE)) != 0)
241		goto fail4;
242
243	if ((rc = siena_board_cfg(enp)) != 0)
244		goto fail5;
245
246	if ((rc = siena_phy_cfg(enp)) != 0)
247		goto fail6;
248
249	/* Obtain the default PHY advertised capabilities */
250	if ((rc = siena_nic_reset(enp)) != 0)
251		goto fail7;
252	if ((rc = siena_phy_get_link(enp, &sls)) != 0)
253		goto fail8;
254	epp->ep_default_adv_cap_mask = sls.sls_adv_cap_mask;
255	epp->ep_adv_cap_mask = sls.sls_adv_cap_mask;
256
257#if EFSYS_OPT_VPD || EFSYS_OPT_NVRAM
258	if ((rc = siena_nic_get_partn_mask(enp, &mask)) != 0)
259		goto fail9;
260	enp->en_u.siena.enu_partn_mask = mask;
261#endif
262
263#if EFSYS_OPT_MAC_STATS
264	/* Wipe the MAC statistics */
265	if ((rc = efx_mcdi_mac_stats_clear(enp)) != 0)
266		goto fail10;
267#endif
268
269#if EFSYS_OPT_LOOPBACK
270	if ((rc = efx_mcdi_get_loopback_modes(enp)) != 0)
271		goto fail11;
272#endif
273
274#if EFSYS_OPT_MON_STATS
275	if ((rc = mcdi_mon_cfg_build(enp)) != 0)
276		goto fail12;
277#endif
278
279	encp->enc_features = enp->en_features;
280
281	return (0);
282
283#if EFSYS_OPT_MON_STATS
284fail12:
285	EFSYS_PROBE(fail12);
286#endif
287#if EFSYS_OPT_LOOPBACK
288fail11:
289	EFSYS_PROBE(fail11);
290#endif
291#if EFSYS_OPT_MAC_STATS
292fail10:
293	EFSYS_PROBE(fail10);
294#endif
295#if EFSYS_OPT_VPD || EFSYS_OPT_NVRAM
296fail9:
297	EFSYS_PROBE(fail9);
298#endif
299fail8:
300	EFSYS_PROBE(fail8);
301fail7:
302	EFSYS_PROBE(fail7);
303fail6:
304	EFSYS_PROBE(fail6);
305fail5:
306	EFSYS_PROBE(fail5);
307fail4:
308	EFSYS_PROBE(fail4);
309fail3:
310	EFSYS_PROBE(fail3);
311fail2:
312	EFSYS_PROBE(fail2);
313fail1:
314	EFSYS_PROBE1(fail1, efx_rc_t, rc);
315
316	return (rc);
317}
318
319	__checkReturn	efx_rc_t
320siena_nic_reset(
321	__in		efx_nic_t *enp)
322{
323	efx_mcdi_req_t req;
324	efx_rc_t rc;
325
326	EFSYS_ASSERT3U(enp->en_family, ==, EFX_FAMILY_SIENA);
327
328	/* siena_nic_reset() is called to recover from BADASSERT failures. */
329	if ((rc = efx_mcdi_read_assertion(enp)) != 0)
330		goto fail1;
331	if ((rc = efx_mcdi_exit_assertion_handler(enp)) != 0)
332		goto fail2;
333
334	/*
335	 * Bug24908: ENTITY_RESET_IN_LEN is non zero but zero may be supplied
336	 * for backwards compatibility with PORT_RESET_IN_LEN.
337	 */
338	EFX_STATIC_ASSERT(MC_CMD_ENTITY_RESET_OUT_LEN == 0);
339
340	req.emr_cmd = MC_CMD_ENTITY_RESET;
341	req.emr_in_buf = NULL;
342	req.emr_in_length = 0;
343	req.emr_out_buf = NULL;
344	req.emr_out_length = 0;
345
346	efx_mcdi_execute(enp, &req);
347
348	if (req.emr_rc != 0) {
349		rc = req.emr_rc;
350		goto fail3;
351	}
352
353	return (0);
354
355fail3:
356	EFSYS_PROBE(fail3);
357fail2:
358	EFSYS_PROBE(fail2);
359fail1:
360	EFSYS_PROBE1(fail1, efx_rc_t, rc);
361
362	return (0);
363}
364
365static			void
366siena_nic_rx_cfg(
367	__in		efx_nic_t *enp)
368{
369	efx_oword_t oword;
370
371	/*
372	 * RX_INGR_EN is always enabled on Siena, because we rely on
373	 * the RX parser to be resiliant to missing SOP/EOP.
374	 */
375	EFX_BAR_READO(enp, FR_AZ_RX_CFG_REG, &oword);
376	EFX_SET_OWORD_FIELD(oword, FRF_BZ_RX_INGR_EN, 1);
377	EFX_BAR_WRITEO(enp, FR_AZ_RX_CFG_REG, &oword);
378
379	/* Disable parsing of additional 802.1Q in Q packets */
380	EFX_BAR_READO(enp, FR_AZ_RX_FILTER_CTL_REG, &oword);
381	EFX_SET_OWORD_FIELD(oword, FRF_CZ_RX_FILTER_ALL_VLAN_ETHERTYPES, 0);
382	EFX_BAR_WRITEO(enp, FR_AZ_RX_FILTER_CTL_REG, &oword);
383}
384
385static			void
386siena_nic_usrev_dis(
387	__in		efx_nic_t *enp)
388{
389	efx_oword_t	oword;
390
391	EFX_POPULATE_OWORD_1(oword, FRF_CZ_USREV_DIS, 1);
392	EFX_BAR_WRITEO(enp, FR_CZ_USR_EV_CFG, &oword);
393}
394
395	__checkReturn	efx_rc_t
396siena_nic_init(
397	__in		efx_nic_t *enp)
398{
399	efx_rc_t rc;
400
401	EFSYS_ASSERT3U(enp->en_family, ==, EFX_FAMILY_SIENA);
402
403	/* Enable reporting of some events (e.g. link change) */
404	if ((rc = efx_mcdi_log_ctrl(enp)) != 0)
405		goto fail1;
406
407	siena_sram_init(enp);
408
409	/* Configure Siena's RX block */
410	siena_nic_rx_cfg(enp);
411
412	/* Disable USR_EVents for now */
413	siena_nic_usrev_dis(enp);
414
415	/* bug17057: Ensure set_link is called */
416	if ((rc = siena_phy_reconfigure(enp)) != 0)
417		goto fail2;
418
419	enp->en_nic_cfg.enc_mcdi_max_payload_length = MCDI_CTL_SDU_LEN_MAX_V1;
420
421	return (0);
422
423fail2:
424	EFSYS_PROBE(fail2);
425fail1:
426	EFSYS_PROBE1(fail1, efx_rc_t, rc);
427
428	return (rc);
429}
430
431			void
432siena_nic_fini(
433	__in		efx_nic_t *enp)
434{
435	_NOTE(ARGUNUSED(enp))
436}
437
438			void
439siena_nic_unprobe(
440	__in		efx_nic_t *enp)
441{
442#if EFSYS_OPT_MON_STATS
443	mcdi_mon_cfg_free(enp);
444#endif /* EFSYS_OPT_MON_STATS */
445	(void) efx_mcdi_drv_attach(enp, B_FALSE);
446}
447
448#if EFSYS_OPT_DIAG
449
450static efx_register_set_t __siena_registers[] = {
451	{ FR_AZ_ADR_REGION_REG_OFST, 0, 1 },
452	{ FR_CZ_USR_EV_CFG_OFST, 0, 1 },
453	{ FR_AZ_RX_CFG_REG_OFST, 0, 1 },
454	{ FR_AZ_TX_CFG_REG_OFST, 0, 1 },
455	{ FR_AZ_TX_RESERVED_REG_OFST, 0, 1 },
456	{ FR_AZ_SRM_TX_DC_CFG_REG_OFST, 0, 1 },
457	{ FR_AZ_RX_DC_CFG_REG_OFST, 0, 1 },
458	{ FR_AZ_RX_DC_PF_WM_REG_OFST, 0, 1 },
459	{ FR_AZ_DP_CTRL_REG_OFST, 0, 1 },
460	{ FR_BZ_RX_RSS_TKEY_REG_OFST, 0, 1},
461	{ FR_CZ_RX_RSS_IPV6_REG1_OFST, 0, 1},
462	{ FR_CZ_RX_RSS_IPV6_REG2_OFST, 0, 1},
463	{ FR_CZ_RX_RSS_IPV6_REG3_OFST, 0, 1}
464};
465
466static const uint32_t __siena_register_masks[] = {
467	0x0003FFFF, 0x0003FFFF, 0x0003FFFF, 0x0003FFFF,
468	0x000103FF, 0x00000000, 0x00000000, 0x00000000,
469	0xFFFFFFFE, 0xFFFFFFFF, 0x0003FFFF, 0x00000000,
470	0x7FFF0037, 0xFFFF8000, 0xFFFFFFFF, 0x03FFFFFF,
471	0xFFFEFE80, 0x1FFFFFFF, 0x020000FE, 0x007FFFFF,
472	0x001FFFFF, 0x00000000, 0x00000000, 0x00000000,
473	0x00000003, 0x00000000, 0x00000000, 0x00000000,
474	0x000003FF, 0x00000000, 0x00000000, 0x00000000,
475	0x00000FFF, 0x00000000, 0x00000000, 0x00000000,
476	0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF,
477	0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF,
478	0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF,
479	0xFFFFFFFF, 0xFFFFFFFF, 0x00000007, 0x00000000
480};
481
482static efx_register_set_t __siena_tables[] = {
483	{ FR_AZ_RX_FILTER_TBL0_OFST, FR_AZ_RX_FILTER_TBL0_STEP,
484	    FR_AZ_RX_FILTER_TBL0_ROWS },
485	{ FR_CZ_RX_MAC_FILTER_TBL0_OFST, FR_CZ_RX_MAC_FILTER_TBL0_STEP,
486	    FR_CZ_RX_MAC_FILTER_TBL0_ROWS },
487	{ FR_AZ_RX_DESC_PTR_TBL_OFST,
488	    FR_AZ_RX_DESC_PTR_TBL_STEP, FR_CZ_RX_DESC_PTR_TBL_ROWS },
489	{ FR_AZ_TX_DESC_PTR_TBL_OFST,
490	    FR_AZ_TX_DESC_PTR_TBL_STEP, FR_CZ_TX_DESC_PTR_TBL_ROWS },
491	{ FR_AZ_TIMER_TBL_OFST, FR_AZ_TIMER_TBL_STEP, FR_CZ_TIMER_TBL_ROWS },
492	{ FR_CZ_TX_FILTER_TBL0_OFST,
493	    FR_CZ_TX_FILTER_TBL0_STEP, FR_CZ_TX_FILTER_TBL0_ROWS },
494	{ FR_CZ_TX_MAC_FILTER_TBL0_OFST,
495	    FR_CZ_TX_MAC_FILTER_TBL0_STEP, FR_CZ_TX_MAC_FILTER_TBL0_ROWS }
496};
497
498static const uint32_t __siena_table_masks[] = {
499	0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0x000003FF,
500	0xFFFF0FFF, 0xFFFFFFFF, 0x00000E7F, 0x00000000,
501	0xFFFFFFFE, 0x0FFFFFFF, 0x01800000, 0x00000000,
502	0xFFFFFFFE, 0x0FFFFFFF, 0x0C000000, 0x00000000,
503	0x3FFFFFFF, 0x00000000, 0x00000000, 0x00000000,
504	0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0x000013FF,
505	0xFFFF07FF, 0xFFFFFFFF, 0x0000007F, 0x00000000,
506};
507
508	__checkReturn	efx_rc_t
509siena_nic_register_test(
510	__in		efx_nic_t *enp)
511{
512	efx_register_set_t *rsp;
513	const uint32_t *dwordp;
514	unsigned int nitems;
515	unsigned int count;
516	efx_rc_t rc;
517
518	/* Fill out the register mask entries */
519	EFX_STATIC_ASSERT(EFX_ARRAY_SIZE(__siena_register_masks)
520		    == EFX_ARRAY_SIZE(__siena_registers) * 4);
521
522	nitems = EFX_ARRAY_SIZE(__siena_registers);
523	dwordp = __siena_register_masks;
524	for (count = 0; count < nitems; ++count) {
525		rsp = __siena_registers + count;
526		rsp->mask.eo_u32[0] = *dwordp++;
527		rsp->mask.eo_u32[1] = *dwordp++;
528		rsp->mask.eo_u32[2] = *dwordp++;
529		rsp->mask.eo_u32[3] = *dwordp++;
530	}
531
532	/* Fill out the register table entries */
533	EFX_STATIC_ASSERT(EFX_ARRAY_SIZE(__siena_table_masks)
534		    == EFX_ARRAY_SIZE(__siena_tables) * 4);
535
536	nitems = EFX_ARRAY_SIZE(__siena_tables);
537	dwordp = __siena_table_masks;
538	for (count = 0; count < nitems; ++count) {
539		rsp = __siena_tables + count;
540		rsp->mask.eo_u32[0] = *dwordp++;
541		rsp->mask.eo_u32[1] = *dwordp++;
542		rsp->mask.eo_u32[2] = *dwordp++;
543		rsp->mask.eo_u32[3] = *dwordp++;
544	}
545
546	if ((rc = efx_nic_test_registers(enp, __siena_registers,
547	    EFX_ARRAY_SIZE(__siena_registers))) != 0)
548		goto fail1;
549
550	if ((rc = efx_nic_test_tables(enp, __siena_tables,
551	    EFX_PATTERN_BYTE_ALTERNATE,
552	    EFX_ARRAY_SIZE(__siena_tables))) != 0)
553		goto fail2;
554
555	if ((rc = efx_nic_test_tables(enp, __siena_tables,
556	    EFX_PATTERN_BYTE_CHANGING,
557	    EFX_ARRAY_SIZE(__siena_tables))) != 0)
558		goto fail3;
559
560	if ((rc = efx_nic_test_tables(enp, __siena_tables,
561	    EFX_PATTERN_BIT_SWEEP, EFX_ARRAY_SIZE(__siena_tables))) != 0)
562		goto fail4;
563
564	return (0);
565
566fail4:
567	EFSYS_PROBE(fail4);
568fail3:
569	EFSYS_PROBE(fail3);
570fail2:
571	EFSYS_PROBE(fail2);
572fail1:
573	EFSYS_PROBE1(fail1, efx_rc_t, rc);
574
575	return (rc);
576}
577
578#endif	/* EFSYS_OPT_DIAG */
579
580#endif	/* EFSYS_OPT_SIENA */
581