xref: /openbsd-src/sys/dev/fdt/if_dwge.c (revision 8550894424f8a4aa4aafb6cd57229dd6ed7cd9dd)
1 /*	$OpenBSD: if_dwge.c,v 1.14 2023/01/14 17:02:57 kettenis Exp $	*/
2 /*
3  * Copyright (c) 2008, 2019 Mark Kettenis <kettenis@openbsd.org>
4  * Copyright (c) 2017 Patrick Wildt <patrick@blueri.se>
5  *
6  * Permission to use, copy, modify, and distribute this software for any
7  * purpose with or without fee is hereby granted, provided that the above
8  * copyright notice and this permission notice appear in all copies.
9  *
10  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17  */
18 
19 /*
20  * Driver for the Synopsys Designware ethernet controller.
21  */
22 
23 #include "bpfilter.h"
24 
25 #include <sys/param.h>
26 #include <sys/systm.h>
27 #include <sys/device.h>
28 #include <sys/kernel.h>
29 #include <sys/malloc.h>
30 #include <sys/mbuf.h>
31 #include <sys/queue.h>
32 #include <sys/socket.h>
33 #include <sys/sockio.h>
34 #include <sys/timeout.h>
35 
36 #include <machine/bus.h>
37 #include <machine/fdt.h>
38 
39 #include <net/if.h>
40 #include <net/if_media.h>
41 
42 #include <dev/ofw/openfirm.h>
43 #include <dev/ofw/ofw_clock.h>
44 #include <dev/ofw/ofw_gpio.h>
45 #include <dev/ofw/ofw_misc.h>
46 #include <dev/ofw/ofw_pinctrl.h>
47 #include <dev/ofw/ofw_regulator.h>
48 #include <dev/ofw/fdt.h>
49 
50 #include <dev/mii/mii.h>
51 #include <dev/mii/miivar.h>
52 
53 #if NBPFILTER > 0
54 #include <net/bpf.h>
55 #endif
56 
57 #include <netinet/in.h>
58 #include <netinet/if_ether.h>
59 
60 /* Registers */
61 
62 #define GMAC_MAC_CONF		0x0000
63 #define  GMAC_MAC_CONF_JD		(1 << 22)
64 #define  GMAC_MAC_CONF_BE		(1 << 21)
65 #define  GMAC_MAC_CONF_DCRS		(1 << 16)
66 #define  GMAC_MAC_CONF_PS		(1 << 15)
67 #define  GMAC_MAC_CONF_FES		(1 << 14)
68 #define  GMAC_MAC_CONF_LM		(1 << 12)
69 #define  GMAC_MAC_CONF_DM		(1 << 11)
70 #define  GMAC_MAC_CONF_TE		(1 << 3)
71 #define  GMAC_MAC_CONF_RE		(1 << 2)
72 #define GMAC_MAC_FRM_FILT	0x0004
73 #define  GMAC_MAC_FRM_FILT_PM		(1 << 4)
74 #define  GMAC_MAC_FRM_FILT_HMC		(1 << 2)
75 #define  GMAC_MAC_FRM_FILT_PR		(1 << 0)
76 #define GMAC_HASH_TAB_HI	0x0008
77 #define GMAC_HASH_TAB_LO	0x000c
78 #define GMAC_GMII_ADDR		0x0010
79 #define  GMAC_GMII_ADDR_PA_SHIFT	11
80 #define  GMAC_GMII_ADDR_GR_SHIFT	6
81 #define  GMAC_GMII_ADDR_CR_SHIFT	2
82 #define  GMAC_GMII_ADDR_CR_MASK		0xf
83 #define  GMAC_GMII_ADDR_CR_DIV_42	0
84 #define  GMAC_GMII_ADDR_CR_DIV_62	1
85 #define  GMAC_GMII_ADDR_CR_DIV_16	2
86 #define  GMAC_GMII_ADDR_CR_DIV_26	3
87 #define  GMAC_GMII_ADDR_CR_DIV_102	4
88 #define  GMAC_GMII_ADDR_CR_DIV_124	5
89 #define  GMAC_GMII_ADDR_GW		(1 << 1)
90 #define  GMAC_GMII_ADDR_GB		(1 << 0)
91 #define GMAC_GMII_DATA		0x0014
92 #define GMAC_VERSION		0x0020
93 #define  GMAC_VERSION_SNPS_MASK		0xff
94 #define GMAC_INT_MASK		0x003c
95 #define  GMAC_INT_MASK_LPIIM		(1 << 10)
96 #define  GMAC_INT_MASK_PIM		(1 << 3)
97 #define  GMAC_INT_MASK_RIM		(1 << 0)
98 #define GMAC_MAC_ADDR0_HI	0x0040
99 #define GMAC_MAC_ADDR0_LO	0x0044
100 #define GMAC_MMC_RX_INT_MSK	0x010c
101 #define GMAC_MMC_TX_INT_MSK	0x0110
102 #define GMAC_MMC_IPC_INT_MSK	0x0200
103 #define GMAC_BUS_MODE		0x1000
104 #define  GMAC_BUS_MODE_8XPBL		(1 << 24)
105 #define  GMAC_BUS_MODE_USP		(1 << 23)
106 #define  GMAC_BUS_MODE_RPBL_MASK	(0x3f << 17)
107 #define  GMAC_BUS_MODE_RPBL_SHIFT	17
108 #define  GMAC_BUS_MODE_FB		(1 << 16)
109 #define  GMAC_BUS_MODE_PBL_MASK		(0x3f << 8)
110 #define  GMAC_BUS_MODE_PBL_SHIFT	8
111 #define  GMAC_BUS_MODE_SWR		(1 << 0)
112 #define GMAC_TX_POLL_DEMAND	0x1004
113 #define GMAC_RX_DESC_LIST_ADDR	0x100c
114 #define GMAC_TX_DESC_LIST_ADDR	0x1010
115 #define GMAC_STATUS		0x1014
116 #define  GMAC_STATUS_RI			(1 << 6)
117 #define  GMAC_STATUS_TU			(1 << 2)
118 #define  GMAC_STATUS_TI			(1 << 0)
119 #define GMAC_OP_MODE		0x1018
120 #define  GMAC_OP_MODE_RSF		(1 << 25)
121 #define  GMAC_OP_MODE_TSF		(1 << 21)
122 #define  GMAC_OP_MODE_FTF		(1 << 20)
123 #define  GMAC_OP_MODE_TTC_MASK		(0x7 << 14)
124 #define  GMAC_OP_MODE_TTC_64		(0x0 << 14)
125 #define  GMAC_OP_MODE_TTC_128		(0x1 << 14)
126 #define  GMAC_OP_MODE_ST		(1 << 13)
127 #define  GMAC_OP_MODE_RTC_MASK		(0x3 << 3)
128 #define  GMAC_OP_MODE_RTC_64		(0x0 << 3)
129 #define  GMAC_OP_MODE_RTC_128		(0x3 << 3)
130 #define  GMAC_OP_MODE_OSF		(1 << 2)
131 #define  GMAC_OP_MODE_SR		(1 << 1)
132 #define GMAC_INT_ENA		0x101c
133 #define  GMAC_INT_ENA_NIE		(1 << 16)
134 #define  GMAC_INT_ENA_RIE		(1 << 6)
135 #define  GMAC_INT_ENA_TUE		(1 << 2)
136 #define  GMAC_INT_ENA_TIE		(1 << 0)
137 #define GMAC_AXI_BUS_MODE	0x1028
138 #define  GMAC_AXI_BUS_MODE_WR_OSR_LMT_MASK	(0xf << 20)
139 #define  GMAC_AXI_BUS_MODE_WR_OSR_LMT_SHIFT	20
140 #define  GMAC_AXI_BUS_MODE_RD_OSR_LMT_MASK	(0xf << 16)
141 #define  GMAC_AXI_BUS_MODE_RD_OSR_LMT_SHIFT	16
142 #define  GMAC_AXI_BUS_MODE_BLEN_256		(1 << 7)
143 #define  GMAC_AXI_BUS_MODE_BLEN_128		(1 << 6)
144 #define  GMAC_AXI_BUS_MODE_BLEN_64		(1 << 5)
145 #define  GMAC_AXI_BUS_MODE_BLEN_32		(1 << 4)
146 #define  GMAC_AXI_BUS_MODE_BLEN_16		(1 << 3)
147 #define  GMAC_AXI_BUS_MODE_BLEN_8		(1 << 2)
148 #define  GMAC_AXI_BUS_MODE_BLEN_4		(1 << 1)
149 #define GMAC_HW_FEATURE		0x1058
150 #define  GMAC_HW_FEATURE_ENHDESSEL	(1 << 24)
151 
152 /*
153  * DWGE descriptors.
154  */
155 
156 struct dwge_desc {
157 	uint32_t sd_status;
158 	uint32_t sd_len;
159 	uint32_t sd_addr;
160 	uint32_t sd_next;
161 };
162 
163 /* Tx status bits. */
164 #define TDES0_DB		(1 << 0)
165 #define TDES0_UF		(1 << 1)
166 #define TDES0_ED		(1 << 2)
167 #define TDES0_CC_MASK		(0xf << 3)
168 #define TDES0_CC_SHIFT		3
169 #define TDES0_EC		(1 << 8)
170 #define TDES0_LC		(1 << 9)
171 #define TDES0_NC		(1 << 10)
172 #define TDES0_PCE		(1 << 12)
173 #define TDES0_JT		(1 << 14)
174 #define TDES0_IHE		(1 << 16)
175 #define TDES0_OWN		(1 << 31)
176 
177 #define ETDES0_TCH		(1 << 20)
178 #define ETDES0_FS		(1 << 28)
179 #define ETDES0_LS		(1 << 29)
180 #define ETDES0_IC		(1 << 30)
181 
182 /* Rx status bits */
183 #define RDES0_PE		(1 << 0)
184 #define RDES0_CE		(1 << 1)
185 #define RDES0_RE		(1 << 3)
186 #define RDES0_RWT		(1 << 4)
187 #define RDES0_FT		(1 << 5)
188 #define RDES0_LC		(1 << 6)
189 #define RDES0_IPC		(1 << 7)
190 #define RDES0_LS		(1 << 8)
191 #define RDES0_FS		(1 << 9)
192 #define RDES0_OE		(1 << 11)
193 #define RDES0_SAF		(1 << 13)
194 #define RDES0_DE		(1 << 14)
195 #define RDES0_FL_MASK		0x3fff
196 #define RDES0_FL_SHIFT		16
197 #define RDES0_AFM		(1 << 30)
198 #define RDES0_OWN		(1 << 31)
199 
200 /* Tx size bits */
201 #define TDES1_TBS1		(0xfff << 0)
202 #define TDES1_TCH		(1 << 24)
203 #define TDES1_DC		(1 << 26)
204 #define TDES1_CIC_MASK		(0x3 << 27)
205 #define TDES1_CIC_IP		(1 << 27)
206 #define TDES1_CIC_NO_PSE	(2 << 27)
207 #define TDES1_CIC_FULL		(3 << 27)
208 #define TDES1_FS		(1 << 29)
209 #define TDES1_LS		(1 << 30)
210 #define TDES1_IC		(1 << 31)
211 
212 /* Rx size bits */
213 #define RDES1_RBS1		(0xfff << 0)
214 #define RDES1_RCH		(1 << 24)
215 #define RDES1_DIC		(1 << 31)
216 
217 #define ERDES1_RCH		(1 << 14)
218 
219 struct dwge_buf {
220 	bus_dmamap_t	tb_map;
221 	struct mbuf	*tb_m;
222 };
223 
224 #define DWGE_NTXDESC	512
225 #define DWGE_NTXSEGS	16
226 
227 #define DWGE_NRXDESC	512
228 
229 struct dwge_dmamem {
230 	bus_dmamap_t		tdm_map;
231 	bus_dma_segment_t	tdm_seg;
232 	size_t			tdm_size;
233 	caddr_t			tdm_kva;
234 };
235 #define DWGE_DMA_MAP(_tdm)	((_tdm)->tdm_map)
236 #define DWGE_DMA_LEN(_tdm)	((_tdm)->tdm_size)
237 #define DWGE_DMA_DVA(_tdm)	((_tdm)->tdm_map->dm_segs[0].ds_addr)
238 #define DWGE_DMA_KVA(_tdm)	((void *)(_tdm)->tdm_kva)
239 
240 struct dwge_softc {
241 	struct device		sc_dev;
242 	int			sc_node;
243 	bus_space_tag_t		sc_iot;
244 	bus_space_handle_t	sc_ioh;
245 	bus_dma_tag_t		sc_dmat;
246 	void			*sc_ih;
247 
248 	struct arpcom		sc_ac;
249 #define sc_lladdr	sc_ac.ac_enaddr
250 	struct mii_data		sc_mii;
251 #define sc_media	sc_mii.mii_media
252 	int			sc_link;
253 	int			sc_phyloc;
254 	int			sc_force_thresh_dma_mode;
255 	int			sc_enh_desc;
256 
257 	struct dwge_dmamem	*sc_txring;
258 	struct dwge_buf		*sc_txbuf;
259 	struct dwge_desc	*sc_txdesc;
260 	int			sc_tx_prod;
261 	int			sc_tx_cons;
262 
263 	struct dwge_dmamem	*sc_rxring;
264 	struct dwge_buf		*sc_rxbuf;
265 	struct dwge_desc	*sc_rxdesc;
266 	int			sc_rx_prod;
267 	struct if_rxring	sc_rx_ring;
268 	int			sc_rx_cons;
269 
270 	struct timeout		sc_tick;
271 	struct timeout		sc_rxto;
272 
273 	uint32_t		sc_clk;
274 
275 	bus_size_t		sc_clk_sel;
276 	uint32_t		sc_clk_sel_125;
277 	uint32_t		sc_clk_sel_25;
278 	uint32_t		sc_clk_sel_2_5;
279 };
280 
281 #define DEVNAME(_s)	((_s)->sc_dev.dv_xname)
282 
283 int	dwge_match(struct device *, void *, void *);
284 void	dwge_attach(struct device *, struct device *, void *);
285 void	dwge_setup_allwinner(struct dwge_softc *);
286 void	dwge_setup_rockchip(struct dwge_softc *);
287 
288 const struct cfattach dwge_ca = {
289 	sizeof(struct dwge_softc), dwge_match, dwge_attach
290 };
291 
292 struct cfdriver dwge_cd = {
293 	NULL, "dwge", DV_IFNET
294 };
295 
296 void	dwge_reset_phy(struct dwge_softc *);
297 
298 uint32_t dwge_read(struct dwge_softc *, bus_addr_t);
299 void	dwge_write(struct dwge_softc *, bus_addr_t, uint32_t);
300 
301 int	dwge_ioctl(struct ifnet *, u_long, caddr_t);
302 void	dwge_start(struct ifqueue *);
303 void	dwge_watchdog(struct ifnet *);
304 
305 int	dwge_media_change(struct ifnet *);
306 void	dwge_media_status(struct ifnet *, struct ifmediareq *);
307 
308 int	dwge_mii_readreg(struct device *, int, int);
309 void	dwge_mii_writereg(struct device *, int, int, int);
310 void	dwge_mii_statchg(struct device *);
311 
312 void	dwge_lladdr_read(struct dwge_softc *, uint8_t *);
313 void	dwge_lladdr_write(struct dwge_softc *);
314 
315 void	dwge_tick(void *);
316 void	dwge_rxtick(void *);
317 
318 int	dwge_intr(void *);
319 void	dwge_tx_proc(struct dwge_softc *);
320 void	dwge_rx_proc(struct dwge_softc *);
321 
322 void	dwge_up(struct dwge_softc *);
323 void	dwge_down(struct dwge_softc *);
324 void	dwge_iff(struct dwge_softc *);
325 int	dwge_encap(struct dwge_softc *, struct mbuf *, int *, int *);
326 
327 void	dwge_reset(struct dwge_softc *);
328 void	dwge_stop_dma(struct dwge_softc *);
329 
330 struct dwge_dmamem *
331 	dwge_dmamem_alloc(struct dwge_softc *, bus_size_t, bus_size_t);
332 void	dwge_dmamem_free(struct dwge_softc *, struct dwge_dmamem *);
333 struct mbuf *dwge_alloc_mbuf(struct dwge_softc *, bus_dmamap_t);
334 void	dwge_fill_rx_ring(struct dwge_softc *);
335 
336 int
337 dwge_match(struct device *parent, void *cfdata, void *aux)
338 {
339 	struct fdt_attach_args *faa = aux;
340 
341 	return (OF_is_compatible(faa->fa_node, "allwinner,sun7i-a20-gmac") ||
342 	    OF_is_compatible(faa->fa_node, "amlogic,meson-axg-dwmac") ||
343 	    OF_is_compatible(faa->fa_node, "amlogic,meson-g12a-dwmac") ||
344 	    OF_is_compatible(faa->fa_node, "rockchip,rk3288-gmac") ||
345 	    OF_is_compatible(faa->fa_node, "rockchip,rk3308-mac") ||
346 	    OF_is_compatible(faa->fa_node, "rockchip,rk3328-gmac") ||
347 	    OF_is_compatible(faa->fa_node, "rockchip,rk3399-gmac") ||
348 	    OF_is_compatible(faa->fa_node, "snps,dwmac"));
349 }
350 
351 void
352 dwge_attach(struct device *parent, struct device *self, void *aux)
353 {
354 	struct dwge_softc *sc = (void *)self;
355 	struct fdt_attach_args *faa = aux;
356 	struct ifnet *ifp;
357 	uint32_t phy, phy_supply;
358 	uint32_t axi_config;
359 	uint32_t mode, pbl;
360 	uint32_t version;
361 	uint32_t feature;
362 	int node;
363 
364 	sc->sc_node = faa->fa_node;
365 	sc->sc_iot = faa->fa_iot;
366 	if (bus_space_map(sc->sc_iot, faa->fa_reg[0].addr,
367 	    faa->fa_reg[0].size, 0, &sc->sc_ioh)) {
368 		printf("%s: cannot map registers\n", self->dv_xname);
369 		return;
370 	}
371 	sc->sc_dmat = faa->fa_dmat;
372 
373 	/* Lookup PHY. */
374 	phy = OF_getpropint(faa->fa_node, "phy", 0);
375 	if (phy == 0)
376 		phy = OF_getpropint(faa->fa_node, "phy-handle", 0);
377 	node = OF_getnodebyphandle(phy);
378 	if (node)
379 		sc->sc_phyloc = OF_getpropint(node, "reg", MII_PHY_ANY);
380 	else
381 		sc->sc_phyloc = MII_PHY_ANY;
382 
383 	pinctrl_byname(faa->fa_node, "default");
384 
385 	/* Enable clocks. */
386 	clock_set_assigned(faa->fa_node);
387 	clock_enable(faa->fa_node, "stmmaceth");
388 	reset_deassert(faa->fa_node, "stmmaceth");
389 	if (OF_is_compatible(faa->fa_node, "rockchip,rk3288-gmac") ||
390 	    OF_is_compatible(faa->fa_node, "rockchip,rk3308-mac") ||
391 	    OF_is_compatible(faa->fa_node, "rockchip,rk3328-gmac") ||
392 	    OF_is_compatible(faa->fa_node, "rockchip,rk3399-gmac")) {
393 		clock_enable(faa->fa_node, "mac_clk_rx");
394 		clock_enable(faa->fa_node, "mac_clk_tx");
395 		clock_enable(faa->fa_node, "aclk_mac");
396 		clock_enable(faa->fa_node, "pclk_mac");
397 	}
398 	delay(5000);
399 
400 	version = dwge_read(sc, GMAC_VERSION);
401 	printf(": rev 0x%02x", version & GMAC_VERSION_SNPS_MASK);
402 
403 	if ((version & GMAC_VERSION_SNPS_MASK) > 0x35) {
404 		feature = dwge_read(sc, GMAC_HW_FEATURE);
405 		if (feature & GMAC_HW_FEATURE_ENHDESSEL)
406 			sc->sc_enh_desc = 1;
407 	}
408 
409 	/* Power up PHY. */
410 	phy_supply = OF_getpropint(faa->fa_node, "phy-supply", 0);
411 	if (phy_supply)
412 		regulator_enable(phy_supply);
413 
414 	/* Reset PHY */
415 	dwge_reset_phy(sc);
416 
417 	sc->sc_clk = clock_get_frequency(faa->fa_node, "stmmaceth");
418 	if (sc->sc_clk > 250000000)
419 		sc->sc_clk = GMAC_GMII_ADDR_CR_DIV_124;
420 	else if (sc->sc_clk > 150000000)
421 		sc->sc_clk = GMAC_GMII_ADDR_CR_DIV_102;
422 	else if (sc->sc_clk > 100000000)
423 		sc->sc_clk = GMAC_GMII_ADDR_CR_DIV_62;
424 	else if (sc->sc_clk > 60000000)
425 		sc->sc_clk = GMAC_GMII_ADDR_CR_DIV_42;
426 	else if (sc->sc_clk > 35000000)
427 		sc->sc_clk = GMAC_GMII_ADDR_CR_DIV_26;
428 	else
429 		sc->sc_clk = GMAC_GMII_ADDR_CR_DIV_16;
430 
431 	if (OF_getprop(faa->fa_node, "local-mac-address",
432 	    &sc->sc_lladdr, ETHER_ADDR_LEN) != ETHER_ADDR_LEN)
433 		dwge_lladdr_read(sc, sc->sc_lladdr);
434 	printf(", address %s\n", ether_sprintf(sc->sc_lladdr));
435 
436 	timeout_set(&sc->sc_tick, dwge_tick, sc);
437 	timeout_set(&sc->sc_rxto, dwge_rxtick, sc);
438 
439 	ifp = &sc->sc_ac.ac_if;
440 	ifp->if_softc = sc;
441 	ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
442 	ifp->if_xflags = IFXF_MPSAFE;
443 	ifp->if_ioctl = dwge_ioctl;
444 	ifp->if_qstart = dwge_start;
445 	ifp->if_watchdog = dwge_watchdog;
446 	ifq_set_maxlen(&ifp->if_snd, DWGE_NTXDESC - 1);
447 	bcopy(sc->sc_dev.dv_xname, ifp->if_xname, IFNAMSIZ);
448 
449 	ifp->if_capabilities = IFCAP_VLAN_MTU;
450 
451 	sc->sc_mii.mii_ifp = ifp;
452 	sc->sc_mii.mii_readreg = dwge_mii_readreg;
453 	sc->sc_mii.mii_writereg = dwge_mii_writereg;
454 	sc->sc_mii.mii_statchg = dwge_mii_statchg;
455 
456 	ifmedia_init(&sc->sc_media, 0, dwge_media_change, dwge_media_status);
457 
458 	/* Do hardware specific initializations. */
459 	if (OF_is_compatible(faa->fa_node, "allwinner,sun7i-a20-gmac"))
460 		dwge_setup_allwinner(sc);
461 	if (OF_is_compatible(faa->fa_node, "rockchip,rk3288-gmac") ||
462 	    OF_is_compatible(faa->fa_node, "rockchip,rk3308-mac") ||
463 	    OF_is_compatible(faa->fa_node, "rockchip,rk3328-gmac") ||
464 	    OF_is_compatible(faa->fa_node, "rockchip,rk3399-gmac"))
465 		dwge_setup_rockchip(sc);
466 
467 	if (OF_getpropbool(faa->fa_node, "snps,force_thresh_dma_mode"))
468 		sc->sc_force_thresh_dma_mode = 1;
469 
470 	dwge_reset(sc);
471 
472 	/* Configure MAC. */
473 	dwge_write(sc, GMAC_MAC_CONF, dwge_read(sc, GMAC_MAC_CONF) |
474 	    GMAC_MAC_CONF_JD | GMAC_MAC_CONF_BE | GMAC_MAC_CONF_DCRS);
475 
476 	/* Configure DMA engine. */
477 	mode = dwge_read(sc, GMAC_BUS_MODE);
478 	mode |= GMAC_BUS_MODE_USP;
479 	if (!OF_getpropbool(faa->fa_node, "snps,no-pbl-x8"))
480 		mode |= GMAC_BUS_MODE_8XPBL;
481 	mode &= ~(GMAC_BUS_MODE_RPBL_MASK | GMAC_BUS_MODE_PBL_MASK);
482 	pbl = OF_getpropint(faa->fa_node, "snps,pbl", 8);
483 	mode |= pbl << GMAC_BUS_MODE_RPBL_SHIFT;
484 	mode |= pbl << GMAC_BUS_MODE_PBL_SHIFT;
485 	if (OF_getpropbool(faa->fa_node, "snps,fixed-burst"))
486 		mode |= GMAC_BUS_MODE_FB;
487 	dwge_write(sc, GMAC_BUS_MODE, mode);
488 
489 	/* Configure AXI master. */
490 	axi_config = OF_getpropint(faa->fa_node, "snps,axi-config", 0);
491 	node = OF_getnodebyphandle(axi_config);
492 	if (node) {
493 		uint32_t blen[7] = { 0 };
494 		uint32_t osr_lmt;
495 		int i;
496 
497 		mode = dwge_read(sc, GMAC_AXI_BUS_MODE);
498 
499 		osr_lmt = OF_getpropint(node, "snps,wr_osr_lmt", 1);
500 		mode &= ~GMAC_AXI_BUS_MODE_WR_OSR_LMT_MASK;
501 		mode |= (osr_lmt << GMAC_AXI_BUS_MODE_WR_OSR_LMT_SHIFT);
502 		osr_lmt = OF_getpropint(node, "snps,rd_osr_lmt", 1);
503 		mode &= ~GMAC_AXI_BUS_MODE_RD_OSR_LMT_MASK;
504 		mode |= (osr_lmt << GMAC_AXI_BUS_MODE_RD_OSR_LMT_SHIFT);
505 
506 		OF_getpropintarray(node, "snps,blen", blen, sizeof(blen));
507 		for (i = 0; i < nitems(blen); i++) {
508 			switch (blen[i]) {
509 			case 256:
510 				mode |= GMAC_AXI_BUS_MODE_BLEN_256;
511 				break;
512 			case 128:
513 				mode |= GMAC_AXI_BUS_MODE_BLEN_128;
514 				break;
515 			case 64:
516 				mode |= GMAC_AXI_BUS_MODE_BLEN_64;
517 				break;
518 			case 32:
519 				mode |= GMAC_AXI_BUS_MODE_BLEN_32;
520 				break;
521 			case 16:
522 				mode |= GMAC_AXI_BUS_MODE_BLEN_16;
523 				break;
524 			case 8:
525 				mode |= GMAC_AXI_BUS_MODE_BLEN_8;
526 				break;
527 			case 4:
528 				mode |= GMAC_AXI_BUS_MODE_BLEN_4;
529 				break;
530 			}
531 		}
532 
533 		dwge_write(sc, GMAC_AXI_BUS_MODE, mode);
534 	}
535 
536 	mii_attach(self, &sc->sc_mii, 0xffffffff, sc->sc_phyloc,
537 	    (sc->sc_phyloc == MII_PHY_ANY) ? 0 : MII_OFFSET_ANY, 0);
538 	if (LIST_FIRST(&sc->sc_mii.mii_phys) == NULL) {
539 		printf("%s: no PHY found!\n", sc->sc_dev.dv_xname);
540 		ifmedia_add(&sc->sc_media, IFM_ETHER|IFM_MANUAL, 0, NULL);
541 		ifmedia_set(&sc->sc_media, IFM_ETHER|IFM_MANUAL);
542 	} else
543 		ifmedia_set(&sc->sc_media, IFM_ETHER|IFM_AUTO);
544 
545 	if_attach(ifp);
546 	ether_ifattach(ifp);
547 
548 	/* Disable interrupts. */
549 	dwge_write(sc, GMAC_INT_ENA, 0);
550 	dwge_write(sc, GMAC_INT_MASK,
551 	    GMAC_INT_MASK_LPIIM | GMAC_INT_MASK_PIM | GMAC_INT_MASK_RIM);
552 	dwge_write(sc, GMAC_MMC_RX_INT_MSK, 0xffffffff);
553 	dwge_write(sc, GMAC_MMC_TX_INT_MSK, 0xffffffff);
554 	dwge_write(sc, GMAC_MMC_IPC_INT_MSK, 0xffffffff);
555 
556 	sc->sc_ih = fdt_intr_establish(faa->fa_node, IPL_NET | IPL_MPSAFE,
557 	    dwge_intr, sc, sc->sc_dev.dv_xname);
558 	if (sc->sc_ih == NULL)
559 		printf("%s: can't establish interrupt\n", sc->sc_dev.dv_xname);
560 }
561 
562 void
563 dwge_reset_phy(struct dwge_softc *sc)
564 {
565 	uint32_t *gpio;
566 	uint32_t delays[3];
567 	int active = 1;
568 	int len;
569 
570 	len = OF_getproplen(sc->sc_node, "snps,reset-gpio");
571 	if (len <= 0)
572 		return;
573 
574 	gpio = malloc(len, M_TEMP, M_WAITOK);
575 
576 	/* Gather information. */
577 	OF_getpropintarray(sc->sc_node, "snps,reset-gpio", gpio, len);
578 	if (OF_getpropbool(sc->sc_node, "snps-reset-active-low"))
579 		active = 0;
580 	delays[0] = delays[1] = delays[2] = 0;
581 	OF_getpropintarray(sc->sc_node, "snps,reset-delays-us", delays,
582 	    sizeof(delays));
583 
584 	/* Perform reset sequence. */
585 	gpio_controller_config_pin(gpio, GPIO_CONFIG_OUTPUT);
586 	gpio_controller_set_pin(gpio, !active);
587 	delay(delays[0]);
588 	gpio_controller_set_pin(gpio, active);
589 	delay(delays[1]);
590 	gpio_controller_set_pin(gpio, !active);
591 	delay(delays[2]);
592 
593 	free(gpio, M_TEMP, len);
594 }
595 
596 uint32_t
597 dwge_read(struct dwge_softc *sc, bus_addr_t addr)
598 {
599 	return bus_space_read_4(sc->sc_iot, sc->sc_ioh, addr);
600 }
601 
602 void
603 dwge_write(struct dwge_softc *sc, bus_addr_t addr, uint32_t data)
604 {
605 	bus_space_write_4(sc->sc_iot, sc->sc_ioh, addr, data);
606 }
607 
608 void
609 dwge_lladdr_read(struct dwge_softc *sc, uint8_t *lladdr)
610 {
611 	uint32_t machi, maclo;
612 
613 	machi = dwge_read(sc, GMAC_MAC_ADDR0_HI);
614 	maclo = dwge_read(sc, GMAC_MAC_ADDR0_LO);
615 
616 	lladdr[0] = (maclo >> 0) & 0xff;
617 	lladdr[1] = (maclo >> 8) & 0xff;
618 	lladdr[2] = (maclo >> 16) & 0xff;
619 	lladdr[3] = (maclo >> 24) & 0xff;
620 	lladdr[4] = (machi >> 0) & 0xff;
621 	lladdr[5] = (machi >> 8) & 0xff;
622 }
623 
624 void
625 dwge_lladdr_write(struct dwge_softc *sc)
626 {
627 	dwge_write(sc, GMAC_MAC_ADDR0_HI,
628 	    sc->sc_lladdr[5] << 8 | sc->sc_lladdr[4] << 0);
629 	dwge_write(sc, GMAC_MAC_ADDR0_LO,
630 	    sc->sc_lladdr[3] << 24 | sc->sc_lladdr[2] << 16 |
631 	    sc->sc_lladdr[1] << 8 | sc->sc_lladdr[0] << 0);
632 }
633 
634 void
635 dwge_start(struct ifqueue *ifq)
636 {
637 	struct ifnet *ifp = ifq->ifq_if;
638 	struct dwge_softc *sc = ifp->if_softc;
639 	struct mbuf *m;
640 	int error, idx, left, used;
641 
642 	if (!(ifp->if_flags & IFF_RUNNING))
643 		return;
644 	if (ifq_is_oactive(&ifp->if_snd))
645 		return;
646 	if (ifq_empty(&ifp->if_snd))
647 		return;
648 	if (!sc->sc_link)
649 		return;
650 
651 	idx = sc->sc_tx_prod;
652 	left = sc->sc_tx_cons;
653 	if (left <= idx)
654 		left += DWGE_NTXDESC;
655 	left -= idx;
656 	used = 0;
657 
658 	for (;;) {
659 		if (used + DWGE_NTXSEGS + 1 > left) {
660 			ifq_set_oactive(ifq);
661 			break;
662 		}
663 
664 		m = ifq_dequeue(ifq);
665 		if (m == NULL)
666 			break;
667 
668 		error = dwge_encap(sc, m, &idx, &used);
669 		if (error == EFBIG) {
670 			m_freem(m); /* give up: drop it */
671 			ifp->if_oerrors++;
672 			continue;
673 		}
674 
675 #if NBPFILTER > 0
676 		if (ifp->if_bpf)
677 			bpf_mtap(ifp->if_bpf, m, BPF_DIRECTION_OUT);
678 #endif
679 	}
680 
681 	if (sc->sc_tx_prod != idx) {
682 		sc->sc_tx_prod = idx;
683 
684 		/* Set a timeout in case the chip goes out to lunch. */
685 		ifp->if_timer = 5;
686 
687 		dwge_write(sc, GMAC_TX_POLL_DEMAND, 0xffffffff);
688 	}
689 }
690 
691 int
692 dwge_ioctl(struct ifnet *ifp, u_long cmd, caddr_t addr)
693 {
694 	struct dwge_softc *sc = ifp->if_softc;
695 	struct ifreq *ifr = (struct ifreq *)addr;
696 	int error = 0, s;
697 
698 	s = splnet();
699 
700 	switch (cmd) {
701 	case SIOCSIFADDR:
702 		ifp->if_flags |= IFF_UP;
703 		/* FALLTHROUGH */
704 	case SIOCSIFFLAGS:
705 		if (ifp->if_flags & IFF_UP) {
706 			if (ifp->if_flags & IFF_RUNNING)
707 				error = ENETRESET;
708 			else
709 				dwge_up(sc);
710 		} else {
711 			if (ifp->if_flags & IFF_RUNNING)
712 				dwge_down(sc);
713 		}
714 		break;
715 
716 	case SIOCGIFMEDIA:
717 	case SIOCSIFMEDIA:
718 		error = ifmedia_ioctl(ifp, ifr, &sc->sc_media, cmd);
719 		break;
720 
721 	case SIOCGIFRXR:
722 		error = if_rxr_ioctl((struct if_rxrinfo *)ifr->ifr_data,
723 		    NULL, MCLBYTES, &sc->sc_rx_ring);
724 		break;
725 
726 	default:
727 		error = ether_ioctl(ifp, &sc->sc_ac, cmd, addr);
728 		break;
729 	}
730 
731 	if (error == ENETRESET) {
732 		if (ifp->if_flags & IFF_RUNNING)
733 			dwge_iff(sc);
734 		error = 0;
735 	}
736 
737 	splx(s);
738 	return (error);
739 }
740 
741 void
742 dwge_watchdog(struct ifnet *ifp)
743 {
744 	printf("%s\n", __func__);
745 }
746 
747 int
748 dwge_media_change(struct ifnet *ifp)
749 {
750 	struct dwge_softc *sc = ifp->if_softc;
751 
752 	if (LIST_FIRST(&sc->sc_mii.mii_phys))
753 		mii_mediachg(&sc->sc_mii);
754 
755 	return (0);
756 }
757 
758 void
759 dwge_media_status(struct ifnet *ifp, struct ifmediareq *ifmr)
760 {
761 	struct dwge_softc *sc = ifp->if_softc;
762 
763 	if (LIST_FIRST(&sc->sc_mii.mii_phys)) {
764 		mii_pollstat(&sc->sc_mii);
765 		ifmr->ifm_active = sc->sc_mii.mii_media_active;
766 		ifmr->ifm_status = sc->sc_mii.mii_media_status;
767 	}
768 }
769 
770 int
771 dwge_mii_readreg(struct device *self, int phy, int reg)
772 {
773 	struct dwge_softc *sc = (void *)self;
774 	int n;
775 
776 	dwge_write(sc, GMAC_GMII_ADDR,
777 	    sc->sc_clk << GMAC_GMII_ADDR_CR_SHIFT |
778 	    phy << GMAC_GMII_ADDR_PA_SHIFT |
779 	    reg << GMAC_GMII_ADDR_GR_SHIFT |
780 	    GMAC_GMII_ADDR_GB);
781 	for (n = 0; n < 1000; n++) {
782 		if ((dwge_read(sc, GMAC_GMII_ADDR) & GMAC_GMII_ADDR_GB) == 0)
783 			return dwge_read(sc, GMAC_GMII_DATA);
784 		delay(10);
785 	}
786 
787 	printf("%s: mii_read timeout\n", sc->sc_dev.dv_xname);
788 	return (0);
789 }
790 
791 void
792 dwge_mii_writereg(struct device *self, int phy, int reg, int val)
793 {
794 	struct dwge_softc *sc = (void *)self;
795 	int n;
796 
797 	dwge_write(sc, GMAC_GMII_DATA, val);
798 	dwge_write(sc, GMAC_GMII_ADDR,
799 	    sc->sc_clk << GMAC_GMII_ADDR_CR_SHIFT |
800 	    phy << GMAC_GMII_ADDR_PA_SHIFT |
801 	    reg << GMAC_GMII_ADDR_GR_SHIFT |
802 	    GMAC_GMII_ADDR_GW | GMAC_GMII_ADDR_GB);
803 	for (n = 0; n < 1000; n++) {
804 		if ((dwge_read(sc, GMAC_GMII_ADDR) & GMAC_GMII_ADDR_GB) == 0)
805 			return;
806 		delay(10);
807 	}
808 
809 	printf("%s: mii_write timeout\n", sc->sc_dev.dv_xname);
810 }
811 
812 void
813 dwge_mii_statchg(struct device *self)
814 {
815 	struct dwge_softc *sc = (void *)self;
816 	uint32_t conf;
817 
818 	conf = dwge_read(sc, GMAC_MAC_CONF);
819 	conf &= ~(GMAC_MAC_CONF_PS | GMAC_MAC_CONF_FES);
820 
821 	switch (IFM_SUBTYPE(sc->sc_mii.mii_media_active)) {
822 	case IFM_1000_SX:
823 	case IFM_1000_LX:
824 	case IFM_1000_CX:
825 	case IFM_1000_T:
826 		sc->sc_link = 1;
827 		break;
828 	case IFM_100_TX:
829 		conf |= GMAC_MAC_CONF_PS | GMAC_MAC_CONF_FES;
830 		sc->sc_link = 1;
831 		break;
832 	case IFM_10_T:
833 		conf |= GMAC_MAC_CONF_PS;
834 		sc->sc_link = 1;
835 		break;
836 	default:
837 		sc->sc_link = 0;
838 		return;
839 	}
840 
841 	if (sc->sc_link == 0)
842 		return;
843 
844 	conf &= ~GMAC_MAC_CONF_DM;
845 	if ((sc->sc_mii.mii_media_active & IFM_GMASK) == IFM_FDX)
846 		conf |= GMAC_MAC_CONF_DM;
847 
848 	/* XXX: RX/TX flow control? */
849 
850 	dwge_write(sc, GMAC_MAC_CONF, conf);
851 }
852 
853 void
854 dwge_tick(void *arg)
855 {
856 	struct dwge_softc *sc = arg;
857 	int s;
858 
859 	s = splnet();
860 	mii_tick(&sc->sc_mii);
861 	splx(s);
862 
863 	timeout_add_sec(&sc->sc_tick, 1);
864 }
865 
866 void
867 dwge_rxtick(void *arg)
868 {
869 	struct dwge_softc *sc = arg;
870 	uint32_t mode;
871 	int s;
872 
873 	s = splnet();
874 
875 	mode = dwge_read(sc, GMAC_OP_MODE);
876 	dwge_write(sc, GMAC_OP_MODE, mode & ~GMAC_OP_MODE_SR);
877 
878 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_rxring),
879 	    0, DWGE_DMA_LEN(sc->sc_rxring),
880 	    BUS_DMASYNC_POSTREAD|BUS_DMASYNC_POSTWRITE);
881 
882 	dwge_write(sc, GMAC_RX_DESC_LIST_ADDR, 0);
883 
884 	sc->sc_rx_prod = sc->sc_rx_cons = 0;
885 	dwge_fill_rx_ring(sc);
886 
887 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_rxring),
888 	    0, DWGE_DMA_LEN(sc->sc_rxring),
889 	    BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);
890 
891 	dwge_write(sc, GMAC_RX_DESC_LIST_ADDR, DWGE_DMA_DVA(sc->sc_rxring));
892 	dwge_write(sc, GMAC_OP_MODE, mode);
893 
894 	splx(s);
895 }
896 
897 int
898 dwge_intr(void *arg)
899 {
900 	struct dwge_softc *sc = arg;
901 	uint32_t reg;
902 
903 	reg = dwge_read(sc, GMAC_STATUS);
904 	dwge_write(sc, GMAC_STATUS, reg);
905 
906 	if (reg & GMAC_STATUS_RI)
907 		dwge_rx_proc(sc);
908 
909 	if (reg & GMAC_STATUS_TI ||
910 	    reg & GMAC_STATUS_TU)
911 		dwge_tx_proc(sc);
912 
913 	return (1);
914 }
915 
916 void
917 dwge_tx_proc(struct dwge_softc *sc)
918 {
919 	struct ifnet *ifp = &sc->sc_ac.ac_if;
920 	struct dwge_desc *txd;
921 	struct dwge_buf *txb;
922 	int idx, txfree;
923 
924 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_txring), 0,
925 	    DWGE_DMA_LEN(sc->sc_txring),
926 	    BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);
927 
928 	txfree = 0;
929 	while (sc->sc_tx_cons != sc->sc_tx_prod) {
930 		idx = sc->sc_tx_cons;
931 		KASSERT(idx < DWGE_NTXDESC);
932 
933 		txd = &sc->sc_txdesc[idx];
934 		if (txd->sd_status & TDES0_OWN)
935 			break;
936 
937 		txb = &sc->sc_txbuf[idx];
938 		if (txb->tb_m) {
939 			bus_dmamap_sync(sc->sc_dmat, txb->tb_map, 0,
940 			    txb->tb_map->dm_mapsize, BUS_DMASYNC_POSTWRITE);
941 			bus_dmamap_unload(sc->sc_dmat, txb->tb_map);
942 
943 			m_freem(txb->tb_m);
944 			txb->tb_m = NULL;
945 		}
946 
947 		txfree++;
948 
949 		if (sc->sc_tx_cons == (DWGE_NTXDESC - 1))
950 			sc->sc_tx_cons = 0;
951 		else
952 			sc->sc_tx_cons++;
953 
954 		txd->sd_status = sc->sc_enh_desc ? ETDES0_TCH : 0;
955 	}
956 
957 	if (sc->sc_tx_cons == sc->sc_tx_prod)
958 		ifp->if_timer = 0;
959 
960 	if (txfree) {
961 		if (ifq_is_oactive(&ifp->if_snd))
962 			ifq_restart(&ifp->if_snd);
963 	}
964 }
965 
966 void
967 dwge_rx_proc(struct dwge_softc *sc)
968 {
969 	struct ifnet *ifp = &sc->sc_ac.ac_if;
970 	struct dwge_desc *rxd;
971 	struct dwge_buf *rxb;
972 	struct mbuf_list ml = MBUF_LIST_INITIALIZER();
973 	struct mbuf *m;
974 	int idx, len, cnt, put;
975 
976 	if ((ifp->if_flags & IFF_RUNNING) == 0)
977 		return;
978 
979 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_rxring), 0,
980 	    DWGE_DMA_LEN(sc->sc_rxring),
981 	    BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE);
982 
983 	cnt = if_rxr_inuse(&sc->sc_rx_ring);
984 	put = 0;
985 	while (put < cnt) {
986 		idx = sc->sc_rx_cons;
987 		KASSERT(idx < DWGE_NRXDESC);
988 
989 		rxd = &sc->sc_rxdesc[idx];
990 		if (rxd->sd_status & RDES0_OWN)
991 			break;
992 
993 		len = (rxd->sd_status >> RDES0_FL_SHIFT) & RDES0_FL_MASK;
994 		rxb = &sc->sc_rxbuf[idx];
995 		KASSERT(rxb->tb_m);
996 
997 		bus_dmamap_sync(sc->sc_dmat, rxb->tb_map, 0,
998 		    len, BUS_DMASYNC_POSTREAD);
999 		bus_dmamap_unload(sc->sc_dmat, rxb->tb_map);
1000 
1001 		/* Strip off CRC. */
1002 		len -= ETHER_CRC_LEN;
1003 		KASSERT(len > 0);
1004 
1005 		m = rxb->tb_m;
1006 		rxb->tb_m = NULL;
1007 		m->m_pkthdr.len = m->m_len = len;
1008 
1009 		ml_enqueue(&ml, m);
1010 
1011 		put++;
1012 		if (sc->sc_rx_cons == (DWGE_NRXDESC - 1))
1013 			sc->sc_rx_cons = 0;
1014 		else
1015 			sc->sc_rx_cons++;
1016 	}
1017 
1018 	if_rxr_put(&sc->sc_rx_ring, put);
1019 	if (ifiq_input(&ifp->if_rcv, &ml))
1020 		if_rxr_livelocked(&sc->sc_rx_ring);
1021 
1022 	dwge_fill_rx_ring(sc);
1023 
1024 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_rxring), 0,
1025 	    DWGE_DMA_LEN(sc->sc_rxring),
1026 	    BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE);
1027 
1028 }
1029 
1030 void
1031 dwge_up(struct dwge_softc *sc)
1032 {
1033 	struct ifnet *ifp = &sc->sc_ac.ac_if;
1034 	struct dwge_buf *txb, *rxb;
1035 	uint32_t mode;
1036 	int i;
1037 
1038 	/* Allocate Tx descriptor ring. */
1039 	sc->sc_txring = dwge_dmamem_alloc(sc,
1040 	    DWGE_NTXDESC * sizeof(struct dwge_desc), 8);
1041 	sc->sc_txdesc = DWGE_DMA_KVA(sc->sc_txring);
1042 
1043 	sc->sc_txbuf = malloc(sizeof(struct dwge_buf) * DWGE_NTXDESC,
1044 	    M_DEVBUF, M_WAITOK);
1045 	for (i = 0; i < DWGE_NTXDESC; i++) {
1046 		txb = &sc->sc_txbuf[i];
1047 		bus_dmamap_create(sc->sc_dmat, MCLBYTES, DWGE_NTXSEGS,
1048 		    MCLBYTES, 0, BUS_DMA_WAITOK, &txb->tb_map);
1049 		txb->tb_m = NULL;
1050 
1051 		sc->sc_txdesc[i].sd_next =
1052 		    DWGE_DMA_DVA(sc->sc_txring) +
1053 		    ((i+1) % DWGE_NTXDESC) * sizeof(struct dwge_desc);
1054 		if (sc->sc_enh_desc)
1055 			sc->sc_txdesc[i].sd_status = ETDES0_TCH;
1056 		else
1057 			sc->sc_txdesc[i].sd_len = TDES1_TCH;
1058 	}
1059 
1060 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_txring),
1061 	    0, DWGE_DMA_LEN(sc->sc_txring), BUS_DMASYNC_PREWRITE);
1062 
1063 	sc->sc_tx_prod = sc->sc_tx_cons = 0;
1064 
1065 	dwge_write(sc, GMAC_TX_DESC_LIST_ADDR, DWGE_DMA_DVA(sc->sc_txring));
1066 
1067 	/* Allocate  descriptor ring. */
1068 	sc->sc_rxring = dwge_dmamem_alloc(sc,
1069 	    DWGE_NRXDESC * sizeof(struct dwge_desc), 8);
1070 	sc->sc_rxdesc = DWGE_DMA_KVA(sc->sc_rxring);
1071 
1072 	sc->sc_rxbuf = malloc(sizeof(struct dwge_buf) * DWGE_NRXDESC,
1073 	    M_DEVBUF, M_WAITOK);
1074 
1075 	for (i = 0; i < DWGE_NRXDESC; i++) {
1076 		rxb = &sc->sc_rxbuf[i];
1077 		bus_dmamap_create(sc->sc_dmat, MCLBYTES, 1,
1078 		    MCLBYTES, 0, BUS_DMA_WAITOK, &rxb->tb_map);
1079 		rxb->tb_m = NULL;
1080 
1081 		sc->sc_rxdesc[i].sd_next =
1082 		    DWGE_DMA_DVA(sc->sc_rxring) +
1083 		    ((i+1) % DWGE_NRXDESC) * sizeof(struct dwge_desc);
1084 		sc->sc_rxdesc[i].sd_len =
1085 		    sc->sc_enh_desc ? ERDES1_RCH : RDES1_RCH;
1086 	}
1087 
1088 	if_rxr_init(&sc->sc_rx_ring, 2, DWGE_NRXDESC);
1089 
1090 	sc->sc_rx_prod = sc->sc_rx_cons = 0;
1091 	dwge_fill_rx_ring(sc);
1092 
1093 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_rxring),
1094 	    0, DWGE_DMA_LEN(sc->sc_rxring),
1095 	    BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE);
1096 
1097 	dwge_write(sc, GMAC_RX_DESC_LIST_ADDR, DWGE_DMA_DVA(sc->sc_rxring));
1098 
1099 	dwge_lladdr_write(sc);
1100 
1101 	/* Configure media. */
1102 	if (LIST_FIRST(&sc->sc_mii.mii_phys))
1103 		mii_mediachg(&sc->sc_mii);
1104 
1105 	/* Program promiscuous mode and multicast filters. */
1106 	dwge_iff(sc);
1107 
1108 	ifp->if_flags |= IFF_RUNNING;
1109 	ifq_clr_oactive(&ifp->if_snd);
1110 
1111 	dwge_write(sc, GMAC_INT_ENA, GMAC_INT_ENA_NIE |
1112 	    GMAC_INT_ENA_RIE | GMAC_INT_ENA_TIE | GMAC_INT_ENA_TUE);
1113 
1114 	mode = dwge_read(sc, GMAC_OP_MODE);
1115 	if (sc->sc_force_thresh_dma_mode) {
1116 		mode &= ~(GMAC_OP_MODE_TSF | GMAC_OP_MODE_TTC_MASK);
1117 		mode |= GMAC_OP_MODE_TTC_128;
1118 		mode &= ~(GMAC_OP_MODE_RSF | GMAC_OP_MODE_RTC_MASK);
1119 		mode |= GMAC_OP_MODE_RTC_128;
1120 	} else {
1121 		mode |= GMAC_OP_MODE_TSF | GMAC_OP_MODE_OSF;
1122 		mode |= GMAC_OP_MODE_RSF;
1123 	}
1124 	dwge_write(sc, GMAC_OP_MODE, mode | GMAC_OP_MODE_ST | GMAC_OP_MODE_SR);
1125 
1126 	dwge_write(sc, GMAC_MAC_CONF, dwge_read(sc, GMAC_MAC_CONF) |
1127 	    GMAC_MAC_CONF_TE | GMAC_MAC_CONF_RE);
1128 
1129 	timeout_add_sec(&sc->sc_tick, 1);
1130 }
1131 
1132 void
1133 dwge_down(struct dwge_softc *sc)
1134 {
1135 	struct ifnet *ifp = &sc->sc_ac.ac_if;
1136 	struct dwge_buf *txb, *rxb;
1137 	uint32_t dmactrl;
1138 	int i;
1139 
1140 	timeout_del(&sc->sc_rxto);
1141 	timeout_del(&sc->sc_tick);
1142 
1143 	ifp->if_flags &= ~IFF_RUNNING;
1144 	ifq_clr_oactive(&ifp->if_snd);
1145 	ifp->if_timer = 0;
1146 
1147 	dwge_stop_dma(sc);
1148 
1149 	dwge_write(sc, GMAC_MAC_CONF, dwge_read(sc,
1150 	    GMAC_MAC_CONF) & ~(GMAC_MAC_CONF_TE | GMAC_MAC_CONF_RE));
1151 
1152 	dmactrl = dwge_read(sc, GMAC_OP_MODE);
1153 	dmactrl &= ~(GMAC_OP_MODE_ST | GMAC_OP_MODE_SR);
1154 	dwge_write(sc, GMAC_OP_MODE, dmactrl);
1155 
1156 	dwge_write(sc, GMAC_INT_ENA, 0);
1157 
1158 	intr_barrier(sc->sc_ih);
1159 	ifq_barrier(&ifp->if_snd);
1160 
1161 	for (i = 0; i < DWGE_NTXDESC; i++) {
1162 		txb = &sc->sc_txbuf[i];
1163 		if (txb->tb_m) {
1164 			bus_dmamap_sync(sc->sc_dmat, txb->tb_map, 0,
1165 			    txb->tb_map->dm_mapsize, BUS_DMASYNC_POSTWRITE);
1166 			bus_dmamap_unload(sc->sc_dmat, txb->tb_map);
1167 			m_freem(txb->tb_m);
1168 		}
1169 		bus_dmamap_destroy(sc->sc_dmat, txb->tb_map);
1170 	}
1171 
1172 	dwge_dmamem_free(sc, sc->sc_txring);
1173 	free(sc->sc_txbuf, M_DEVBUF, 0);
1174 
1175 	for (i = 0; i < DWGE_NRXDESC; i++) {
1176 		rxb = &sc->sc_rxbuf[i];
1177 		if (rxb->tb_m) {
1178 			bus_dmamap_sync(sc->sc_dmat, rxb->tb_map, 0,
1179 			    rxb->tb_map->dm_mapsize, BUS_DMASYNC_POSTREAD);
1180 			bus_dmamap_unload(sc->sc_dmat, rxb->tb_map);
1181 			m_freem(rxb->tb_m);
1182 		}
1183 		bus_dmamap_destroy(sc->sc_dmat, rxb->tb_map);
1184 	}
1185 
1186 	dwge_dmamem_free(sc, sc->sc_rxring);
1187 	free(sc->sc_rxbuf, M_DEVBUF, 0);
1188 }
1189 
1190 /* Bit Reversal - http://aggregate.org/MAGIC/#Bit%20Reversal */
1191 static uint32_t
1192 bitrev32(uint32_t x)
1193 {
1194 	x = (((x & 0xaaaaaaaa) >> 1) | ((x & 0x55555555) << 1));
1195 	x = (((x & 0xcccccccc) >> 2) | ((x & 0x33333333) << 2));
1196 	x = (((x & 0xf0f0f0f0) >> 4) | ((x & 0x0f0f0f0f) << 4));
1197 	x = (((x & 0xff00ff00) >> 8) | ((x & 0x00ff00ff) << 8));
1198 
1199 	return (x >> 16) | (x << 16);
1200 }
1201 
1202 void
1203 dwge_iff(struct dwge_softc *sc)
1204 {
1205 	struct arpcom *ac = &sc->sc_ac;
1206 	struct ifnet *ifp = &sc->sc_ac.ac_if;
1207 	struct ether_multi *enm;
1208 	struct ether_multistep step;
1209 	uint32_t crc, hash[2], hashbit, hashreg;
1210 	uint32_t reg;
1211 
1212 	reg = 0;
1213 
1214 	ifp->if_flags &= ~IFF_ALLMULTI;
1215 	bzero(hash, sizeof(hash));
1216 	if (ifp->if_flags & IFF_PROMISC || ac->ac_multirangecnt > 0) {
1217 		ifp->if_flags |= IFF_ALLMULTI;
1218 		reg |= GMAC_MAC_FRM_FILT_PM;
1219 		if (ifp->if_flags & IFF_PROMISC)
1220 			reg |= GMAC_MAC_FRM_FILT_PR;
1221 	} else {
1222 		reg |= GMAC_MAC_FRM_FILT_HMC;
1223 		ETHER_FIRST_MULTI(step, ac, enm);
1224 		while (enm != NULL) {
1225 			crc = ether_crc32_le(enm->enm_addrlo,
1226 			    ETHER_ADDR_LEN) & 0x7f;
1227 
1228 			crc = bitrev32(~crc) >> 26;
1229 			hashreg = (crc >> 5);
1230 			hashbit = (crc & 0x1f);
1231 			hash[hashreg] |= (1 << hashbit);
1232 
1233 			ETHER_NEXT_MULTI(step, enm);
1234 		}
1235 	}
1236 
1237 	dwge_lladdr_write(sc);
1238 
1239 	dwge_write(sc, GMAC_HASH_TAB_HI, hash[1]);
1240 	dwge_write(sc, GMAC_HASH_TAB_LO, hash[0]);
1241 
1242 	dwge_write(sc, GMAC_MAC_FRM_FILT, reg);
1243 }
1244 
1245 int
1246 dwge_encap(struct dwge_softc *sc, struct mbuf *m, int *idx, int *used)
1247 {
1248 	struct dwge_desc *txd, *txd_start;
1249 	bus_dmamap_t map;
1250 	int cur, frag, i;
1251 
1252 	cur = frag = *idx;
1253 	map = sc->sc_txbuf[cur].tb_map;
1254 
1255 	if (bus_dmamap_load_mbuf(sc->sc_dmat, map, m, BUS_DMA_NOWAIT)) {
1256 		if (m_defrag(m, M_DONTWAIT))
1257 			return (EFBIG);
1258 		if (bus_dmamap_load_mbuf(sc->sc_dmat, map, m, BUS_DMA_NOWAIT))
1259 			return (EFBIG);
1260 	}
1261 
1262 	/* Sync the DMA map. */
1263 	bus_dmamap_sync(sc->sc_dmat, map, 0, map->dm_mapsize,
1264 	    BUS_DMASYNC_PREWRITE);
1265 
1266 	txd = txd_start = &sc->sc_txdesc[frag];
1267 	for (i = 0; i < map->dm_nsegs; i++) {
1268 		txd->sd_addr = map->dm_segs[i].ds_addr;
1269 		if (sc->sc_enh_desc) {
1270 			txd->sd_status = ETDES0_TCH;
1271 			txd->sd_len = map->dm_segs[i].ds_len;
1272 			if (i == 0)
1273 				txd->sd_status |= ETDES0_FS;
1274 			if (i == (map->dm_nsegs - 1))
1275 				txd->sd_status |= ETDES0_LS | ETDES0_IC;
1276 		} else {
1277 			txd->sd_status = 0;
1278 			txd->sd_len = map->dm_segs[i].ds_len | TDES1_TCH;
1279 			if (i == 0)
1280 				txd->sd_len |= TDES1_FS;
1281 			if (i == (map->dm_nsegs - 1))
1282 				txd->sd_len |= TDES1_LS | TDES1_IC;
1283 		}
1284 		if (i != 0)
1285 			txd->sd_status |= TDES0_OWN;
1286 
1287 		bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_txring),
1288 		    frag * sizeof(*txd), sizeof(*txd), BUS_DMASYNC_PREWRITE);
1289 
1290 		cur = frag;
1291 		if (frag == (DWGE_NTXDESC - 1)) {
1292 			txd = &sc->sc_txdesc[0];
1293 			frag = 0;
1294 		} else {
1295 			txd++;
1296 			frag++;
1297 		}
1298 		KASSERT(frag != sc->sc_tx_cons);
1299 	}
1300 
1301 	txd_start->sd_status |= TDES0_OWN;
1302 	bus_dmamap_sync(sc->sc_dmat, DWGE_DMA_MAP(sc->sc_txring),
1303 	    *idx * sizeof(*txd), sizeof(*txd), BUS_DMASYNC_PREWRITE);
1304 
1305 	KASSERT(sc->sc_txbuf[cur].tb_m == NULL);
1306 	sc->sc_txbuf[*idx].tb_map = sc->sc_txbuf[cur].tb_map;
1307 	sc->sc_txbuf[cur].tb_map = map;
1308 	sc->sc_txbuf[cur].tb_m = m;
1309 
1310 	*idx = frag;
1311 	*used += map->dm_nsegs;
1312 
1313 	return (0);
1314 }
1315 
1316 void
1317 dwge_reset(struct dwge_softc *sc)
1318 {
1319 	int n;
1320 
1321 	dwge_stop_dma(sc);
1322 
1323 	dwge_write(sc, GMAC_BUS_MODE, dwge_read(sc, GMAC_BUS_MODE) |
1324 	    GMAC_BUS_MODE_SWR);
1325 
1326 	for (n = 0; n < 30000; n++) {
1327 		if ((dwge_read(sc, GMAC_BUS_MODE) &
1328 		    GMAC_BUS_MODE_SWR) == 0)
1329 			return;
1330 		delay(10);
1331 	}
1332 
1333 	printf("%s: reset timeout\n", sc->sc_dev.dv_xname);
1334 }
1335 
1336 void
1337 dwge_stop_dma(struct dwge_softc *sc)
1338 {
1339 	uint32_t dmactrl;
1340 
1341 	/* Stop DMA. */
1342 	dmactrl = dwge_read(sc, GMAC_OP_MODE);
1343 	dmactrl &= ~GMAC_OP_MODE_ST;
1344 	dmactrl |= GMAC_OP_MODE_FTF;
1345 	dwge_write(sc, GMAC_OP_MODE, dmactrl);
1346 }
1347 
1348 struct dwge_dmamem *
1349 dwge_dmamem_alloc(struct dwge_softc *sc, bus_size_t size, bus_size_t align)
1350 {
1351 	struct dwge_dmamem *tdm;
1352 	int nsegs;
1353 
1354 	tdm = malloc(sizeof(*tdm), M_DEVBUF, M_WAITOK | M_ZERO);
1355 	tdm->tdm_size = size;
1356 
1357 	if (bus_dmamap_create(sc->sc_dmat, size, 1, size, 0,
1358 	    BUS_DMA_WAITOK | BUS_DMA_ALLOCNOW, &tdm->tdm_map) != 0)
1359 		goto tdmfree;
1360 
1361 	if (bus_dmamem_alloc(sc->sc_dmat, size, align, 0, &tdm->tdm_seg, 1,
1362 	    &nsegs, BUS_DMA_WAITOK) != 0)
1363 		goto destroy;
1364 
1365 	if (bus_dmamem_map(sc->sc_dmat, &tdm->tdm_seg, nsegs, size,
1366 	    &tdm->tdm_kva, BUS_DMA_WAITOK | BUS_DMA_COHERENT) != 0)
1367 		goto free;
1368 
1369 	if (bus_dmamap_load(sc->sc_dmat, tdm->tdm_map, tdm->tdm_kva, size,
1370 	    NULL, BUS_DMA_WAITOK) != 0)
1371 		goto unmap;
1372 
1373 	bzero(tdm->tdm_kva, size);
1374 
1375 	return (tdm);
1376 
1377 unmap:
1378 	bus_dmamem_unmap(sc->sc_dmat, tdm->tdm_kva, size);
1379 free:
1380 	bus_dmamem_free(sc->sc_dmat, &tdm->tdm_seg, 1);
1381 destroy:
1382 	bus_dmamap_destroy(sc->sc_dmat, tdm->tdm_map);
1383 tdmfree:
1384 	free(tdm, M_DEVBUF, 0);
1385 
1386 	return (NULL);
1387 }
1388 
1389 void
1390 dwge_dmamem_free(struct dwge_softc *sc, struct dwge_dmamem *tdm)
1391 {
1392 	bus_dmamem_unmap(sc->sc_dmat, tdm->tdm_kva, tdm->tdm_size);
1393 	bus_dmamem_free(sc->sc_dmat, &tdm->tdm_seg, 1);
1394 	bus_dmamap_destroy(sc->sc_dmat, tdm->tdm_map);
1395 	free(tdm, M_DEVBUF, 0);
1396 }
1397 
1398 struct mbuf *
1399 dwge_alloc_mbuf(struct dwge_softc *sc, bus_dmamap_t map)
1400 {
1401 	struct mbuf *m = NULL;
1402 
1403 	m = MCLGETL(NULL, M_DONTWAIT, MCLBYTES);
1404 	if (!m)
1405 		return (NULL);
1406 	m->m_len = m->m_pkthdr.len = MCLBYTES;
1407 	m_adj(m, ETHER_ALIGN);
1408 
1409 	if (bus_dmamap_load_mbuf(sc->sc_dmat, map, m, BUS_DMA_NOWAIT) != 0) {
1410 		printf("%s: could not load mbuf DMA map", DEVNAME(sc));
1411 		m_freem(m);
1412 		return (NULL);
1413 	}
1414 
1415 	bus_dmamap_sync(sc->sc_dmat, map, 0,
1416 	    m->m_pkthdr.len, BUS_DMASYNC_PREREAD);
1417 
1418 	return (m);
1419 }
1420 
1421 void
1422 dwge_fill_rx_ring(struct dwge_softc *sc)
1423 {
1424 	struct dwge_desc *rxd;
1425 	struct dwge_buf *rxb;
1426 	u_int slots;
1427 
1428 	for (slots = if_rxr_get(&sc->sc_rx_ring, DWGE_NRXDESC);
1429 	    slots > 0; slots--) {
1430 		rxb = &sc->sc_rxbuf[sc->sc_rx_prod];
1431 		rxb->tb_m = dwge_alloc_mbuf(sc, rxb->tb_map);
1432 		if (rxb->tb_m == NULL)
1433 			break;
1434 
1435 		rxd = &sc->sc_rxdesc[sc->sc_rx_prod];
1436 		rxd->sd_len = rxb->tb_map->dm_segs[0].ds_len;
1437 		rxd->sd_len |= sc->sc_enh_desc ? ERDES1_RCH : RDES1_RCH;
1438 		rxd->sd_addr = rxb->tb_map->dm_segs[0].ds_addr;
1439 		rxd->sd_status = RDES0_OWN;
1440 
1441 		if (sc->sc_rx_prod == (DWGE_NRXDESC - 1))
1442 			sc->sc_rx_prod = 0;
1443 		else
1444 			sc->sc_rx_prod++;
1445 	}
1446 	if_rxr_put(&sc->sc_rx_ring, slots);
1447 
1448 	if (if_rxr_inuse(&sc->sc_rx_ring) == 0)
1449 		timeout_add(&sc->sc_rxto, 1);
1450 }
1451 
1452 /*
1453  * Allwinner A20/A31.
1454  */
1455 
1456 void
1457 dwge_setup_allwinner(struct dwge_softc *sc)
1458 {
1459 	char phy_mode[8];
1460 	uint32_t freq;
1461 
1462 	/* default to RGMII */
1463 	OF_getprop(sc->sc_node, "phy-mode", phy_mode, sizeof(phy_mode));
1464 	if (strcmp(phy_mode, "mii") == 0)
1465 		freq = 25000000;
1466 	else
1467 		freq = 125000000;
1468 	clock_set_frequency(sc->sc_node, "allwinner_gmac_tx", freq);
1469 }
1470 
1471 /*
1472  * Rockchip RK3288/RK3399.
1473  */
1474 
1475 /* RK3308 registers */
1476 #define RK3308_GRF_MAC_CON0	0x04a0
1477 #define RK3308_MAC_SPEED_100M	((0x1 << 0) << 16 | (0x1 << 0))
1478 #define RK3308_MAC_SPEED_10M	((0x1 << 0) << 16 | (0x0 << 0))
1479 #define RK3308_INTF_SEL_RMII	((0x1 << 4) << 16 | (0x1 << 4))
1480 
1481 /* RK3288 registers */
1482 #define RK3288_GRF_SOC_CON1	0x0248
1483 #define  RK3288_GMAC_PHY_INTF_SEL_RGMII	((0x7 << 6) << 16 | (0x1 << 6))
1484 #define  RK3288_GMAC_PHY_INTF_SEL_RMII	((0x7 << 6) << 16 | (0x4 << 6))
1485 #define  RK3288_RMII_MODE_RMII		((1 << 14) << 16 | (1 << 14))
1486 #define  RK3288_RMII_MODE_MII		((1 << 14) << 16 | (0 << 14))
1487 #define  RK3288_GMAC_CLK_SEL_125	((0x3 << 12) << 16 | (0x0 << 12))
1488 #define  RK3288_GMAC_CLK_SEL_25		((0x3 << 12) << 16 | (0x3 << 12))
1489 #define  RK3288_GMAC_CLK_SEL_2_5	((0x3 << 12) << 16 | (0x2 << 12))
1490 
1491 #define RK3288_GRF_SOC_CON3	0x0250
1492 #define  RK3288_GMAC_RXCLK_DLY_ENA	((1 << 15) << 16 | (1 << 15))
1493 #define  RK3288_GMAC_CLK_RX_DL_CFG(val) ((0x7f << 7) << 16 | ((val) << 7))
1494 #define  RK3288_GMAC_TXCLK_DLY_ENA	((1 << 14) << 16 | (1 << 14))
1495 #define  RK3288_GMAC_CLK_TX_DL_CFG(val) ((0x7f << 0) << 16 | ((val) << 0))
1496 
1497 /* RK3328 registers */
1498 #define RK3328_GRF_MAC_CON0	0x0900
1499 #define  RK3328_GMAC_CLK_RX_DL_CFG(val) ((0x7f << 7) << 16 | ((val) << 7))
1500 #define  RK3328_GMAC_CLK_TX_DL_CFG(val) ((0x7f << 0) << 16 | ((val) << 0))
1501 
1502 #define RK3328_GRF_MAC_CON1	0x0904
1503 #define  RK3328_GMAC_PHY_INTF_SEL_RGMII	((0x7 << 4) << 16 | (0x1 << 4))
1504 #define  RK3328_GMAC_PHY_INTF_SEL_RMII	((0x7 << 4) << 16 | (0x4 << 4))
1505 #define  RK3328_RMII_MODE_RMII		((1 << 9) << 16 | (1 << 9))
1506 #define  RK3328_RMII_MODE_MII		((1 << 9) << 16 | (0 << 9))
1507 #define  RK3328_GMAC_CLK_SEL_125	((0x3 << 11) << 16 | (0x0 << 11))
1508 #define  RK3328_GMAC_CLK_SEL_25		((0x3 << 11) << 16 | (0x3 << 11))
1509 #define  RK3328_GMAC_CLK_SEL_2_5	((0x3 << 11) << 16 | (0x2 << 11))
1510 #define  RK3328_GMAC_RXCLK_DLY_ENA	((1 << 1) << 16 | (1 << 1))
1511 #define  RK3328_GMAC_TXCLK_DLY_ENA	((1 << 0) << 16 | (1 << 0))
1512 
1513 /* RK3399 registers */
1514 #define RK3399_GRF_SOC_CON5	0xc214
1515 #define  RK3399_GMAC_PHY_INTF_SEL_RGMII	((0x7 << 9) << 16 | (0x1 << 9))
1516 #define  RK3399_GMAC_PHY_INTF_SEL_RMII	((0x7 << 9) << 16 | (0x4 << 9))
1517 #define  RK3399_RMII_MODE_RMII		((1 << 6) << 16 | (1 << 6))
1518 #define  RK3399_RMII_MODE_MII		((1 << 6) << 16 | (0 << 6))
1519 #define  RK3399_GMAC_CLK_SEL_125	((0x3 << 4) << 16 | (0x0 << 4))
1520 #define  RK3399_GMAC_CLK_SEL_25		((0x3 << 4) << 16 | (0x3 << 4))
1521 #define  RK3399_GMAC_CLK_SEL_2_5	((0x3 << 4) << 16 | (0x2 << 4))
1522 #define RK3399_GRF_SOC_CON6	0xc218
1523 #define  RK3399_GMAC_RXCLK_DLY_ENA	((1 << 15) << 16 | (1 << 15))
1524 #define  RK3399_GMAC_CLK_RX_DL_CFG(val) ((0x7f << 8) << 16 | ((val) << 8))
1525 #define  RK3399_GMAC_TXCLK_DLY_ENA	((1 << 7) << 16 | (1 << 7))
1526 #define  RK3399_GMAC_CLK_TX_DL_CFG(val) ((0x7f << 0) << 16 | ((val) << 0))
1527 
1528 void	dwge_mii_statchg_rockchip(struct device *);
1529 
1530 void
1531 dwge_setup_rockchip(struct dwge_softc *sc)
1532 {
1533 	struct regmap *rm;
1534 	uint32_t grf;
1535 	int tx_delay, rx_delay;
1536 	char clock_mode[8];
1537 
1538 	grf = OF_getpropint(sc->sc_node, "rockchip,grf", 0);
1539 	rm = regmap_byphandle(grf);
1540 	if (rm == NULL)
1541 		return;
1542 
1543 	tx_delay = OF_getpropint(sc->sc_node, "tx_delay", 0x30);
1544 	rx_delay = OF_getpropint(sc->sc_node, "rx_delay", 0x10);
1545 
1546 	if (OF_is_compatible(sc->sc_node, "rockchip,rk3288-gmac")) {
1547 		/* Use RGMII interface. */
1548 		regmap_write_4(rm, RK3288_GRF_SOC_CON1,
1549 		    RK3288_GMAC_PHY_INTF_SEL_RGMII | RK3288_RMII_MODE_MII);
1550 
1551 		/* Program clock delay lines. */
1552 		regmap_write_4(rm, RK3288_GRF_SOC_CON3,
1553 		    RK3288_GMAC_TXCLK_DLY_ENA | RK3288_GMAC_RXCLK_DLY_ENA |
1554 		    RK3288_GMAC_CLK_TX_DL_CFG(tx_delay) |
1555 		    RK3288_GMAC_CLK_RX_DL_CFG(rx_delay));
1556 
1557 		/* Clock speed bits. */
1558 		sc->sc_clk_sel = RK3288_GRF_SOC_CON1;
1559 		sc->sc_clk_sel_2_5 = RK3288_GMAC_CLK_SEL_2_5;
1560 		sc->sc_clk_sel_25 = RK3288_GMAC_CLK_SEL_25;
1561 		sc->sc_clk_sel_125 = RK3288_GMAC_CLK_SEL_125;
1562 	} else if (OF_is_compatible(sc->sc_node, "rockchip,rk3308-mac")) {
1563 		/* Use RMII interface. */
1564 		regmap_write_4(rm, RK3308_GRF_MAC_CON0,
1565 		    RK3308_INTF_SEL_RMII | RK3308_MAC_SPEED_100M);
1566 
1567 		/* Adjust MAC clock if necessary. */
1568 		OF_getprop(sc->sc_node, "clock_in_out", clock_mode,
1569 		    sizeof(clock_mode));
1570 		if (strcmp(clock_mode, "output") == 0) {
1571 			clock_set_frequency(sc->sc_node, "stmmaceth",
1572 			    50000000);
1573 			sc->sc_clk = GMAC_GMII_ADDR_CR_DIV_26;
1574 		}
1575 
1576 		/* Clock speed bits. */
1577 		sc->sc_clk_sel = RK3308_GRF_MAC_CON0;
1578 		sc->sc_clk_sel_2_5 = RK3308_MAC_SPEED_10M;
1579 		sc->sc_clk_sel_25 = RK3308_MAC_SPEED_100M;
1580 	} else if (OF_is_compatible(sc->sc_node, "rockchip,rk3328-gmac")) {
1581 		/* Use RGMII interface. */
1582 		regmap_write_4(rm, RK3328_GRF_MAC_CON1,
1583 		    RK3328_GMAC_PHY_INTF_SEL_RGMII | RK3328_RMII_MODE_MII);
1584 
1585 		/* Program clock delay lines. */
1586 		regmap_write_4(rm, RK3328_GRF_MAC_CON0,
1587 		    RK3328_GMAC_CLK_TX_DL_CFG(tx_delay) |
1588 		    RK3328_GMAC_CLK_RX_DL_CFG(rx_delay));
1589 		regmap_write_4(rm, RK3328_GRF_MAC_CON1,
1590 		    RK3328_GMAC_TXCLK_DLY_ENA | RK3328_GMAC_RXCLK_DLY_ENA);
1591 
1592 		/* Clock speed bits. */
1593 		sc->sc_clk_sel = RK3328_GRF_MAC_CON1;
1594 		sc->sc_clk_sel_2_5 = RK3328_GMAC_CLK_SEL_2_5;
1595 		sc->sc_clk_sel_25 = RK3328_GMAC_CLK_SEL_25;
1596 		sc->sc_clk_sel_125 = RK3328_GMAC_CLK_SEL_125;
1597 	} else {
1598 		/* Use RGMII interface. */
1599 		regmap_write_4(rm, RK3399_GRF_SOC_CON5,
1600 		    RK3399_GMAC_PHY_INTF_SEL_RGMII | RK3399_RMII_MODE_MII);
1601 
1602 		/* Program clock delay lines. */
1603 		regmap_write_4(rm, RK3399_GRF_SOC_CON6,
1604 		    RK3399_GMAC_TXCLK_DLY_ENA | RK3399_GMAC_RXCLK_DLY_ENA |
1605 		    RK3399_GMAC_CLK_TX_DL_CFG(tx_delay) |
1606 		    RK3399_GMAC_CLK_RX_DL_CFG(rx_delay));
1607 
1608 		/* Clock speed bits. */
1609 		sc->sc_clk_sel = RK3399_GRF_SOC_CON5;
1610 		sc->sc_clk_sel_2_5 = RK3399_GMAC_CLK_SEL_2_5;
1611 		sc->sc_clk_sel_25 = RK3399_GMAC_CLK_SEL_25;
1612 		sc->sc_clk_sel_125 = RK3399_GMAC_CLK_SEL_125;
1613 	}
1614 
1615 	sc->sc_mii.mii_statchg = dwge_mii_statchg_rockchip;
1616 }
1617 
1618 void
1619 dwge_mii_statchg_rockchip(struct device *self)
1620 {
1621 	struct dwge_softc *sc = (void *)self;
1622 	struct regmap *rm;
1623 	uint32_t grf;
1624 	uint32_t gmac_clk_sel = 0;
1625 
1626 	dwge_mii_statchg(self);
1627 
1628 	grf = OF_getpropint(sc->sc_node, "rockchip,grf", 0);
1629 	rm = regmap_byphandle(grf);
1630 	if (rm == NULL)
1631 		return;
1632 
1633 	switch (IFM_SUBTYPE(sc->sc_mii.mii_media_active)) {
1634 	case IFM_10_T:
1635 		gmac_clk_sel = sc->sc_clk_sel_2_5;
1636 		break;
1637 	case IFM_100_TX:
1638 		gmac_clk_sel = sc->sc_clk_sel_25;
1639 		break;
1640 	case IFM_1000_T:
1641 		gmac_clk_sel = sc->sc_clk_sel_125;
1642 		break;
1643 	}
1644 
1645 	regmap_write_4(rm, sc->sc_clk_sel, gmac_clk_sel);
1646 }
1647