efx_impl.h revision 293980
1/*-
2 * Copyright (c) 2007-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 * $FreeBSD: stable/10/sys/dev/sfxge/common/efx_impl.h 293980 2016-01-14 15:52:44Z arybchik $
31 */
32
33#ifndef	_SYS_EFX_IMPL_H
34#define	_SYS_EFX_IMPL_H
35
36#include "efsys.h"
37#include "efx.h"
38#include "efx_regs.h"
39#include "efx_regs_ef10.h"
40
41/* FIXME: Add definition for driver generated software events */
42#ifndef	ESE_DZ_EV_CODE_DRV_GEN_EV
43#define	ESE_DZ_EV_CODE_DRV_GEN_EV FSE_AZ_EV_CODE_DRV_GEN_EV
44#endif
45
46#include "efx_check.h"
47
48
49#if EFSYS_OPT_FALCON
50#include "falcon_impl.h"
51#endif	/* EFSYS_OPT_FALCON */
52
53#if EFSYS_OPT_SIENA
54#include "siena_impl.h"
55#endif	/* EFSYS_OPT_SIENA */
56
57#if EFSYS_OPT_HUNTINGTON
58#include "hunt_impl.h"
59#endif	/* EFSYS_OPT_HUNTINGTON */
60
61#if EFSYS_OPT_MEDFORD
62#include "medford_impl.h"
63#endif	/* EFSYS_OPT_MEDFORD */
64
65#if (EFSYS_OPT_HUNTINGTON || EFSYS_OPT_MEDFORD)
66#include "ef10_impl.h"
67#endif	/* (EFSYS_OPT_HUNTINGTON || EFSYS_OPT_MEDFORD) */
68
69#ifdef	__cplusplus
70extern "C" {
71#endif
72
73#define	EFX_MOD_MCDI		0x00000001
74#define	EFX_MOD_PROBE		0x00000002
75#define	EFX_MOD_NVRAM		0x00000004
76#define	EFX_MOD_VPD		0x00000008
77#define	EFX_MOD_NIC		0x00000010
78#define	EFX_MOD_INTR		0x00000020
79#define	EFX_MOD_EV		0x00000040
80#define	EFX_MOD_RX		0x00000080
81#define	EFX_MOD_TX		0x00000100
82#define	EFX_MOD_PORT		0x00000200
83#define	EFX_MOD_MON		0x00000400
84#define	EFX_MOD_WOL		0x00000800
85#define	EFX_MOD_FILTER		0x00001000
86#define	EFX_MOD_PKTFILTER	0x00002000
87
88#define	EFX_RESET_MAC		0x00000001
89#define	EFX_RESET_PHY		0x00000002
90#define	EFX_RESET_RXQ_ERR	0x00000004
91#define	EFX_RESET_TXQ_ERR	0x00000008
92
93typedef enum efx_mac_type_e {
94	EFX_MAC_INVALID = 0,
95	EFX_MAC_FALCON_GMAC,
96	EFX_MAC_FALCON_XMAC,
97	EFX_MAC_SIENA,
98	EFX_MAC_HUNTINGTON,
99	EFX_MAC_NTYPES
100} efx_mac_type_t;
101
102typedef struct efx_ev_ops_s {
103	efx_rc_t	(*eevo_init)(efx_nic_t *);
104	void		(*eevo_fini)(efx_nic_t *);
105	efx_rc_t	(*eevo_qcreate)(efx_nic_t *, unsigned int,
106					  efsys_mem_t *, size_t, uint32_t,
107					  efx_evq_t *);
108	void		(*eevo_qdestroy)(efx_evq_t *);
109	efx_rc_t	(*eevo_qprime)(efx_evq_t *, unsigned int);
110	void		(*eevo_qpost)(efx_evq_t *, uint16_t);
111	efx_rc_t	(*eevo_qmoderate)(efx_evq_t *, unsigned int);
112#if EFSYS_OPT_QSTATS
113	void		(*eevo_qstats_update)(efx_evq_t *, efsys_stat_t *);
114#endif
115} efx_ev_ops_t;
116
117typedef struct efx_tx_ops_s {
118	efx_rc_t	(*etxo_init)(efx_nic_t *);
119	void		(*etxo_fini)(efx_nic_t *);
120	efx_rc_t	(*etxo_qcreate)(efx_nic_t *,
121					unsigned int, unsigned int,
122					efsys_mem_t *, size_t,
123					uint32_t, uint16_t,
124					efx_evq_t *, efx_txq_t *,
125					unsigned int *);
126	void		(*etxo_qdestroy)(efx_txq_t *);
127	efx_rc_t	(*etxo_qpost)(efx_txq_t *, efx_buffer_t *,
128				      unsigned int, unsigned int,
129				      unsigned int *);
130	void		(*etxo_qpush)(efx_txq_t *, unsigned int, unsigned int);
131	efx_rc_t	(*etxo_qpace)(efx_txq_t *, unsigned int);
132	efx_rc_t	(*etxo_qflush)(efx_txq_t *);
133	void		(*etxo_qenable)(efx_txq_t *);
134	efx_rc_t	(*etxo_qpio_enable)(efx_txq_t *);
135	void		(*etxo_qpio_disable)(efx_txq_t *);
136	efx_rc_t	(*etxo_qpio_write)(efx_txq_t *,uint8_t *, size_t,
137					   size_t);
138	efx_rc_t	(*etxo_qpio_post)(efx_txq_t *, size_t, unsigned int,
139					   unsigned int *);
140	efx_rc_t	(*etxo_qdesc_post)(efx_txq_t *, efx_desc_t *,
141				      unsigned int, unsigned int,
142				      unsigned int *);
143	void		(*etxo_qdesc_dma_create)(efx_txq_t *, efsys_dma_addr_t,
144						size_t, boolean_t,
145						efx_desc_t *);
146	void		(*etxo_qdesc_tso_create)(efx_txq_t *, uint16_t,
147						uint32_t, uint8_t,
148						efx_desc_t *);
149	void		(*etxo_qdesc_vlantci_create)(efx_txq_t *, uint16_t,
150						efx_desc_t *);
151#if EFSYS_OPT_QSTATS
152	void		(*etxo_qstats_update)(efx_txq_t *,
153					      efsys_stat_t *);
154#endif
155} efx_tx_ops_t;
156
157typedef struct efx_rx_ops_s {
158	efx_rc_t	(*erxo_init)(efx_nic_t *);
159	void		(*erxo_fini)(efx_nic_t *);
160#if EFSYS_OPT_RX_HDR_SPLIT
161	efx_rc_t	(*erxo_hdr_split_enable)(efx_nic_t *, unsigned int,
162						 unsigned int);
163#endif
164#if EFSYS_OPT_RX_SCATTER
165	efx_rc_t	(*erxo_scatter_enable)(efx_nic_t *, unsigned int);
166#endif
167#if EFSYS_OPT_RX_SCALE
168	efx_rc_t	(*erxo_scale_mode_set)(efx_nic_t *, efx_rx_hash_alg_t,
169					       efx_rx_hash_type_t, boolean_t);
170	efx_rc_t	(*erxo_scale_key_set)(efx_nic_t *, uint8_t *, size_t);
171	efx_rc_t	(*erxo_scale_tbl_set)(efx_nic_t *, unsigned int *,
172					      size_t);
173#endif
174	void		(*erxo_qpost)(efx_rxq_t *, efsys_dma_addr_t *, size_t,
175				      unsigned int, unsigned int,
176				      unsigned int);
177	void		(*erxo_qpush)(efx_rxq_t *, unsigned int, unsigned int *);
178	efx_rc_t	(*erxo_qflush)(efx_rxq_t *);
179	void		(*erxo_qenable)(efx_rxq_t *);
180	efx_rc_t	(*erxo_qcreate)(efx_nic_t *enp, unsigned int,
181					unsigned int, efx_rxq_type_t,
182					efsys_mem_t *, size_t, uint32_t,
183					efx_evq_t *, efx_rxq_t *);
184	void		(*erxo_qdestroy)(efx_rxq_t *);
185} efx_rx_ops_t;
186
187typedef struct efx_mac_ops_s {
188	efx_rc_t	(*emo_reset)(efx_nic_t *); /* optional */
189	efx_rc_t	(*emo_poll)(efx_nic_t *, efx_link_mode_t *);
190	efx_rc_t	(*emo_up)(efx_nic_t *, boolean_t *);
191	efx_rc_t	(*emo_addr_set)(efx_nic_t *);
192	efx_rc_t	(*emo_reconfigure)(efx_nic_t *);
193	efx_rc_t	(*emo_multicast_list_set)(efx_nic_t *);
194	efx_rc_t	(*emo_filter_default_rxq_set)(efx_nic_t *,
195						      efx_rxq_t *, boolean_t);
196	void		(*emo_filter_default_rxq_clear)(efx_nic_t *);
197#if EFSYS_OPT_LOOPBACK
198	efx_rc_t	(*emo_loopback_set)(efx_nic_t *, efx_link_mode_t,
199					    efx_loopback_type_t);
200#endif	/* EFSYS_OPT_LOOPBACK */
201#if EFSYS_OPT_MAC_STATS
202	efx_rc_t	(*emo_stats_upload)(efx_nic_t *, efsys_mem_t *);
203	efx_rc_t	(*emo_stats_periodic)(efx_nic_t *, efsys_mem_t *,
204					      uint16_t, boolean_t);
205	efx_rc_t	(*emo_stats_update)(efx_nic_t *, efsys_mem_t *,
206					    efsys_stat_t *, uint32_t *);
207#endif	/* EFSYS_OPT_MAC_STATS */
208} efx_mac_ops_t;
209
210typedef struct efx_phy_ops_s {
211	efx_rc_t	(*epo_power)(efx_nic_t *, boolean_t); /* optional */
212	efx_rc_t	(*epo_reset)(efx_nic_t *);
213	efx_rc_t	(*epo_reconfigure)(efx_nic_t *);
214	efx_rc_t	(*epo_verify)(efx_nic_t *);
215	efx_rc_t	(*epo_uplink_check)(efx_nic_t *,
216					    boolean_t *); /* optional */
217	efx_rc_t	(*epo_downlink_check)(efx_nic_t *, efx_link_mode_t *,
218					      unsigned int *, uint32_t *);
219	efx_rc_t	(*epo_oui_get)(efx_nic_t *, uint32_t *);
220#if EFSYS_OPT_PHY_STATS
221	efx_rc_t	(*epo_stats_update)(efx_nic_t *, efsys_mem_t *,
222					    uint32_t *);
223#endif	/* EFSYS_OPT_PHY_STATS */
224#if EFSYS_OPT_PHY_PROPS
225#if EFSYS_OPT_NAMES
226	const char	*(*epo_prop_name)(efx_nic_t *, unsigned int);
227#endif	/* EFSYS_OPT_PHY_PROPS */
228	efx_rc_t	(*epo_prop_get)(efx_nic_t *, unsigned int, uint32_t,
229					uint32_t *);
230	efx_rc_t	(*epo_prop_set)(efx_nic_t *, unsigned int, uint32_t);
231#endif	/* EFSYS_OPT_PHY_PROPS */
232#if EFSYS_OPT_BIST
233	efx_rc_t	(*epo_bist_enable_offline)(efx_nic_t *);
234	efx_rc_t	(*epo_bist_start)(efx_nic_t *, efx_bist_type_t);
235	efx_rc_t	(*epo_bist_poll)(efx_nic_t *, efx_bist_type_t,
236					 efx_bist_result_t *, uint32_t *,
237					 unsigned long *, size_t);
238	void		(*epo_bist_stop)(efx_nic_t *, efx_bist_type_t);
239#endif	/* EFSYS_OPT_BIST */
240} efx_phy_ops_t;
241
242#if EFSYS_OPT_FILTER
243typedef struct efx_filter_ops_s {
244	efx_rc_t	(*efo_init)(efx_nic_t *);
245	void		(*efo_fini)(efx_nic_t *);
246	efx_rc_t	(*efo_restore)(efx_nic_t *);
247	efx_rc_t	(*efo_add)(efx_nic_t *, efx_filter_spec_t *,
248				   boolean_t may_replace);
249	efx_rc_t	(*efo_delete)(efx_nic_t *, efx_filter_spec_t *);
250	efx_rc_t	(*efo_supported_filters)(efx_nic_t *, uint32_t *, size_t *);
251	efx_rc_t	(*efo_reconfigure)(efx_nic_t *, uint8_t const *, boolean_t,
252				   boolean_t, boolean_t, boolean_t,
253				   uint8_t const *, int);
254} efx_filter_ops_t;
255
256extern	__checkReturn	efx_rc_t
257efx_filter_reconfigure(
258	__in				efx_nic_t *enp,
259	__in_ecount(6)			uint8_t const *mac_addr,
260	__in				boolean_t all_unicst,
261	__in				boolean_t mulcst,
262	__in				boolean_t all_mulcst,
263	__in				boolean_t brdcst,
264	__in_ecount(6*count)		uint8_t const *addrs,
265	__in				int count);
266
267#endif /* EFSYS_OPT_FILTER */
268
269typedef struct efx_pktfilter_ops_s {
270	efx_rc_t	(*epfo_set)(efx_nic_t *,
271				boolean_t unicst,
272				boolean_t brdcast);
273#if EFSYS_OPT_MCAST_FILTER_LIST
274	efx_rc_t	(*epfo_mcast_list_set)(efx_nic_t *,
275				uint8_t const *addrs, int count);
276#endif /* EFSYS_OPT_MCAST_FILTER_LIST */
277	efx_rc_t	(*epfo_mcast_all)(efx_nic_t *);
278} efx_pktfilter_ops_t;
279
280typedef struct efx_port_s {
281	efx_mac_type_t		ep_mac_type;
282	uint32_t  		ep_phy_type;
283	uint8_t			ep_port;
284	uint32_t		ep_mac_pdu;
285	uint8_t			ep_mac_addr[6];
286	efx_link_mode_t		ep_link_mode;
287	boolean_t		ep_all_unicst;
288	boolean_t		ep_mulcst;
289	boolean_t		ep_all_mulcst;
290	boolean_t		ep_brdcst;
291	unsigned int		ep_fcntl;
292	boolean_t		ep_fcntl_autoneg;
293	efx_oword_t		ep_multicst_hash[2];
294	uint8_t			ep_mulcst_addr_list[EFX_MAC_ADDR_LEN *
295						    EFX_MAC_MULTICAST_LIST_MAX];
296	uint32_t		ep_mulcst_addr_count;
297#if EFSYS_OPT_LOOPBACK
298	efx_loopback_type_t	ep_loopback_type;
299	efx_link_mode_t		ep_loopback_link_mode;
300#endif	/* EFSYS_OPT_LOOPBACK */
301#if EFSYS_OPT_PHY_FLAGS
302	uint32_t		ep_phy_flags;
303#endif	/* EFSYS_OPT_PHY_FLAGS */
304#if EFSYS_OPT_PHY_LED_CONTROL
305	efx_phy_led_mode_t	ep_phy_led_mode;
306#endif	/* EFSYS_OPT_PHY_LED_CONTROL */
307	efx_phy_media_type_t	ep_fixed_port_type;
308	efx_phy_media_type_t	ep_module_type;
309	uint32_t		ep_adv_cap_mask;
310	uint32_t		ep_lp_cap_mask;
311	uint32_t		ep_default_adv_cap_mask;
312	uint32_t		ep_phy_cap_mask;
313#if EFSYS_OPT_PHY_TXC43128 || EFSYS_OPT_PHY_QT2025C
314	union {
315		struct {
316			unsigned int	bug10934_count;
317		} ep_txc43128;
318		struct {
319			unsigned int	bug17190_count;
320		} ep_qt2025c;
321	};
322#endif
323	boolean_t		ep_mac_poll_needed; /* falcon only */
324	boolean_t		ep_mac_up; /* falcon only */
325	uint32_t		ep_fwver; /* falcon only */
326	boolean_t		ep_mac_drain;
327	boolean_t		ep_mac_stats_pending;
328#if EFSYS_OPT_BIST
329	efx_bist_type_t		ep_current_bist;
330#endif
331	efx_mac_ops_t		*ep_emop;
332	efx_phy_ops_t		*ep_epop;
333} efx_port_t;
334
335typedef struct efx_mon_ops_s {
336	efx_rc_t	(*emo_reset)(efx_nic_t *);
337	efx_rc_t	(*emo_reconfigure)(efx_nic_t *);
338#if EFSYS_OPT_MON_STATS
339	efx_rc_t	(*emo_stats_update)(efx_nic_t *, efsys_mem_t *,
340					    efx_mon_stat_value_t *);
341#endif	/* EFSYS_OPT_MON_STATS */
342} efx_mon_ops_t;
343
344typedef struct efx_mon_s {
345	efx_mon_type_t	em_type;
346	efx_mon_ops_t	*em_emop;
347} efx_mon_t;
348
349typedef struct efx_intr_ops_s {
350	efx_rc_t	(*eio_init)(efx_nic_t *, efx_intr_type_t, efsys_mem_t *);
351	void		(*eio_enable)(efx_nic_t *);
352	void		(*eio_disable)(efx_nic_t *);
353	void		(*eio_disable_unlocked)(efx_nic_t *);
354	efx_rc_t	(*eio_trigger)(efx_nic_t *, unsigned int);
355	void		(*eio_fini)(efx_nic_t *);
356} efx_intr_ops_t;
357
358typedef struct efx_intr_s {
359	efx_intr_ops_t	*ei_eiop;
360	efsys_mem_t	*ei_esmp;
361	efx_intr_type_t	ei_type;
362	unsigned int	ei_level;
363} efx_intr_t;
364
365typedef struct efx_nic_ops_s {
366	efx_rc_t	(*eno_probe)(efx_nic_t *);
367	efx_rc_t	(*eno_set_drv_limits)(efx_nic_t *, efx_drv_limits_t*);
368	efx_rc_t	(*eno_reset)(efx_nic_t *);
369	efx_rc_t	(*eno_init)(efx_nic_t *);
370	efx_rc_t	(*eno_get_vi_pool)(efx_nic_t *, uint32_t *);
371	efx_rc_t	(*eno_get_bar_region)(efx_nic_t *, efx_nic_region_t,
372					uint32_t *, size_t *);
373#if EFSYS_OPT_DIAG
374	efx_rc_t	(*eno_sram_test)(efx_nic_t *, efx_sram_pattern_fn_t);
375	efx_rc_t	(*eno_register_test)(efx_nic_t *);
376#endif	/* EFSYS_OPT_DIAG */
377	void		(*eno_fini)(efx_nic_t *);
378	void		(*eno_unprobe)(efx_nic_t *);
379} efx_nic_ops_t;
380
381#ifndef EFX_TXQ_LIMIT_TARGET
382#define	EFX_TXQ_LIMIT_TARGET 259
383#endif
384#ifndef EFX_RXQ_LIMIT_TARGET
385#define	EFX_RXQ_LIMIT_TARGET 512
386#endif
387#ifndef EFX_TXQ_DC_SIZE
388#define	EFX_TXQ_DC_SIZE 1 /* 16 descriptors */
389#endif
390#ifndef EFX_RXQ_DC_SIZE
391#define	EFX_RXQ_DC_SIZE 3 /* 64 descriptors */
392#endif
393
394#if EFSYS_OPT_FILTER
395
396typedef struct falconsiena_filter_spec_s {
397	uint8_t		fsfs_type;
398	uint32_t	fsfs_flags;
399	uint32_t	fsfs_dmaq_id;
400	uint32_t	fsfs_dword[3];
401} falconsiena_filter_spec_t;
402
403typedef enum falconsiena_filter_type_e {
404	EFX_FS_FILTER_RX_TCP_FULL,	/* TCP/IPv4 4-tuple {dIP,dTCP,sIP,sTCP} */
405	EFX_FS_FILTER_RX_TCP_WILD,	/* TCP/IPv4 dest    {dIP,dTCP,  -,   -} */
406	EFX_FS_FILTER_RX_UDP_FULL,	/* UDP/IPv4 4-tuple {dIP,dUDP,sIP,sUDP} */
407	EFX_FS_FILTER_RX_UDP_WILD,	/* UDP/IPv4 dest    {dIP,dUDP,  -,   -} */
408
409#if EFSYS_OPT_SIENA
410	EFX_FS_FILTER_RX_MAC_FULL,	/* Ethernet {dMAC,VLAN} */
411	EFX_FS_FILTER_RX_MAC_WILD,	/* Ethernet {dMAC,   -} */
412
413	EFX_FS_FILTER_TX_TCP_FULL,		/* TCP/IPv4 {dIP,dTCP,sIP,sTCP} */
414	EFX_FS_FILTER_TX_TCP_WILD,		/* TCP/IPv4 {  -,   -,sIP,sTCP} */
415	EFX_FS_FILTER_TX_UDP_FULL,		/* UDP/IPv4 {dIP,dTCP,sIP,sTCP} */
416	EFX_FS_FILTER_TX_UDP_WILD,		/* UDP/IPv4 source (host, port) */
417
418	EFX_FS_FILTER_TX_MAC_FULL,		/* Ethernet source (MAC address, VLAN ID) */
419	EFX_FS_FILTER_TX_MAC_WILD,		/* Ethernet source (MAC address) */
420#endif /* EFSYS_OPT_SIENA */
421
422	EFX_FS_FILTER_NTYPES
423} falconsiena_filter_type_t;
424
425typedef enum falconsiena_filter_tbl_id_e {
426	EFX_FS_FILTER_TBL_RX_IP = 0,
427	EFX_FS_FILTER_TBL_RX_MAC,
428	EFX_FS_FILTER_TBL_TX_IP,
429	EFX_FS_FILTER_TBL_TX_MAC,
430	EFX_FS_FILTER_NTBLS
431} falconsiena_filter_tbl_id_t;
432
433typedef struct falconsiena_filter_tbl_s {
434	int				fsft_size;	/* number of entries */
435	int				fsft_used;	/* active count */
436	uint32_t			*fsft_bitmap;	/* active bitmap */
437	falconsiena_filter_spec_t	*fsft_spec;	/* array of saved specs */
438} falconsiena_filter_tbl_t;
439
440typedef struct falconsiena_filter_s {
441	falconsiena_filter_tbl_t	fsf_tbl[EFX_FS_FILTER_NTBLS];
442	unsigned int			fsf_depth[EFX_FS_FILTER_NTYPES];
443} falconsiena_filter_t;
444
445typedef struct efx_filter_s {
446#if EFSYS_OPT_FALCON || EFSYS_OPT_SIENA
447	falconsiena_filter_t	*ef_falconsiena_filter;
448#endif /* EFSYS_OPT_FALCON || EFSYS_OPT_SIENA */
449#if EFSYS_OPT_HUNTINGTON
450	hunt_filter_table_t	*ef_hunt_filter_table;
451#endif /* EFSYS_OPT_HUNTINGTON */
452} efx_filter_t;
453
454extern			void
455falconsiena_filter_tbl_clear(
456	__in		efx_nic_t *enp,
457	__in		falconsiena_filter_tbl_id_t tbl);
458
459#endif	/* EFSYS_OPT_FILTER */
460
461#if EFSYS_OPT_MCDI
462
463typedef struct efx_mcdi_ops_s {
464	efx_rc_t	(*emco_init)(efx_nic_t *, const efx_mcdi_transport_t *);
465	void		(*emco_request_copyin)(efx_nic_t *, efx_mcdi_req_t *,
466					unsigned int, boolean_t, boolean_t);
467	void		(*emco_request_copyout)(efx_nic_t *, efx_mcdi_req_t *);
468	efx_rc_t	(*emco_poll_reboot)(efx_nic_t *);
469	boolean_t	(*emco_poll_response)(efx_nic_t *);
470	void		(*emco_read_response)(efx_nic_t *, void *, size_t, size_t);
471	void		(*emco_fini)(efx_nic_t *);
472	efx_rc_t	(*emco_feature_supported)(efx_nic_t *, efx_mcdi_feature_id_t, boolean_t *);
473} efx_mcdi_ops_t;
474
475typedef struct efx_mcdi_s {
476	efx_mcdi_ops_t			*em_emcop;
477	const efx_mcdi_transport_t	*em_emtp;
478	efx_mcdi_iface_t		em_emip;
479} efx_mcdi_t;
480
481#endif /* EFSYS_OPT_MCDI */
482
483#if EFSYS_OPT_NVRAM
484typedef struct efx_nvram_ops_s {
485#if EFSYS_OPT_DIAG
486	efx_rc_t	(*envo_test)(efx_nic_t *);
487#endif	/* EFSYS_OPT_DIAG */
488	efx_rc_t	(*envo_size)(efx_nic_t *, efx_nvram_type_t, size_t *);
489	efx_rc_t	(*envo_get_version)(efx_nic_t *, efx_nvram_type_t,
490					    uint32_t *, uint16_t *);
491	efx_rc_t	(*envo_rw_start)(efx_nic_t *, efx_nvram_type_t, size_t *);
492	efx_rc_t	(*envo_read_chunk)(efx_nic_t *, efx_nvram_type_t,
493					    unsigned int, caddr_t, size_t);
494	efx_rc_t	(*envo_erase)(efx_nic_t *, efx_nvram_type_t);
495	efx_rc_t	(*envo_write_chunk)(efx_nic_t *, efx_nvram_type_t,
496					    unsigned int, caddr_t, size_t);
497	void		(*envo_rw_finish)(efx_nic_t *, efx_nvram_type_t);
498	efx_rc_t	(*envo_set_version)(efx_nic_t *, efx_nvram_type_t,
499					    uint16_t *);
500
501} efx_nvram_ops_t;
502#endif /* EFSYS_OPT_NVRAM */
503
504#if EFSYS_OPT_VPD
505typedef struct efx_vpd_ops_s {
506	efx_rc_t	(*evpdo_init)(efx_nic_t *);
507	efx_rc_t	(*evpdo_size)(efx_nic_t *, size_t *);
508	efx_rc_t	(*evpdo_read)(efx_nic_t *, caddr_t, size_t);
509	efx_rc_t	(*evpdo_verify)(efx_nic_t *, caddr_t, size_t);
510	efx_rc_t	(*evpdo_reinit)(efx_nic_t *, caddr_t, size_t);
511	efx_rc_t	(*evpdo_get)(efx_nic_t *, caddr_t, size_t,
512					efx_vpd_value_t *);
513	efx_rc_t	(*evpdo_set)(efx_nic_t *, caddr_t, size_t,
514					efx_vpd_value_t *);
515	efx_rc_t	(*evpdo_next)(efx_nic_t *, caddr_t, size_t,
516					efx_vpd_value_t *, unsigned int *);
517	efx_rc_t	(*evpdo_write)(efx_nic_t *, caddr_t, size_t);
518	void		(*evpdo_fini)(efx_nic_t *);
519} efx_vpd_ops_t;
520#endif	/* EFSYS_OPT_VPD */
521
522#if EFSYS_OPT_VPD || EFSYS_OPT_NVRAM
523
524	__checkReturn		efx_rc_t
525efx_mcdi_nvram_partitions(
526	__in			efx_nic_t *enp,
527	__out_bcount(size)	caddr_t data,
528	__in			size_t size,
529	__out			unsigned int *npartnp);
530
531	__checkReturn		efx_rc_t
532efx_mcdi_nvram_metadata(
533	__in			efx_nic_t *enp,
534	__in			uint32_t partn,
535	__out			uint32_t *subtypep,
536	__out_ecount(4)		uint16_t version[4],
537	__out_bcount_opt(size)	char *descp,
538	__in			size_t size);
539
540	__checkReturn		efx_rc_t
541efx_mcdi_nvram_info(
542	__in			efx_nic_t *enp,
543	__in			uint32_t partn,
544	__out_opt		size_t *sizep,
545	__out_opt		uint32_t *addressp,
546	__out_opt		uint32_t *erase_sizep,
547	__out_opt		uint32_t *write_sizep);
548
549	__checkReturn		efx_rc_t
550efx_mcdi_nvram_update_start(
551	__in			efx_nic_t *enp,
552	__in			uint32_t partn);
553
554	__checkReturn		efx_rc_t
555efx_mcdi_nvram_read(
556	__in			efx_nic_t *enp,
557	__in			uint32_t partn,
558	__in			uint32_t offset,
559	__out_bcount(size)	caddr_t data,
560	__in			size_t size);
561
562	__checkReturn		efx_rc_t
563efx_mcdi_nvram_erase(
564	__in			efx_nic_t *enp,
565	__in			uint32_t partn,
566	__in			uint32_t offset,
567	__in			size_t size);
568
569	__checkReturn		efx_rc_t
570efx_mcdi_nvram_write(
571	__in			efx_nic_t *enp,
572	__in			uint32_t partn,
573	__in			uint32_t offset,
574	__out_bcount(size)	caddr_t data,
575	__in			size_t size);
576
577	__checkReturn		efx_rc_t
578efx_mcdi_nvram_update_finish(
579	__in			efx_nic_t *enp,
580	__in			uint32_t partn,
581	__in			boolean_t reboot);
582
583#if EFSYS_OPT_DIAG
584
585	__checkReturn		efx_rc_t
586efx_mcdi_nvram_test(
587	__in			efx_nic_t *enp,
588	__in			uint32_t partn);
589
590#endif	/* EFSYS_OPT_DIAG */
591
592#endif /* EFSYS_OPT_VPD || EFSYS_OPT_NVRAM */
593
594typedef struct efx_drv_cfg_s {
595	uint32_t		edc_min_vi_count;
596	uint32_t		edc_max_vi_count;
597
598	uint32_t		edc_max_piobuf_count;
599	uint32_t		edc_pio_alloc_size;
600} efx_drv_cfg_t;
601
602struct efx_nic_s {
603	uint32_t		en_magic;
604	efx_family_t		en_family;
605	uint32_t		en_features;
606	efsys_identifier_t	*en_esip;
607	efsys_lock_t		*en_eslp;
608	efsys_bar_t 		*en_esbp;
609	unsigned int		en_mod_flags;
610	unsigned int		en_reset_flags;
611	efx_nic_cfg_t		en_nic_cfg;
612	efx_drv_cfg_t		en_drv_cfg;
613	efx_port_t		en_port;
614	efx_mon_t		en_mon;
615	efx_intr_t		en_intr;
616	uint32_t		en_ev_qcount;
617	uint32_t		en_rx_qcount;
618	uint32_t		en_tx_qcount;
619	efx_nic_ops_t		*en_enop;
620	efx_ev_ops_t		*en_eevop;
621	efx_tx_ops_t		*en_etxop;
622	efx_rx_ops_t		*en_erxop;
623#if EFSYS_OPT_FILTER
624	efx_filter_t		en_filter;
625	efx_filter_ops_t	*en_efop;
626#endif	/* EFSYS_OPT_FILTER */
627	efx_pktfilter_ops_t	*en_epfop;
628#if EFSYS_OPT_MCDI
629	efx_mcdi_t		en_mcdi;
630#endif	/* EFSYS_OPT_MCDI */
631#if EFSYS_OPT_NVRAM
632	efx_nvram_type_t	en_nvram_locked;
633	efx_nvram_ops_t		*en_envop;
634#endif	/* EFSYS_OPT_NVRAM */
635#if EFSYS_OPT_VPD
636	efx_vpd_ops_t		*en_evpdop;
637#endif	/* EFSYS_OPT_VPD */
638#if EFSYS_OPT_RX_SCALE
639	efx_rx_hash_support_t	en_hash_support;
640	efx_rx_scale_support_t	en_rss_support;
641	uint32_t		en_rss_context;
642#endif	/* EFSYS_OPT_RX_SCALE */
643	uint32_t		en_vport_id;
644	union {
645#if EFSYS_OPT_FALCON
646		struct {
647			falcon_spi_dev_t	enu_fsd[FALCON_SPI_NTYPES];
648			falcon_i2c_t		enu_fip;
649			boolean_t		enu_i2c_locked;
650#if EFSYS_OPT_FALCON_NIC_CFG_OVERRIDE
651			const uint8_t		*enu_forced_cfg;
652#endif	/* EFSYS_OPT_FALCON_NIC_CFG_OVERRIDE */
653			uint8_t			enu_mon_devid;
654#if EFSYS_OPT_PCIE_TUNE
655			unsigned int 		enu_nlanes;
656#endif	/* EFSYS_OPT_PCIE_TUNE */
657			uint16_t		enu_board_rev;
658			boolean_t		enu_internal_sram;
659			uint8_t			enu_sram_num_bank;
660			uint8_t			enu_sram_bank_size;
661		} falcon;
662#endif	/* EFSYS_OPT_FALCON */
663#if EFSYS_OPT_SIENA
664		struct {
665#if EFSYS_OPT_NVRAM || EFSYS_OPT_VPD
666			unsigned int		enu_partn_mask;
667#endif	/* EFSYS_OPT_NVRAM || EFSYS_OPT_VPD */
668#if EFSYS_OPT_VPD
669			caddr_t			enu_svpd;
670			size_t			enu_svpd_length;
671#endif	/* EFSYS_OPT_VPD */
672			int			enu_unused;
673		} siena;
674#endif	/* EFSYS_OPT_SIENA */
675#if EFSYS_OPT_HUNTINGTON
676		struct {
677			int			enu_vi_base;
678			int			enu_vi_count;
679#if EFSYS_OPT_VPD
680			caddr_t			enu_svpd;
681			size_t			enu_svpd_length;
682#endif	/* EFSYS_OPT_VPD */
683			efx_piobuf_handle_t	enu_piobuf_handle[HUNT_PIOBUF_NBUFS];
684			uint32_t		enu_piobuf_count;
685			uint32_t		enu_pio_alloc_map[HUNT_PIOBUF_NBUFS];
686			uint32_t		enu_pio_write_vi_base;
687			/* Memory BAR mapping regions */
688			uint32_t		enu_uc_mem_map_offset;
689			size_t			enu_uc_mem_map_size;
690			uint32_t		enu_wc_mem_map_offset;
691			size_t			enu_wc_mem_map_size;
692		} hunt;
693#endif	/* EFSYS_OPT_HUNTINGTON */
694	} en_u;
695};
696
697
698#define	EFX_NIC_MAGIC	0x02121996
699
700typedef	boolean_t (*efx_ev_handler_t)(efx_evq_t *, efx_qword_t *,
701    const efx_ev_callbacks_t *, void *);
702
703typedef struct efx_evq_rxq_state_s {
704	unsigned int			eers_rx_read_ptr;
705	unsigned int			eers_rx_mask;
706} efx_evq_rxq_state_t;
707
708struct efx_evq_s {
709	uint32_t			ee_magic;
710	efx_nic_t			*ee_enp;
711	unsigned int			ee_index;
712	unsigned int			ee_mask;
713	efsys_mem_t			*ee_esmp;
714#if EFSYS_OPT_QSTATS
715	uint32_t			ee_stat[EV_NQSTATS];
716#endif	/* EFSYS_OPT_QSTATS */
717
718	efx_ev_handler_t		ee_rx;
719	efx_ev_handler_t		ee_tx;
720	efx_ev_handler_t		ee_driver;
721	efx_ev_handler_t		ee_global;
722	efx_ev_handler_t		ee_drv_gen;
723#if EFSYS_OPT_MCDI
724	efx_ev_handler_t		ee_mcdi;
725#endif	/* EFSYS_OPT_MCDI */
726
727	efx_evq_rxq_state_t		ee_rxq_state[EFX_EV_RX_NLABELS];
728};
729
730#define	EFX_EVQ_MAGIC	0x08081997
731
732#define	EFX_EVQ_FALCON_TIMER_QUANTUM_NS	4968 /* 621 cycles */
733#define	EFX_EVQ_SIENA_TIMER_QUANTUM_NS	6144 /* 768 cycles */
734
735struct efx_rxq_s {
736	uint32_t			er_magic;
737	efx_nic_t			*er_enp;
738	efx_evq_t			*er_eep;
739	unsigned int			er_index;
740	unsigned int			er_label;
741	unsigned int			er_mask;
742	efsys_mem_t			*er_esmp;
743};
744
745#define	EFX_RXQ_MAGIC	0x15022005
746
747struct efx_txq_s {
748	uint32_t			et_magic;
749	efx_nic_t			*et_enp;
750	unsigned int			et_index;
751	unsigned int			et_mask;
752	efsys_mem_t			*et_esmp;
753#if EFSYS_OPT_HUNTINGTON
754	uint32_t			et_pio_bufnum;
755	uint32_t			et_pio_blknum;
756	uint32_t			et_pio_write_offset;
757	uint32_t			et_pio_offset;
758	size_t				et_pio_size;
759#endif
760#if EFSYS_OPT_QSTATS
761	uint32_t			et_stat[TX_NQSTATS];
762#endif	/* EFSYS_OPT_QSTATS */
763};
764
765#define	EFX_TXQ_MAGIC	0x05092005
766
767#define	EFX_MAC_ADDR_COPY(_dst, _src)					\
768	do {								\
769		(_dst)[0] = (_src)[0];					\
770		(_dst)[1] = (_src)[1];					\
771		(_dst)[2] = (_src)[2];					\
772		(_dst)[3] = (_src)[3];					\
773		(_dst)[4] = (_src)[4];					\
774		(_dst)[5] = (_src)[5];					\
775	_NOTE(CONSTANTCONDITION)					\
776	} while (B_FALSE)
777
778#define	EFX_MAC_BROADCAST_ADDR_SET(_dst)				\
779	do {								\
780		uint16_t *_d = (uint16_t *)(_dst);			\
781		_d[0] = 0xffff;						\
782		_d[1] = 0xffff;						\
783		_d[2] = 0xffff;						\
784	_NOTE(CONSTANTCONDITION)					\
785	} while (B_FALSE)
786
787#if EFSYS_OPT_CHECK_REG
788#define	EFX_CHECK_REG(_enp, _reg)					\
789	do {								\
790		const char *name = #_reg;				\
791		char min = name[4];					\
792		char max = name[5];					\
793		char rev;						\
794									\
795		switch ((_enp)->en_family) {				\
796		case EFX_FAMILY_FALCON:					\
797			rev = 'B';					\
798			break;						\
799									\
800		case EFX_FAMILY_SIENA:					\
801			rev = 'C';					\
802			break;						\
803									\
804		case EFX_FAMILY_HUNTINGTON:				\
805			rev = 'D';					\
806			break;						\
807									\
808		case EFX_FAMILY_MEDFORD:				\
809			rev = 'E';					\
810			break;						\
811									\
812		default:						\
813			rev = '?';					\
814			break;						\
815		}							\
816									\
817		EFSYS_ASSERT3S(rev, >=, min);				\
818		EFSYS_ASSERT3S(rev, <=, max);				\
819									\
820	_NOTE(CONSTANTCONDITION)					\
821	} while (B_FALSE)
822#else
823#define	EFX_CHECK_REG(_enp, _reg) do {					\
824	_NOTE(CONSTANTCONDITION)					\
825	} while(B_FALSE)
826#endif
827
828#define	EFX_BAR_READD(_enp, _reg, _edp, _lock)				\
829	do {								\
830		EFX_CHECK_REG((_enp), (_reg));				\
831		EFSYS_BAR_READD((_enp)->en_esbp, _reg ## _OFST,		\
832		    (_edp), (_lock));					\
833		EFSYS_PROBE3(efx_bar_readd, const char *, #_reg,	\
834		    uint32_t, _reg ## _OFST,				\
835		    uint32_t, (_edp)->ed_u32[0]);			\
836	_NOTE(CONSTANTCONDITION)					\
837	} while (B_FALSE)
838
839#define	EFX_BAR_WRITED(_enp, _reg, _edp, _lock)				\
840	do {								\
841		EFX_CHECK_REG((_enp), (_reg));				\
842		EFSYS_PROBE3(efx_bar_writed, const char *, #_reg,	\
843		    uint32_t, _reg ## _OFST,				\
844		    uint32_t, (_edp)->ed_u32[0]);			\
845		EFSYS_BAR_WRITED((_enp)->en_esbp, _reg ## _OFST,	\
846		    (_edp), (_lock));					\
847	_NOTE(CONSTANTCONDITION)					\
848	} while (B_FALSE)
849
850#define	EFX_BAR_READQ(_enp, _reg, _eqp)					\
851	do {								\
852		EFX_CHECK_REG((_enp), (_reg));				\
853		EFSYS_BAR_READQ((_enp)->en_esbp, _reg ## _OFST,		\
854		    (_eqp));						\
855		EFSYS_PROBE4(efx_bar_readq, const char *, #_reg,	\
856		    uint32_t, _reg ## _OFST,				\
857		    uint32_t, (_eqp)->eq_u32[1],			\
858		    uint32_t, (_eqp)->eq_u32[0]);			\
859	_NOTE(CONSTANTCONDITION)					\
860	} while (B_FALSE)
861
862#define	EFX_BAR_WRITEQ(_enp, _reg, _eqp)				\
863	do {								\
864		EFX_CHECK_REG((_enp), (_reg));				\
865		EFSYS_PROBE4(efx_bar_writeq, const char *, #_reg,	\
866		    uint32_t, _reg ## _OFST,				\
867		    uint32_t, (_eqp)->eq_u32[1],			\
868		    uint32_t, (_eqp)->eq_u32[0]);			\
869		EFSYS_BAR_WRITEQ((_enp)->en_esbp, _reg ## _OFST,	\
870		    (_eqp));						\
871	_NOTE(CONSTANTCONDITION)					\
872	} while (B_FALSE)
873
874#define	EFX_BAR_READO(_enp, _reg, _eop)					\
875	do {								\
876		EFX_CHECK_REG((_enp), (_reg));				\
877		EFSYS_BAR_READO((_enp)->en_esbp, _reg ## _OFST,		\
878		    (_eop), B_TRUE);					\
879		EFSYS_PROBE6(efx_bar_reado, const char *, #_reg,	\
880		    uint32_t, _reg ## _OFST,				\
881		    uint32_t, (_eop)->eo_u32[3],			\
882		    uint32_t, (_eop)->eo_u32[2],			\
883		    uint32_t, (_eop)->eo_u32[1],			\
884		    uint32_t, (_eop)->eo_u32[0]);			\
885	_NOTE(CONSTANTCONDITION)					\
886	} while (B_FALSE)
887
888#define	EFX_BAR_WRITEO(_enp, _reg, _eop)				\
889	do {								\
890		EFX_CHECK_REG((_enp), (_reg));				\
891		EFSYS_PROBE6(efx_bar_writeo, const char *, #_reg,	\
892		    uint32_t, _reg ## _OFST,				\
893		    uint32_t, (_eop)->eo_u32[3],			\
894		    uint32_t, (_eop)->eo_u32[2],			\
895		    uint32_t, (_eop)->eo_u32[1],			\
896		    uint32_t, (_eop)->eo_u32[0]);			\
897		EFSYS_BAR_WRITEO((_enp)->en_esbp, _reg ## _OFST,	\
898		    (_eop), B_TRUE);					\
899	_NOTE(CONSTANTCONDITION)					\
900	} while (B_FALSE)
901
902#define	EFX_BAR_TBL_READD(_enp, _reg, _index, _edp, _lock)		\
903	do {								\
904		EFX_CHECK_REG((_enp), (_reg));				\
905		EFSYS_BAR_READD((_enp)->en_esbp,			\
906		    (_reg ## _OFST + ((_index) * _reg ## _STEP)),	\
907		    (_edp), (_lock));					\
908		EFSYS_PROBE4(efx_bar_tbl_readd, const char *, #_reg,	\
909		    uint32_t, (_index),					\
910		    uint32_t, _reg ## _OFST,				\
911		    uint32_t, (_edp)->ed_u32[0]);			\
912	_NOTE(CONSTANTCONDITION)					\
913	} while (B_FALSE)
914
915#define	EFX_BAR_TBL_WRITED(_enp, _reg, _index, _edp, _lock)		\
916	do {								\
917		EFX_CHECK_REG((_enp), (_reg));				\
918		EFSYS_PROBE4(efx_bar_tbl_writed, const char *, #_reg,	\
919		    uint32_t, (_index),					\
920		    uint32_t, _reg ## _OFST,				\
921		    uint32_t, (_edp)->ed_u32[0]);			\
922		EFSYS_BAR_WRITED((_enp)->en_esbp,			\
923		    (_reg ## _OFST + ((_index) * _reg ## _STEP)),	\
924		    (_edp), (_lock));					\
925	_NOTE(CONSTANTCONDITION)					\
926	} while (B_FALSE)
927
928#define	EFX_BAR_TBL_WRITED2(_enp, _reg, _index, _edp, _lock)		\
929	do {								\
930		EFX_CHECK_REG((_enp), (_reg));				\
931		EFSYS_PROBE4(efx_bar_tbl_writed, const char *, #_reg,	\
932		    uint32_t, (_index),					\
933		    uint32_t, _reg ## _OFST,				\
934		    uint32_t, (_edp)->ed_u32[0]);			\
935		EFSYS_BAR_WRITED((_enp)->en_esbp,			\
936		    (_reg ## _OFST +					\
937		    (2 * sizeof (efx_dword_t)) + 			\
938		    ((_index) * _reg ## _STEP)),			\
939		    (_edp), (_lock));					\
940	_NOTE(CONSTANTCONDITION)					\
941	} while (B_FALSE)
942
943#define	EFX_BAR_TBL_WRITED3(_enp, _reg, _index, _edp, _lock)		\
944	do {								\
945		EFX_CHECK_REG((_enp), (_reg));				\
946		EFSYS_PROBE4(efx_bar_tbl_writed, const char *, #_reg,	\
947		    uint32_t, (_index),					\
948		    uint32_t, _reg ## _OFST,				\
949		    uint32_t, (_edp)->ed_u32[0]);			\
950		EFSYS_BAR_WRITED((_enp)->en_esbp,			\
951		    (_reg ## _OFST +					\
952		    (3 * sizeof (efx_dword_t)) + 			\
953		    ((_index) * _reg ## _STEP)),			\
954		    (_edp), (_lock));					\
955	_NOTE(CONSTANTCONDITION)					\
956	} while (B_FALSE)
957
958#define	EFX_BAR_TBL_READQ(_enp, _reg, _index, _eqp)			\
959	do {								\
960		EFX_CHECK_REG((_enp), (_reg));				\
961		EFSYS_BAR_READQ((_enp)->en_esbp,			\
962		    (_reg ## _OFST + ((_index) * _reg ## _STEP)),	\
963		    (_eqp));						\
964		EFSYS_PROBE5(efx_bar_tbl_readq, const char *, #_reg,	\
965		    uint32_t, (_index),					\
966		    uint32_t, _reg ## _OFST,				\
967		    uint32_t, (_eqp)->eq_u32[1],			\
968		    uint32_t, (_eqp)->eq_u32[0]);			\
969	_NOTE(CONSTANTCONDITION)					\
970	} while (B_FALSE)
971
972#define	EFX_BAR_TBL_WRITEQ(_enp, _reg, _index, _eqp)			\
973	do {								\
974		EFX_CHECK_REG((_enp), (_reg));				\
975		EFSYS_PROBE5(efx_bar_tbl_writeq, const char *, #_reg,	\
976		    uint32_t, (_index),					\
977		    uint32_t, _reg ## _OFST,				\
978		    uint32_t, (_eqp)->eq_u32[1],			\
979		    uint32_t, (_eqp)->eq_u32[0]);			\
980		EFSYS_BAR_WRITEQ((_enp)->en_esbp,			\
981		    (_reg ## _OFST + ((_index) * _reg ## _STEP)),	\
982		    (_eqp));						\
983	_NOTE(CONSTANTCONDITION)					\
984	} while (B_FALSE)
985
986#define	EFX_BAR_TBL_READO(_enp, _reg, _index, _eop, _lock)		\
987	do {								\
988		EFX_CHECK_REG((_enp), (_reg));				\
989		EFSYS_BAR_READO((_enp)->en_esbp,			\
990		    (_reg ## _OFST + ((_index) * _reg ## _STEP)),	\
991		    (_eop), (_lock));					\
992		EFSYS_PROBE7(efx_bar_tbl_reado, const char *, #_reg,	\
993		    uint32_t, (_index),					\
994		    uint32_t, _reg ## _OFST,				\
995		    uint32_t, (_eop)->eo_u32[3],			\
996		    uint32_t, (_eop)->eo_u32[2],			\
997		    uint32_t, (_eop)->eo_u32[1],			\
998		    uint32_t, (_eop)->eo_u32[0]);			\
999	_NOTE(CONSTANTCONDITION)					\
1000	} while (B_FALSE)
1001
1002#define	EFX_BAR_TBL_WRITEO(_enp, _reg, _index, _eop, _lock)		\
1003	do {								\
1004		EFX_CHECK_REG((_enp), (_reg));				\
1005		EFSYS_PROBE7(efx_bar_tbl_writeo, const char *, #_reg,	\
1006		    uint32_t, (_index),					\
1007		    uint32_t, _reg ## _OFST,				\
1008		    uint32_t, (_eop)->eo_u32[3],			\
1009		    uint32_t, (_eop)->eo_u32[2],			\
1010		    uint32_t, (_eop)->eo_u32[1],			\
1011		    uint32_t, (_eop)->eo_u32[0]);			\
1012		EFSYS_BAR_WRITEO((_enp)->en_esbp,			\
1013		    (_reg ## _OFST + ((_index) * _reg ## _STEP)),	\
1014		    (_eop), (_lock));					\
1015	_NOTE(CONSTANTCONDITION)					\
1016	} while (B_FALSE)
1017
1018/*
1019 * Allow drivers to perform optimised 128-bit doorbell writes.
1020 * The DMA descriptor pointers (RX_DESC_UPD and TX_DESC_UPD) are
1021 * special-cased in the BIU on the Falcon/Siena and EF10 architectures to avoid
1022 * the need for locking in the host, and are the only ones known to be safe to
1023 * use 128-bites write with.
1024 */
1025#define	EFX_BAR_TBL_DOORBELL_WRITEO(_enp, _reg, _index, _eop)		\
1026	do {								\
1027		EFX_CHECK_REG((_enp), (_reg));				\
1028		EFSYS_PROBE7(efx_bar_tbl_doorbell_writeo,		\
1029		    const char *,					\
1030		    #_reg,						\
1031		    uint32_t, (_index),					\
1032		    uint32_t, _reg ## _OFST,				\
1033		    uint32_t, (_eop)->eo_u32[3],			\
1034		    uint32_t, (_eop)->eo_u32[2],			\
1035		    uint32_t, (_eop)->eo_u32[1],			\
1036		    uint32_t, (_eop)->eo_u32[0]);			\
1037		EFSYS_BAR_DOORBELL_WRITEO((_enp)->en_esbp,		\
1038		    (_reg ## _OFST + ((_index) * _reg ## _STEP)),	\
1039		    (_eop));						\
1040	_NOTE(CONSTANTCONDITION)					\
1041	} while (B_FALSE)
1042
1043#define	EFX_DMA_SYNC_QUEUE_FOR_DEVICE(_esmp, _entries, _wptr, _owptr)	\
1044	do {								\
1045		unsigned int _new = (_wptr);				\
1046		unsigned int _old = (_owptr);				\
1047									\
1048		if ((_new) >= (_old))					\
1049			EFSYS_DMA_SYNC_FOR_DEVICE((_esmp),		\
1050			    (_old) * sizeof (efx_desc_t),		\
1051			    ((_new) - (_old)) * sizeof (efx_desc_t));	\
1052		else							\
1053			/*						\
1054			 * It is cheaper to sync entire map than sync	\
1055			 * two parts especially when offset/size are	\
1056			 * ignored and entire map is synced in any case.\
1057			 */						\
1058			EFSYS_DMA_SYNC_FOR_DEVICE((_esmp),		\
1059			    0,						\
1060			    (_entries) * sizeof (efx_desc_t));		\
1061	_NOTE(CONSTANTCONDITION)					\
1062	} while (B_FALSE)
1063
1064extern	__checkReturn	efx_rc_t
1065efx_nic_biu_test(
1066	__in		efx_nic_t *enp);
1067
1068extern	__checkReturn	efx_rc_t
1069efx_mac_select(
1070	__in		efx_nic_t *enp);
1071
1072extern	void
1073efx_mac_multicast_hash_compute(
1074	__in_ecount(6*count)		uint8_t const *addrs,
1075	__in				int count,
1076	__out				efx_oword_t *hash_low,
1077	__out				efx_oword_t *hash_high);
1078
1079extern	__checkReturn	efx_rc_t
1080efx_phy_probe(
1081	__in		efx_nic_t *enp);
1082
1083extern			void
1084efx_phy_unprobe(
1085	__in		efx_nic_t *enp);
1086
1087#if EFSYS_OPT_VPD
1088
1089/* VPD utility functions */
1090
1091extern	__checkReturn		efx_rc_t
1092efx_vpd_hunk_length(
1093	__in_bcount(size)	caddr_t data,
1094	__in			size_t size,
1095	__out			size_t *lengthp);
1096
1097extern	__checkReturn		efx_rc_t
1098efx_vpd_hunk_verify(
1099	__in_bcount(size)	caddr_t data,
1100	__in			size_t size,
1101	__out_opt		boolean_t *cksummedp);
1102
1103extern	__checkReturn		efx_rc_t
1104efx_vpd_hunk_reinit(
1105	__in_bcount(size)	caddr_t data,
1106	__in			size_t size,
1107	__in			boolean_t wantpid);
1108
1109extern	__checkReturn		efx_rc_t
1110efx_vpd_hunk_get(
1111	__in_bcount(size)	caddr_t data,
1112	__in			size_t size,
1113	__in			efx_vpd_tag_t tag,
1114	__in			efx_vpd_keyword_t keyword,
1115	__out			unsigned int *payloadp,
1116	__out			uint8_t *paylenp);
1117
1118extern	__checkReturn			efx_rc_t
1119efx_vpd_hunk_next(
1120	__in_bcount(size)		caddr_t data,
1121	__in				size_t size,
1122	__out				efx_vpd_tag_t *tagp,
1123	__out				efx_vpd_keyword_t *keyword,
1124	__out_bcount_opt(*paylenp)	unsigned int *payloadp,
1125	__out_opt			uint8_t *paylenp,
1126	__inout				unsigned int *contp);
1127
1128extern	__checkReturn		efx_rc_t
1129efx_vpd_hunk_set(
1130	__in_bcount(size)	caddr_t data,
1131	__in			size_t size,
1132	__in			efx_vpd_value_t *evvp);
1133
1134#endif	/* EFSYS_OPT_VPD */
1135
1136#if EFSYS_OPT_DIAG
1137
1138extern	efx_sram_pattern_fn_t	__efx_sram_pattern_fns[];
1139
1140typedef struct efx_register_set_s {
1141	unsigned int		address;
1142	unsigned int		step;
1143	unsigned int		rows;
1144	efx_oword_t		mask;
1145} efx_register_set_t;
1146
1147extern	__checkReturn	efx_rc_t
1148efx_nic_test_registers(
1149	__in		efx_nic_t *enp,
1150	__in		efx_register_set_t *rsp,
1151	__in		size_t count);
1152
1153extern	__checkReturn	efx_rc_t
1154efx_nic_test_tables(
1155	__in		efx_nic_t *enp,
1156	__in		efx_register_set_t *rsp,
1157	__in		efx_pattern_type_t pattern,
1158	__in		size_t count);
1159
1160#endif	/* EFSYS_OPT_DIAG */
1161
1162#if EFSYS_OPT_MCDI
1163
1164extern	__checkReturn		efx_rc_t
1165efx_mcdi_set_workaround(
1166	__in			efx_nic_t *enp,
1167	__in			uint32_t type,
1168	__in			boolean_t enabled,
1169	__out_opt		uint32_t *flagsp);
1170
1171extern	__checkReturn		efx_rc_t
1172efx_mcdi_get_workarounds(
1173	__in			efx_nic_t *enp,
1174	__out_opt		uint32_t *implementedp,
1175	__out_opt		uint32_t *enabledp);
1176
1177#endif /* EFSYS_OPT_MCDI */
1178
1179#ifdef	__cplusplus
1180}
1181#endif
1182
1183#endif	/* _SYS_EFX_IMPL_H */
1184