sfxge.h revision 272328
1145857Sume/*-
2145857Sume * Copyright (c) 2010-2011 Solarflare Communications, Inc.
3145857Sume * All rights reserved.
4145857Sume *
5145857Sume * This software was developed in part by Philip Paeps under contract for
6145857Sume * Solarflare Communications, Inc.
7145857Sume *
8145857Sume * Redistribution and use in source and binary forms, with or without
9145857Sume * modification, are permitted provided that the following conditions
10145857Sume * are met:
11145857Sume * 1. Redistributions of source code must retain the above copyright
12145857Sume *    notice, this list of conditions and the following disclaimer.
13145857Sume * 2. Redistributions in binary form must reproduce the above copyright
14145857Sume *    notice, this list of conditions and the following disclaimer in the
15145857Sume *    documentation and/or other materials provided with the distribution.
16145857Sume *
17145857Sume * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18145857Sume * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19145857Sume * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20145857Sume * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21145857Sume * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22145857Sume * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23145857Sume * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24145857Sume * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25145857Sume * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26145857Sume * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27145857Sume * SUCH DAMAGE.
28145857Sume *
29145857Sume * $FreeBSD: head/sys/dev/sfxge/sfxge.h 272328 2014-09-30 20:36:07Z gnn $
30145857Sume */
31145860Sume
32145857Sume#ifndef _SFXGE_H
33145857Sume#define	_SFXGE_H
34145857Sume
35145860Sume#include <sys/param.h>
36145860Sume#include <sys/kernel.h>
37145857Sume#include <sys/condvar.h>
38145857Sume#include <sys/socket.h>
39145857Sume#include <sys/sysctl.h>
40145857Sume#include <sys/sx.h>
41145857Sume#include <vm/uma.h>
42145857Sume
43145857Sume#include <net/ethernet.h>
44145857Sume#include <net/if.h>
45145857Sume#include <net/if_var.h>
46145857Sume#include <net/if_media.h>
47145857Sume#include <net/if_types.h>
48145857Sume
49145857Sume/*
50145860Sume * Backward-compatibility
51145860Sume */
52145860Sume#ifndef CACHE_LINE_SIZE
53145860Sume/* This should be right on most machines the driver will be used on, and
54145860Sume * we needn't care too much about wasting a few KB per interface.
55145860Sume */
56145857Sume#define	CACHE_LINE_SIZE 128
57145857Sume#endif
58145860Sume#ifndef IFCAP_LINKSTATE
59145860Sume#define	IFCAP_LINKSTATE 0
60145857Sume#endif
61145857Sume#ifndef IFCAP_VLAN_HWTSO
62145857Sume#define	IFCAP_VLAN_HWTSO 0
63145857Sume#endif
64145857Sume#ifndef IFM_10G_T
65145857Sume#define	IFM_10G_T IFM_UNKNOWN
66145857Sume#endif
67145857Sume#ifndef IFM_10G_KX4
68145857Sume#define	IFM_10G_KX4 IFM_10G_CX4
69145857Sume#endif
70145857Sume#if __FreeBSD_version >= 800054
71145857Sume/* Networking core is multiqueue aware. We can manage our own TX
72145857Sume * queues and use m_pkthdr.flowid.
73145857Sume */
74145857Sume#define	SFXGE_HAVE_MQ
75145860Sume#endif
76145857Sume#if (__FreeBSD_version >= 800501 && __FreeBSD_version < 900000) || \
77145857Sume	__FreeBSD_version >= 900003
78145857Sume#define	SFXGE_HAVE_DESCRIBE_INTR
79145857Sume#endif
80145857Sume#ifdef IFM_ETH_RXPAUSE
81145857Sume#define	SFXGE_HAVE_PAUSE_MEDIAOPTS
82145857Sume#endif
83145857Sume#ifndef CTLTYPE_U64
84145857Sume#define	CTLTYPE_U64 CTLTYPE_QUAD
85145857Sume#endif
86145857Sume
87145857Sume#include "sfxge_rx.h"
88145857Sume#include "sfxge_tx.h"
89145857Sume
90145857Sume#define	ROUNDUP_POW_OF_TWO(_n)	(1ULL << flsl((_n) - 1))
91145857Sume
92145857Sume#define	SFXGE_IP_ALIGN	2
93291362Sngie
94291362Sngie#define	SFXGE_ETHERTYPE_LOOPBACK	0x9000	/* Xerox loopback */
95291362Sngie
96145857Sumeenum sfxge_evq_state {
97291362Sngie	SFXGE_EVQ_UNINITIALIZED = 0,
98145857Sume	SFXGE_EVQ_INITIALIZED,
99145857Sume	SFXGE_EVQ_STARTING,
100145857Sume	SFXGE_EVQ_STARTED
101145857Sume};
102145857Sume
103145857Sume#define	SFXGE_EV_BATCH	16384
104145860Sume
105145860Sumestruct sfxge_evq {
106145860Sume	struct sfxge_softc	*sc  __aligned(CACHE_LINE_SIZE);
107145860Sume	struct mtx		lock __aligned(CACHE_LINE_SIZE);
108145860Sume
109145860Sume	enum sfxge_evq_state	init_state;
110145860Sume	unsigned int		index;
111145860Sume	unsigned int		entries;
112145860Sume	efsys_mem_t		mem;
113145860Sume	unsigned int		buf_base_id;
114145860Sume
115145860Sume	boolean_t		exception;
116145860Sume
117145860Sume	efx_evq_t		*common;
118145860Sume	unsigned int		read_ptr;
119145860Sume	unsigned int		rx_done;
120145860Sume	unsigned int		tx_done;
121145860Sume
122145860Sume	/* Linked list of TX queues with completions to process */
123145860Sume	struct sfxge_txq	*txq;
124145860Sume	struct sfxge_txq	**txqs;
125145860Sume};
126145860Sume
127145860Sume#define	SFXGE_NDESCS	1024
128145860Sume#define	SFXGE_MODERATION	30
129145860Sume
130145860Sumeenum sfxge_intr_state {
131145860Sume	SFXGE_INTR_UNINITIALIZED = 0,
132145860Sume	SFXGE_INTR_INITIALIZED,
133145860Sume	SFXGE_INTR_TESTING,
134145860Sume	SFXGE_INTR_STARTED
135145860Sume};
136145860Sume
137145860Sumestruct sfxge_intr_hdl {
138145860Sume	int			eih_rid;
139145860Sume	void			*eih_tag;
140145860Sume	struct resource		*eih_res;
141145860Sume};
142145860Sume
143145860Sumestruct sfxge_intr {
144145860Sume	enum sfxge_intr_state	state;
145145860Sume	struct resource		*msix_res;
146145860Sume	struct sfxge_intr_hdl	*table;
147145860Sume	int			n_alloc;
148145860Sume	int			type;
149145860Sume	efsys_mem_t		status;
150145860Sume	uint32_t		zero_count;
151145860Sume};
152145860Sume
153145860Sumeenum sfxge_mcdi_state {
154145860Sume	SFXGE_MCDI_UNINITIALIZED = 0,
155145860Sume	SFXGE_MCDI_INITIALIZED,
156145860Sume	SFXGE_MCDI_BUSY,
157145860Sume	SFXGE_MCDI_COMPLETED
158145860Sume};
159145860Sume
160145860Sumestruct sfxge_mcdi {
161145860Sume	struct mtx		lock;
162145860Sume	struct cv		cv;
163145860Sume	enum sfxge_mcdi_state	state;
164145860Sume	efx_mcdi_transport_t	transport;
165145860Sume};
166145860Sume
167145860Sumestruct sfxge_hw_stats {
168145860Sume	clock_t			update_time;
169145860Sume	efsys_mem_t		dma_buf;
170145860Sume	void			*decode_buf;
171145860Sume};
172145860Sume
173145860Sumeenum sfxge_port_state {
174145860Sume	SFXGE_PORT_UNINITIALIZED = 0,
175145860Sume	SFXGE_PORT_INITIALIZED,
176145860Sume	SFXGE_PORT_STARTED
177145860Sume};
178145860Sume
179145860Sumestruct sfxge_port {
180145860Sume	struct sfxge_softc	*sc;
181145860Sume	struct mtx		lock;
182145860Sume	enum sfxge_port_state	init_state;
183145860Sume#ifndef SFXGE_HAVE_PAUSE_MEDIAOPTS
184145860Sume	unsigned int		wanted_fc;
185145860Sume#endif
186145860Sume	struct sfxge_hw_stats	phy_stats;
187145860Sume	struct sfxge_hw_stats	mac_stats;
188145860Sume	efx_link_mode_t		link_mode;
189145860Sume};
190145860Sume
191145860Sumeenum sfxge_softc_state {
192145860Sume	SFXGE_UNINITIALIZED = 0,
193145857Sume	SFXGE_INITIALIZED,
194145857Sume	SFXGE_REGISTERED,
195145857Sume	SFXGE_STARTED
196145857Sume};
197145857Sume
198145857Sumestruct sfxge_softc {
199145857Sume	device_t			dev;
200145860Sume	struct sx			softc_lock;
201145857Sume	enum sfxge_softc_state		init_state;
202145860Sume	struct ifnet			*ifnet;
203145857Sume	unsigned int			if_flags;
204145857Sume	struct sysctl_oid		*stats_node;
205145857Sume
206145857Sume	struct task			task_reset;
207145857Sume
208145860Sume	efx_family_t			family;
209145860Sume	caddr_t				vpd_data;
210145860Sume	size_t				vpd_size;
211145860Sume	efx_nic_t			*enp;
212145860Sume	struct mtx			enp_lock;
213145860Sume
214145860Sume	unsigned int			rxq_entries;
215145860Sume	unsigned int			txq_entries;
216145860Sume
217145860Sume	bus_dma_tag_t			parent_dma_tag;
218145860Sume	efsys_bar_t			bar;
219145860Sume
220145857Sume	struct sfxge_intr		intr;
221145857Sume	struct sfxge_mcdi		mcdi;
222145857Sume	struct sfxge_port		port;
223145857Sume	uint32_t			buffer_table_next;
224145857Sume
225145857Sume	struct sfxge_evq		*evq[SFXGE_RX_SCALE_MAX];
226145857Sume	unsigned int			ev_moderation;
227145857Sume	clock_t				ev_stats_update_time;
228145857Sume	uint64_t			ev_stats[EV_NQSTATS];
229145857Sume
230145857Sume	uma_zone_t			rxq_cache;
231145857Sume	struct sfxge_rxq		*rxq[SFXGE_RX_SCALE_MAX];
232243346Semaste	unsigned int			rx_indir_table[SFXGE_RX_SCALE_MAX];
233145857Sume
234145857Sume#ifdef SFXGE_HAVE_MQ
235145857Sume	struct sfxge_txq		*txq[SFXGE_TXQ_NTYPES + SFXGE_RX_SCALE_MAX];
236145857Sume#else
237145857Sume	struct sfxge_txq		*txq[SFXGE_TXQ_NTYPES];
238145857Sume#endif
239145857Sume
240145857Sume	struct ifmedia			media;
241145857Sume
242145857Sume	size_t				rx_prefix_size;
243145857Sume	size_t				rx_buffer_size;
244145857Sume	uma_zone_t			rx_buffer_zone;
245145857Sume
246145857Sume#ifndef SFXGE_HAVE_MQ
247145857Sume	struct mtx			tx_lock __aligned(CACHE_LINE_SIZE);
248145857Sume#endif
249145857Sume};
250145857Sume
251145857Sume#define	SFXGE_LINK_UP(sc) ((sc)->port.link_mode != EFX_LINK_DOWN)
252145857Sume#define	SFXGE_RUNNING(sc) ((sc)->ifnet->if_drv_flags & IFF_DRV_RUNNING)
253145857Sume
254145857Sume#define	SFXGE_PARAM(_name)	"hw.sfxge." #_name
255145857Sume
256145857SumeSYSCTL_DECL(_hw_sfxge);
257145860Sume
258145857Sume/*
259145860Sume * From sfxge.c.
260145860Sume */
261145860Sumeextern void sfxge_schedule_reset(struct sfxge_softc *sc);
262145857Sumeextern void sfxge_sram_buf_tbl_alloc(struct sfxge_softc *sc, size_t n,
263145857Sume				     uint32_t *idp);
264145857Sume
265145857Sume/*
266145857Sume * From sfxge_dma.c.
267145857Sume */
268145860Sumeextern int sfxge_dma_init(struct sfxge_softc *sc);
269145860Sumeextern void sfxge_dma_fini(struct sfxge_softc *sc);
270145860Sumeextern int sfxge_dma_alloc(struct sfxge_softc *sc, bus_size_t len,
271145860Sume    efsys_mem_t *esmp);
272145860Sumeextern void sfxge_dma_free(efsys_mem_t *esmp);
273145860Sumeextern int sfxge_dma_map_sg_collapse(bus_dma_tag_t tag, bus_dmamap_t map,
274145857Sume    struct mbuf **mp, bus_dma_segment_t *segs, int *nsegs, int maxsegs);
275145857Sume
276145857Sume/*
277145860Sume * From sfxge_ev.c.
278145860Sume */
279145860Sumeextern int sfxge_ev_init(struct sfxge_softc *sc);
280145857Sumeextern void sfxge_ev_fini(struct sfxge_softc *sc);
281145857Sumeextern int sfxge_ev_start(struct sfxge_softc *sc);
282145857Sumeextern void sfxge_ev_stop(struct sfxge_softc *sc);
283145857Sumeextern int sfxge_ev_qpoll(struct sfxge_softc *sc, unsigned int index);
284145857Sume
285145857Sume/*
286145857Sume * From sfxge_intr.c.
287145857Sume */
288145857Sumeextern int sfxge_intr_init(struct sfxge_softc *sc);
289145857Sumeextern void sfxge_intr_fini(struct sfxge_softc *sc);
290145857Sumeextern int sfxge_intr_start(struct sfxge_softc *sc);
291145857Sumeextern void sfxge_intr_stop(struct sfxge_softc *sc);
292145857Sume
293145857Sume/*
294145857Sume * From sfxge_mcdi.c.
295145857Sume */
296145857Sumeextern int sfxge_mcdi_init(struct sfxge_softc *sc);
297145857Sumeextern void sfxge_mcdi_fini(struct sfxge_softc *sc);
298145857Sume
299145857Sume/*
300145857Sume * From sfxge_port.c.
301145857Sume */
302145857Sumeextern int sfxge_port_init(struct sfxge_softc *sc);
303145857Sumeextern void sfxge_port_fini(struct sfxge_softc *sc);
304145857Sumeextern int sfxge_port_start(struct sfxge_softc *sc);
305145857Sumeextern void sfxge_port_stop(struct sfxge_softc *sc);
306145857Sumeextern void sfxge_mac_link_update(struct sfxge_softc *sc,
307145857Sume    efx_link_mode_t mode);
308145857Sumeextern int sfxge_mac_filter_set(struct sfxge_softc *sc);
309145857Sumeextern int sfxge_port_ifmedia_init(struct sfxge_softc *sc);
310145857Sume
311145857Sume#define	SFXGE_MAX_MTU (9 * 1024)
312145857Sume
313145857Sume#endif /* _SFXGE_H */
314145857Sume