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