1364973Szec/*-
2364973Szec * SPDX-License-Identifier: BSD-2-Clause-FreeBSD
3364973Szec *
4364973Szec * Copyright (c) 2015 Bjoern A. Zeeb
5364973Szec * Copyright (c) 2020 Denis Salopek
6364973Szec *
7364973Szec * This software was developed by SRI International and the University of
8364973Szec * Cambridge Computer Laboratory under DARPA/AFRL contract FA8750-11-C-0249
9364973Szec * ("MRC2"), as part of the DARPA MRC research programme.
10364973Szec *
11364973Szec * Redistribution and use in source and binary forms, with or without
12364973Szec * modification, are permitted provided that the following conditions
13364973Szec * are met:
14364973Szec * 1. Redistributions of source code must retain the above copyright
15364973Szec *    notice, this list of conditions and the following disclaimer.
16364973Szec * 2. Redistributions in binary form must reproduce the above copyright
17364973Szec *    notice, this list of conditions and the following disclaimer in the
18364973Szec *    documentation and/or other materials provided with the distribution.
19364973Szec *
20364973Szec * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21364973Szec * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22364973Szec * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23364973Szec * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
24364973Szec * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
25364973Szec * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
26364973Szec * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27364973Szec * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28364973Szec * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
29364973Szec * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
30364973Szec * POSSIBILITY OF SUCH DAMAGE.
31364973Szec */
32364973Szec
33364973Szec/* $FreeBSD: stable/11/sys/dev/sume/adapter.h 364973 2020-08-30 07:34:32Z zec $ */
34364973Szec
35364973Szec#define	DEFAULT_ETHER_ADDRESS		"\02SUME\00"
36364973Szec#define	SUME_ETH_DEVICE_NAME		"sume"
37364973Szec#define	MAX_IFC_NAME_LEN		8
38364973Szec
39364973Szec#define	SUME_NPORTS			4
40364973Szec
41364973Szec#define	SUME_IOCTL_CMD_WRITE_REG	(SIOCGPRIVATE_0)
42364973Szec#define	SUME_IOCTL_CMD_READ_REG		(SIOCGPRIVATE_1)
43364973Szec
44364973Szec#define	SUME_LOCK(adapter)		mtx_lock(&adapter->lock);
45364973Szec#define	SUME_UNLOCK(adapter)		mtx_unlock(&adapter->lock);
46364973Szec
47364973Szec/* Currently SUME only uses 2 fixed channels for all port traffic and regs. */
48364973Szec#define	SUME_RIFFA_CHANNEL_DATA		0
49364973Szec#define	SUME_RIFFA_CHANNEL_REG		1
50364973Szec#define	SUME_RIFFA_CHANNELS		2
51364973Szec
52364973Szec/* RIFFA constants. */
53364973Szec#define	RIFFA_MAX_CHNLS			12
54364973Szec#define	RIFFA_MAX_BUS_WIDTH_PARAM	4
55364973Szec#define	RIFFA_SG_BUF_SIZE		(4*1024)
56364973Szec#define	RIFFA_SG_ELEMS			200
57364973Szec
58364973Szec/* RIFFA register offsets. */
59364973Szec#define	RIFFA_RX_SG_LEN_REG_OFF		0x0
60364973Szec#define	RIFFA_RX_SG_ADDR_LO_REG_OFF	0x1
61364973Szec#define	RIFFA_RX_SG_ADDR_HI_REG_OFF	0x2
62364973Szec#define	RIFFA_RX_LEN_REG_OFF		0x3
63364973Szec#define	RIFFA_RX_OFFLAST_REG_OFF	0x4
64364973Szec#define	RIFFA_TX_SG_LEN_REG_OFF		0x5
65364973Szec#define	RIFFA_TX_SG_ADDR_LO_REG_OFF	0x6
66364973Szec#define	RIFFA_TX_SG_ADDR_HI_REG_OFF	0x7
67364973Szec#define	RIFFA_TX_LEN_REG_OFF		0x8
68364973Szec#define	RIFFA_TX_OFFLAST_REG_OFF	0x9
69364973Szec#define	RIFFA_INFO_REG_OFF		0xA
70364973Szec#define	RIFFA_IRQ_REG0_OFF		0xB
71364973Szec#define	RIFFA_IRQ_REG1_OFF		0xC
72364973Szec#define	RIFFA_RX_TNFR_LEN_REG_OFF	0xD
73364973Szec#define	RIFFA_TX_TNFR_LEN_REG_OFF	0xE
74364973Szec
75364973Szec#define	RIFFA_CHNL_REG(c, o)		((c << 4) + o)
76364973Szec
77364973Szec/*
78364973Szec * RIFFA state machine;
79364973Szec * rather than using complex circular buffers for 1 transaction.
80364973Szec */
81364973Szec#define	SUME_RIFFA_CHAN_STATE_IDLE	0x01
82364973Szec#define	SUME_RIFFA_CHAN_STATE_READY	0x02
83364973Szec#define	SUME_RIFFA_CHAN_STATE_READ	0x04
84364973Szec#define	SUME_RIFFA_CHAN_STATE_LEN	0x08
85364973Szec
86364973Szec/* Accessor macros. */
87364973Szec#define	SUME_OFFLAST			((0 << 1) | (1 & 0x01))
88364973Szec#define	SUME_RIFFA_LAST(offlast)	((offlast) & 0x01)
89364973Szec#define	SUME_RIFFA_OFFSET(offlast)	((uint64_t)((offlast) >> 1) << 2)
90364973Szec#define	SUME_RIFFA_LEN(len)		((uint64_t)(len) << 2)
91364973Szec
92364973Szec#define	SUME_RIFFA_LO_ADDR(addr)	(addr & 0xFFFFFFFF)
93364973Szec#define	SUME_RIFFA_HI_ADDR(addr)	((addr >> 32) & 0xFFFFFFFF)
94364973Szec
95364973Szec/* Vector bits. */
96364973Szec#define	SUME_MSI_RXQUE			(1 << 0)
97364973Szec#define	SUME_MSI_RXBUF			(1 << 1)
98364973Szec#define	SUME_MSI_RXDONE			(1 << 2)
99364973Szec#define	SUME_MSI_TXBUF			(1 << 3)
100364973Szec#define	SUME_MSI_TXDONE			(1 << 4)
101364973Szec
102364973Szec/* Invalid vector. */
103364973Szec#define	SUME_INVALID_VECT		0xc0000000
104364973Szec
105364973Szec/* Module register data (packet counters, link status...) */
106364973Szec#define	SUME_MOD0_REG_BASE		0x44040000
107364973Szec#define	SUME_MOD_REG(port)		(SUME_MOD0_REG_BASE + 0x10000 * port)
108364973Szec
109364973Szec#define	SUME_RESET_OFFSET		0x8
110364973Szec#define	SUME_PKTIN_OFFSET		0x18
111364973Szec#define	SUME_PKTOUT_OFFSET		0x1c
112364973Szec#define	SUME_STATUS_OFFSET		0x48
113364973Szec
114364973Szec#define	SUME_RESET_ADDR(p)		(SUME_MOD_REG(p) + SUME_RESET_OFFSET)
115364973Szec#define	SUME_STAT_RX_ADDR(p)		(SUME_MOD_REG(p) + SUME_PKTIN_OFFSET)
116364973Szec#define	SUME_STAT_TX_ADDR(p)		(SUME_MOD_REG(p) + SUME_PKTOUT_OFFSET)
117364973Szec#define	SUME_STATUS_ADDR(p)		(SUME_MOD_REG(p) + SUME_STATUS_OFFSET)
118364973Szec
119364973Szec#define	SUME_LINK_STATUS(val)		((val >> 12) & 0x1)
120364973Szec
121364973Szec/* Various bits and pieces. */
122364973Szec#define	SUME_RIFFA_MAGIC		0xcafe
123364973Szec#define	SUME_MR_WRITE			0x1f
124364973Szec#define	SUME_MR_READ			0x00
125364973Szec#define	SUME_INIT_RTAG			-3
126364973Szec#define	SUME_DPORT_MASK			0xaa
127364973Szec#define	SUME_MIN_PKT_SIZE		(ETHER_MIN_LEN - ETHER_CRC_LEN)
128364973Szec
129364973Szecstruct irq {
130364973Szec	uint32_t		rid;
131364973Szec	struct resource		*res;
132364973Szec	void			*tag;
133364973Szec} __aligned(CACHE_LINE_SIZE);
134364973Szec
135364973Szecstruct nf_stats {
136364973Szec	uint64_t		hw_rx_packets;
137364973Szec	uint64_t		hw_tx_packets;
138364973Szec	uint64_t		ifc_down_bytes;
139364973Szec	uint64_t		ifc_down_packets;
140364973Szec	uint64_t		rx_bytes;
141364973Szec	uint64_t		rx_dropped;
142364973Szec	uint64_t		rx_packets;
143364973Szec	uint64_t		tx_bytes;
144364973Szec	uint64_t		tx_dropped;
145364973Szec	uint64_t		tx_packets;
146364973Szec};
147364973Szec
148364973Szecstruct riffa_chnl_dir {
149364973Szec	uint32_t		state;
150364973Szec	bus_dma_tag_t		ch_tag;
151364973Szec	bus_dmamap_t		ch_map;
152364973Szec	char			*buf_addr;	/* bouncebuf addresses+len. */
153364973Szec	bus_addr_t		buf_hw_addr;	/* -- " -- mapped. */
154364973Szec	uint32_t		num_sg;
155364973Szec	uint32_t		event;		/* Used for modreg r/w */
156364973Szec	uint32_t		len;		/* words */
157364973Szec	uint32_t		offlast;
158364973Szec	uint32_t		recovery;
159364973Szec	uint32_t		rtag;
160364973Szec};
161364973Szec
162364973Szecstruct sume_ifreq {
163364973Szec	uint32_t		addr;
164364973Szec	uint32_t		val;
165364973Szec};
166364973Szec
167364973Szecstruct nf_priv {
168364973Szec	struct sume_adapter	*adapter;
169364973Szec	struct ifmedia		media;
170364973Szec	struct nf_stats		stats;
171364973Szec	uint32_t		unit;
172364973Szec	uint32_t		port;
173364973Szec	uint32_t		link_up;
174364973Szec};
175364973Szec
176364973Szecstruct sume_adapter {
177364973Szec	struct mtx		lock;
178364973Szec	uint32_t		running;
179364973Szec	uint32_t		rid;
180364973Szec	struct riffa_chnl_dir	**recv;
181364973Szec	struct riffa_chnl_dir	**send;
182364973Szec	device_t		dev;
183364973Szec	struct ifnet		*ifp[SUME_NPORTS];
184364973Szec	struct resource		*bar0_addr;
185364973Szec	bus_space_tag_t		bt;
186364973Szec	bus_space_handle_t	bh;
187364973Szec	bus_size_t		bar0_len;
188364973Szec	struct irq		irq;
189364973Szec	struct callout		timer;
190364973Szec	struct task		stat_task;
191364973Szec	struct taskqueue	*tq;
192364973Szec	uint64_t		bytes_err;
193364973Szec	uint64_t		packets_err;
194364973Szec	uint32_t		last_ifc;
195364973Szec	uint32_t		num_sg;
196364973Szec	uint32_t		sg_buf_size;
197364973Szec	uint32_t		sume_debug;
198364973Szec	uint32_t		wd_counter;
199364973Szec};
200364973Szec
201364973Szec/* SUME metadata:
202364973Szec * sport - not used for RX. For TX, set to 0x02, 0x08, 0x20, 0x80, depending on
203364973Szec *     the sending interface (nf0, nf1, nf2 or nf3).
204364973Szec * dport - For RX, is set to 0x02, 0x08, 0x20, 0x80, depending on the receiving
205364973Szec *     interface (nf0, nf1, nf2 or nf3). For TX, set to 0x01, 0x04, 0x10, 0x40,
206364973Szec *     depending on the sending HW interface (nf0, nf1, nf2 or nf3).
207364973Szec * plen - length of the send/receive packet data (in bytes)
208364973Szec * magic - SUME hardcoded magic number which should be 0xcafe
209364973Szec * t1, t1 - could be used for timestamping by SUME
210364973Szec */
211364973Szecstruct nf_metadata {
212364973Szec	uint16_t		sport;
213364973Szec	uint16_t		dport;
214364973Szec	uint16_t		plen;
215364973Szec	uint16_t		magic;
216364973Szec	uint32_t		t1;
217364973Szec	uint32_t		t2;
218364973Szec};
219364973Szec
220364973Szec/* Used for ioctl communication with the rwaxi program used to read/write SUME
221364973Szec *    internally defined register data.
222364973Szec * addr - address of the SUME module register to read/write
223364973Szec * val - value to write/read to/from the register
224364973Szec * rtag - returned on read: transaction tag, for syncronization
225364973Szec * optype - 0x1f when writing, 0x00 for reading
226364973Szec */
227364973Szecstruct nf_regop_data {
228364973Szec	uint32_t		addr;
229364973Szec	uint32_t		val;
230364973Szec	uint32_t		rtag;
231364973Szec	uint32_t		optype;
232364973Szec};
233364973Szec
234364973Szec/* Our bouncebuffer "descriptor". This holds our physical address (lower and
235364973Szec * upper values) of the beginning of the DMA data to RX/TX. The len is number
236364973Szec * of words to transmit.
237364973Szec */
238364973Szecstruct nf_bb_desc {
239364973Szec	uint32_t		lower;
240364973Szec	uint32_t		upper;
241364973Szec	uint32_t		len;
242364973Szec};
243