xref: /freebsd/sys/dev/mgb/if_mgb.h (revision 95ee2897)
1 /*-
2  * SPDX-License-Identifier: BSD-2-Clause
3  *
4  * Copyright (c) 2019 The FreeBSD Foundation, Inc.
5  *
6  * This driver was written by Gerald ND Aryeetey <gndaryee@uwaterloo.ca>
7  * under sponsorship from the FreeBSD Foundation.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions and the following disclaimer.
14  * 2. Redistributions in binary form must reproduce the above copyright
15  *    notice, this list of conditions and the following disclaimer in the
16  *    documentation and/or other materials provided with the distribution.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
19  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21  * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
22  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
24  * OR SERVICES; LOSS OF USE DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
26  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28  * SUCH DAMAGE.
29  */
30 #ifndef _IF_MGB_H_
31 #define _IF_MGB_H_
32 
33 #define MGB_MICROCHIP_VENDOR_ID		0x1055
34 #define MGB_LAN7430_DEVICE_ID		0x7430
35 #define MGB_LAN7431_DEVICE_ID		0x7431
36 
37 #define MGB_TIMEOUT			(500)
38 
39 /** Control/Status Registers **/
40 #define MGB_BAR				0 /* PCI Base Address */
41 
42 /** Reset **/
43 #define MGB_HW_CFG			0x10 /** H/W Configuration Register **/
44 #define MGB_LITE_RESET 			0x2
45 
46 /** MAC **/
47 #define MGB_MAC_CR			0x0100 /** MAC Crontrol Register **/
48 #define MGB_MAC_ADD_ENBL		0x1000 /* Automatic Duplex Detection */
49 #define MGB_MAC_ASD_ENBL		0x0800 /* Automatic Speed Detection */
50 
51 #define MGB_MAC_ADDR_BASE_L		0x11C /** MAC address lower 4 bytes (read) register **/
52 #define MGB_MAC_ADDR_BASE_H		0x118 /** MAC address upper 2 bytes (read) register **/
53 
54 #define MGB_MAC_TX			0x0104
55 #define MGB_MAC_RX			0x0108
56 #define MGB_MAC_ENBL			(1 << 0)
57 #define MGB_MAC_DSBL			(1 << 1)
58 
59 /** MAC Statistics **/
60 #define MGB_MAC_STAT_RX_FCS_ERR_CNT	0x1200
61 #define MGB_MAC_STAT_RX_ALIGN_ERR_CNT	0x1204
62 #define MGB_MAC_STAT_RX_FRAG_ERR_CNT	0x1208
63 #define MGB_MAC_STAT_RX_JABBER_ERR_CNT	0x120C
64 #define MGB_MAC_STAT_RX_UNDER_ERR_CNT	0x1210
65 #define MGB_MAC_STAT_RX_OVER_ERR_CNT	0x1214
66 #define MGB_MAC_STAT_RX_DROPPED_CNT	0x1218
67 #define MGB_MAC_STAT_RX_BROADCAST_CNT1	0x1220
68 #define MGB_MAC_STAT_RX_BROADCAST_CNT	0x122C
69 #define MGB_MAC_STAT_RX_FRAME_CNT	0x1254
70 #define MGB_MAC_STAT_RX_DROPPED_CNT	0x1218
71 #define MGB_MAC_STAT_RX_BROADCAST_CNT1	0x1220
72 #define MGB_MAC_STAT_RX_BROADCAST_CNT	0x122C
73 #define MGB_MAC_STAT_RX_FRAME_CNT	0x1254
74 /* etc. */
75 
76 /** Receive Filtering Engine **/
77 #define MGB_RFE_CTL			0x508
78 #define MGB_RFE_ALLOW_BROADCAST		(1 << 10)
79 #define MGB_RFE_ALLOW_MULTICAST		(1 << 9)
80 #define MGB_RFE_ALLOW_UNICAST		(1 << 8)
81 #define MGB_RFE_ALLOW_PERFECT_FILTER	(1 << 1)
82 
83 /** PHY Reset (via power management control) **/
84 #define MGB_PMT_CTL			0x14 /** Power Management Control Register **/
85 #define MGB_PHY_RESET			0x10
86 #define MGB_PHY_READY			0x80
87 
88 /** FIFO Controller **/
89 #define MGB_FCT_TX_CTL			0xC4
90 #define MGB_FCT_RX_CTL			0xAC
91 #define MGB_FCT_ENBL(_channel)		(1 << (28 + (_channel)))
92 #define MGB_FCT_DSBL(_channel)		(1 << (24 + (_channel)))
93 #define MGB_FCT_RESET(_channel)		(1 << (20 + (_channel)))
94 
95 /** DMA Controller **/
96 #define MGB_DMAC_CMD			0xC0C
97 #define MGB_DMAC_RESET			(1 << 31)
98 #define MGB_DMAC_TX_START		16
99 #define MGB_DMAC_RX_START		0
100 #define MGB_DMAC_CMD_VAL(s, o, ch)	(1 << ((s) + (o) + (ch)))
101 #define MGB_DMAC_CMD_RESET(_s, _ch)	MGB_DMAC_CMD_VAL(_s, 8, _ch)
102 #define MGB_DMAC_CMD_START(_s, _ch)	MGB_DMAC_CMD_VAL(_s, 4, _ch)
103 #define MGB_DMAC_CMD_STOP( _s, _ch)	MGB_DMAC_CMD_VAL(_s, 0, _ch)
104 #define MGB_DMAC_STATE(_start, _stop)	\
105 	(((_start) ? 2 : 0) | ((_stop) ? 1 : 0))
106 #define MGB_DMAC_STATE_INITIAL		MGB_DMAC_STATE(0, 0)
107 #define MGB_DMAC_STATE_STARTED		MGB_DMAC_STATE(1, 0)
108 #define MGB_DMAC_STATE_STOP_PENDING	MGB_DMAC_STATE(1, 1)
109 #define MGB_DMAC_STATE_STOPPED		MGB_DMAC_STATE(0, 1)
110 #define MGB_DMAC_CMD_STATE(sc, _s, _ch)				\
111 	(MGB_DMAC_STATE(					\
112 	    CSR_READ_REG(sc, MGB_DMAC_CMD) & MGB_DMAC_CMD_START(_s, _ch),	\
113 	    CSR_READ_REG(sc, MGB_DMAC_CMD) & MGB_DMAC_CMD_STOP(_s, _ch)))
114 #define MGB_DMAC_STATE_IS_INITIAL(sc, _s, _ch)			\
115 	(MGB_DMAC_CMD_STATE(sc, _s, _ch) == MGB_DMAC_STATE_INITIAL)
116 
117 #define MGB_DMAC_INTR_STS		0xC10
118 #define MGB_DMAC_INTR_ENBL_SET		0xC14
119 #define MGB_DMAC_INTR_ENBL_CLR		0xC18
120 #define MGB_DMAC_TX_INTR_ENBL(_ch)	(1 << (_ch))
121 #define MGB_DMAC_RX_INTR_ENBL(_ch)	(1 << (16 + (_ch)))
122 
123 /** DMA Rings **/
124 /**
125  * Page size is 256 bytes
126  *
127  * Ring size, however, these could be tunable (for RX & TX)
128  * to be a multiple of 4 (max is 65532)
129  *
130  **/
131 /* In linux driver these numbers are 50 and 65 for tx and rx .... */
132 #define MGB_DMA_RING_SIZE		16 /* in programming guide, this number is 100 */
133 #define MGB_DMA_MAXSEGS			32
134 #define MGB_DMA_REG(reg, _channel)	((reg) | ((_channel) << 6))
135 #define MGB_DMA_RING_LIST_SIZE		\
136 	(sizeof(struct mgb_ring_desc) * MGB_DMA_RING_SIZE)
137 #define MGB_DMA_RING_INFO_SIZE		\
138 	(sizeof(uint32_t) + MGB_DMA_RING_LIST_SIZE)
139 
140 #define MGB_DMA_TX_CONFIG0(_channel)	MGB_DMA_REG(0x0D40, _channel)
141 #define MGB_DMA_TX_CONFIG1(_channel)	MGB_DMA_REG(0x0D44, _channel)
142 #define MGB_DMA_TX_BASE_H(_channel)	MGB_DMA_REG(0x0D48, _channel)
143 #define MGB_DMA_TX_BASE_L(_channel)	MGB_DMA_REG(0x0D4C, _channel)
144 #define MGB_DMA_TX_HEAD_WB_H(_channel)	MGB_DMA_REG(0x0D50, _channel) /* head Writeback */
145 #define MGB_DMA_TX_HEAD_WB_L(_channel)	MGB_DMA_REG(0x0D54, _channel)
146 #define MGB_DMA_TX_HEAD(_channel)	MGB_DMA_REG(0x0D58, _channel)
147 #define MGB_DMA_TX_TAIL(_channel)	MGB_DMA_REG(0x0D5C, _channel)
148 
149 #define MGB_DMA_RX_CONFIG0(_channel)	MGB_DMA_REG(0x0C40, _channel)
150 #define MGB_DMA_RX_CONFIG1(_channel)	MGB_DMA_REG(0x0C44, _channel)
151 #define MGB_DMA_RX_BASE_H(_channel)	MGB_DMA_REG(0x0C48, _channel)
152 #define MGB_DMA_RX_BASE_L(_channel)	MGB_DMA_REG(0x0C4C, _channel)
153 #define MGB_DMA_RX_HEAD_WB_H(_channel)	MGB_DMA_REG(0x0C50, _channel) /* head Writeback */
154 #define MGB_DMA_RX_HEAD_WB_L(_channel)	MGB_DMA_REG(0x0C54, _channel)
155 #define MGB_DMA_RX_HEAD(_channel)	MGB_DMA_REG(0x0C58, _channel)
156 #define MGB_DMA_RX_TAIL(_channel)	MGB_DMA_REG(0x0C5C, _channel)
157 
158 #define MGB_DMA_RING_LEN_MASK		0xFFFF
159 #define MGB_DMA_IOC_ENBL		0x10000000
160 #define MGB_DMA_HEAD_WB_LS_ENBL		0x20000000
161 #define MGB_DMA_HEAD_WB_ENBL		(1 << 5)
162 #define MGB_DMA_RING_PAD_MASK		0x03000000
163 #define MGB_DMA_RING_PAD_0		0x00000000
164 #define MGB_DMA_RING_PAD_2		0x02000000
165 
166 #define MGB_DESC_CTL_OWN		(1 << 15)
167 #define MGB_DESC_CTL_FCS		(1 << 17)
168 #define MGB_DESC_CTL_IOC		(1 << 26)
169 #define MGB_TX_DESC_CTL_LS		(1 << 28)
170 #define MGB_TX_DESC_CTL_FS		(1 << 29)
171 #define MGB_RX_DESC_CTL_LS		(1 << 30)
172 #define MGB_RX_DESC_CTL_FS		(1 << 31)
173 #define MGB_DESC_CTL_BUFLEN_MASK	(0x0000FFFF)
174 #define MGB_DESC_STS_BUFLEN_MASK	(0x00003FFF)
175 #define MGB_DESC_FRAME_LEN_MASK		(0x3FFF0000)
176 #define MGB_DESC_GET_FRAME_LEN(_desc)	\
177 	(((_desc)->ctl & MGB_DESC_FRAME_LEN_MASK) >> 16)
178 
179 #define MGB_NEXT_RING_IDX(_idx)		(((_idx) == MGB_DMA_RING_SIZE - 1) ? 0 : ((_idx) + 1))
180 #define MGB_PREV_RING_IDX(_idx)		(((_idx) == 0) ? (MGB_DMA_RING_SIZE - 1) : ((_idx) - 1))
181 #define MGB_RING_SPACE(_sc)		\
182 	((((_sc)->tx_ring_data.last_head - (_sc)->tx_ring_data.last_tail - 1) \
183 	 + MGB_DMA_RING_SIZE ) % MGB_DMA_RING_SIZE )
184 
185 /** PHY **/
186 #define MGB_MII_ACCESS			0x120
187 #define MGB_MII_DATA			0x124
188 #define MGB_MII_PHY_ADDR_MASK		0x1F
189 #define MGB_MII_PHY_ADDR_SHIFT		11
190 #define MGB_MII_REG_ADDR_MASK		0x1F
191 #define MGB_MII_REG_ADDR_SHIFT		6
192 #define MGB_MII_READ			0x0
193 #define MGB_MII_WRITE			0x2
194 #define MGB_MII_BUSY			0x1
195 
196 /** Interrupt registers **/
197 #define MGB_INTR_STS			0x780
198 #define MGB_INTR_SET			0x784 /* This triggers a particular interrupt */
199 #define MGB_INTR_ENBL_SET		0x788
200 #define MGB_INTR_STS_ANY		(0x1)
201 #define MGB_INTR_STS_RX(_channel)	(1 << (24 + (_channel)))
202 #define MGB_INTR_STS_RX_ANY		(0xF << 24)
203 #define MGB_INTR_STS_TX(_channel)	(1 << (16 + (_channel)))
204 #define MGB_INTR_STS_TX_ANY		(0xF << 16)
205 #define MGB_INTR_STS_TEST		(1 << 9)
206 #define MGB_INTR_ENBL_CLR		0x78C
207 
208 #define MGB_INTR_VEC_ENBL_SET		0x794
209 #define MGB_INTR_VEC_ENBL_CLR		0x798
210 #define MGB_INTR_VEC_ENBL_AUTO_CLR	0x79C
211 #define MGB_INTR_VEC_RX_MAP		0x7A0
212 #define MGB_INTR_VEC_TX_MAP		0x7A4
213 #define MGB_INTR_VEC_OTHER_MAP		0x7A8
214 #define MGB_INTR_VEC_MAP(_vsts, _ch)	((_vsts) << ((_ch) << 2))
215 #define MGB_INTR_VEC_STS(_v)		(1 << (_v))
216 #define MGB_INTR_RX_VEC_STS(_qid)	MGB_INTR_VEC_STS((_qid) + 1)
217 
218 #define MGB_STS_OK			( 0 )
219 #define MGB_STS_TIMEOUT 		(-1 )
220 
221 #define CSR_READ_BYTE(sc, reg)		\
222 	bus_read_1((sc)->regs, reg)
223 
224 #define CSR_WRITE_BYTE(sc, reg, val)	\
225 	bus_write_1((sc)->regs, reg, val)
226 
227 #define CSR_UPDATE_BYTE(sc, reg, val)	\
228 	CSR_WRITE_BYTE(sc, reg, CSR_READ_BYTE(sc, reg) | (val))
229 
230 #define CSR_READ_REG(sc, reg)		\
231 	bus_read_4((sc)->regs, reg)
232 
233 #define CSR_WRITE_REG(sc, reg, val)	\
234 	bus_write_4((sc)->regs, reg, val)
235 
236 #define CSR_CLEAR_REG(sc, reg, bits)	\
237 	CSR_WRITE_REG(sc, reg, CSR_READ_REG(sc, reg) & ~(bits))
238 
239 #define CSR_UPDATE_REG(sc, reg, val)	\
240 	CSR_WRITE_REG(sc, reg, CSR_READ_REG(sc, reg) | (val))
241 
242 #define CSR_READ_2_BYTES(sc, reg)	\
243 	bus_read_2((sc)->regs, reg)
244 
245 #define CSR_READ_REG_BYTES(sc, reg, dest, cnt)	\
246 	bus_read_region_1((sc)->regs, reg, dest, cnt)
247 
248 #define CSR_TRANSLATE_ADDR_LOW32(addr)		((uint64_t) (addr) & 0xFFFFFFFF)
249 #define CSR_TRANSLATE_ADDR_HIGH32(addr)		((uint64_t) (addr) >> 32)
250 
251 struct mgb_irq {
252 	struct resource			*res;
253 	void				*handler;
254 };
255 
256 enum mgb_dmac_cmd { DMAC_RESET, DMAC_START, DMAC_STOP };
257 enum mgb_fct_cmd { FCT_RESET, FCT_ENABLE, FCT_DISABLE };
258 
259 struct mgb_ring_desc_addr {
260 	uint32_t				low;
261 	uint32_t				high;
262 } __packed;
263 
264 /* TODO: With descriptor bit information
265  * this could be done without masks etc.
266  * (using bitwise structs like vmx,
267  * would have to separate rx/tx ring desc
268  * definitions)
269  */
270 struct mgb_ring_desc {
271 	uint32_t				ctl; /* data0 */
272 	struct mgb_ring_desc_addr		addr; /* data(1|2) */
273 	uint32_t				sts; /* data3 */
274 } __packed;
275 
276 #if 0
277 struct mgb_ring_info {
278 	uint32_t				head_wb;
279 	struct mgb_ring_desc			*ring;
280 }
281 #endif
282 #define MGB_HEAD_WB_PTR(_ring_info_ptr)		\
283 	((uint32_t *)(_ring_info_ptr))
284 
285 #define MGB_RING_PTR(_ring_info_ptr)		\
286 	((struct mgb_ring_desc *)(MGB_HEAD_WB_PTR(_ring_info_ptr) + 1))
287 
288 struct mgb_ring_data {
289 	uint32_t			*head_wb;
290 	struct mgb_ring_desc		*ring;
291 
292 	bus_addr_t			 head_wb_bus_addr;
293 	bus_addr_t			 ring_bus_addr;
294 
295 	uint32_t			 last_head;
296 	uint32_t			 last_tail;
297 };
298 
299 struct mgb_softc {
300 	if_ctx_t			 ctx;
301 	device_t			 dev;
302 
303 	struct resource			*regs;
304 
305 	struct resource			*pba;
306 	struct if_irq			 admin_irq;
307 	struct if_irq			 rx_irq;
308 
309 	bool 				 isr_test_flag;
310 
311 	device_t			 miibus;
312 	int				 link_state;
313 	int				 baudrate;
314 
315 	int				 if_flags;
316 	int				 ethaddr;
317 	int				 flags;
318 
319 	struct mtx			 mtx;
320 	struct callout			 watchdog;
321 	int				 timer;
322 
323 	bus_dma_tag_t			 dma_parent_tag;
324 	struct mgb_ring_data		 rx_ring_data;
325 	struct mgb_ring_data		 tx_ring_data;
326 
327 };
328 
329 #endif /* _IF_MGB_H_ */
330