xref: /freebsd/sys/dev/etherswitch/rtl8366/rtl8366rb.c (revision e0c4386e7e71d93b0edc0c8fa156263fc4a8b0b6)
1 /*-
2  * SPDX-License-Identifier: BSD-2-Clause
3  *
4  * Copyright (c) 2015-2016 Hiroki Mori.
5  * Copyright (c) 2011-2012 Stefan Bethke.
6  * All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27  * SUCH DAMAGE.
28  */
29 
30 #include "opt_etherswitch.h"
31 
32 #include <sys/param.h>
33 #include <sys/bus.h>
34 #include <sys/errno.h>
35 #include <sys/kernel.h>
36 #include <sys/lock.h>
37 #include <sys/malloc.h>
38 #include <sys/module.h>
39 #include <sys/mutex.h>
40 #include <sys/socket.h>
41 #include <sys/sockio.h>
42 #include <sys/sysctl.h>
43 #include <sys/systm.h>
44 
45 #include <net/if.h>
46 #include <net/if_var.h>
47 #include <net/ethernet.h>
48 #include <net/if_media.h>
49 #include <net/if_types.h>
50 
51 #include <machine/bus.h>
52 #include <dev/iicbus/iic.h>
53 #include <dev/iicbus/iiconf.h>
54 #include <dev/iicbus/iicbus.h>
55 #include <dev/mii/mii.h>
56 #include <dev/mii/miivar.h>
57 #include <dev/mdio/mdio.h>
58 
59 #include <dev/etherswitch/etherswitch.h>
60 #include <dev/etherswitch/rtl8366/rtl8366rbvar.h>
61 
62 #include "mdio_if.h"
63 #include "iicbus_if.h"
64 #include "miibus_if.h"
65 #include "etherswitch_if.h"
66 
67 
68 struct rtl8366rb_softc {
69 	struct mtx	sc_mtx;		/* serialize access to softc */
70 	int		smi_acquired;	/* serialize access to SMI/I2C bus */
71 	struct mtx	callout_mtx;	/* serialize callout */
72 	device_t	dev;
73 	int		vid[RTL8366_NUM_VLANS];
74 	char		*ifname[RTL8366_NUM_PHYS];
75 	device_t	miibus[RTL8366_NUM_PHYS];
76 	if_t ifp[RTL8366_NUM_PHYS];
77 	struct callout	callout_tick;
78 	etherswitch_info_t	info;
79 	int		chip_type;
80 	int		phy4cpu;
81 	int		numphys;
82 };
83 
84 #define RTL_LOCK(_sc)	mtx_lock(&(_sc)->sc_mtx)
85 #define RTL_UNLOCK(_sc)	mtx_unlock(&(_sc)->sc_mtx)
86 #define RTL_LOCK_ASSERT(_sc, _what)	mtx_assert(&(_s)c->sc_mtx, (_what))
87 #define RTL_TRYLOCK(_sc)	mtx_trylock(&(_sc)->sc_mtx)
88 
89 #define RTL_WAITOK	0
90 #define	RTL_NOWAIT	1
91 
92 #define RTL_SMI_ACQUIRED	1
93 #define RTL_SMI_ACQUIRED_ASSERT(_sc) \
94 	KASSERT((_sc)->smi_acquired == RTL_SMI_ACQUIRED, ("smi must be acquired @%s", __FUNCTION__))
95 
96 #if defined(DEBUG)
97 #define DPRINTF(dev, args...) device_printf(dev, args)
98 #define DEVERR(dev, err, fmt, args...) do { \
99 		if (err != 0) device_printf(dev, fmt, err, args); \
100 	} while (0)
101 #define DEBUG_INCRVAR(var)	do { \
102 		var++; \
103 	} while (0)
104 
105 static int callout_blocked = 0;
106 static int iic_select_retries = 0;
107 static int phy_access_retries = 0;
108 static SYSCTL_NODE(_debug, OID_AUTO, rtl8366rb, CTLFLAG_RD | CTLFLAG_MPSAFE, 0,
109     "rtl8366rb");
110 SYSCTL_INT(_debug_rtl8366rb, OID_AUTO, callout_blocked, CTLFLAG_RW, &callout_blocked, 0,
111 	"number of times the callout couldn't acquire the bus");
112 SYSCTL_INT(_debug_rtl8366rb, OID_AUTO, iic_select_retries, CTLFLAG_RW, &iic_select_retries, 0,
113 	"number of times the I2C bus selection had to be retried");
114 SYSCTL_INT(_debug_rtl8366rb, OID_AUTO, phy_access_retries, CTLFLAG_RW, &phy_access_retries, 0,
115 	"number of times PHY register access had to be retried");
116 #else
117 #define DPRINTF(dev, args...)
118 #define DEVERR(dev, err, fmt, args...)
119 #define DEBUG_INCRVAR(var)
120 #endif
121 
122 static int smi_probe(device_t dev);
123 static int smi_read(device_t dev, uint16_t addr, uint16_t *data, int sleep);
124 static int smi_write(device_t dev, uint16_t addr, uint16_t data, int sleep);
125 static int smi_rmw(device_t dev, uint16_t addr, uint16_t mask, uint16_t data, int sleep);
126 static void rtl8366rb_tick(void *arg);
127 static int rtl8366rb_ifmedia_upd(if_t);
128 static void rtl8366rb_ifmedia_sts(if_t, struct ifmediareq *);
129 
130 static void
131 rtl8366rb_identify(driver_t *driver, device_t parent)
132 {
133 	device_t child;
134 	struct iicbus_ivar *devi;
135 
136 	if (device_find_child(parent, "rtl8366rb", -1) == NULL) {
137 		child = BUS_ADD_CHILD(parent, 0, "rtl8366rb", -1);
138 		devi = IICBUS_IVAR(child);
139 		devi->addr = RTL8366_IIC_ADDR;
140 	}
141 }
142 
143 static int
144 rtl8366rb_probe(device_t dev)
145 {
146 	struct rtl8366rb_softc *sc;
147 
148 	sc = device_get_softc(dev);
149 
150 	bzero(sc, sizeof(*sc));
151 	if (smi_probe(dev) != 0)
152 		return (ENXIO);
153 	if (sc->chip_type == RTL8366RB)
154 		device_set_desc(dev, "RTL8366RB Ethernet Switch Controller");
155 	else
156 		device_set_desc(dev, "RTL8366SR Ethernet Switch Controller");
157 	return (BUS_PROBE_DEFAULT);
158 }
159 
160 static void
161 rtl8366rb_init(device_t dev)
162 {
163 	struct rtl8366rb_softc *sc;
164 	int i;
165 
166 	sc = device_get_softc(dev);
167 
168 	/* Initialisation for TL-WR1043ND */
169 #ifdef RTL8366_SOFT_RESET
170 	smi_rmw(dev, RTL8366_RCR,
171 		RTL8366_RCR_SOFT_RESET,
172 		RTL8366_RCR_SOFT_RESET, RTL_WAITOK);
173 #else
174 	smi_rmw(dev, RTL8366_RCR,
175 		RTL8366_RCR_HARD_RESET,
176 		RTL8366_RCR_HARD_RESET, RTL_WAITOK);
177 #endif
178 	/* hard reset not return ack */
179 	DELAY(100000);
180 	/* Enable 16 VLAN mode */
181 	smi_rmw(dev, RTL8366_SGCR,
182 		RTL8366_SGCR_EN_VLAN | RTL8366_SGCR_EN_VLAN_4KTB,
183 		RTL8366_SGCR_EN_VLAN, RTL_WAITOK);
184 	/* Initialize our vlan table. */
185 	for (i = 0; i <= 1; i++)
186 		sc->vid[i] = (i + 1) | ETHERSWITCH_VID_VALID;
187 	/* Remove port 0 from VLAN 1. */
188 	smi_rmw(dev, RTL8366_VMCR(RTL8366_VMCR_MU_REG, 0),
189 		(1 << 0), 0, RTL_WAITOK);
190 	/* Add port 0 untagged and port 5 tagged to VLAN 2. */
191 	smi_rmw(dev, RTL8366_VMCR(RTL8366_VMCR_MU_REG, 1),
192 		((1 << 5 | 1 << 0) << RTL8366_VMCR_MU_MEMBER_SHIFT)
193 			| ((1 << 5 | 1 << 0) << RTL8366_VMCR_MU_UNTAG_SHIFT),
194 		((1 << 5 | 1 << 0) << RTL8366_VMCR_MU_MEMBER_SHIFT
195 			| ((1 << 0) << RTL8366_VMCR_MU_UNTAG_SHIFT)),
196 		RTL_WAITOK);
197 	/* Set PVID 2 for port 0. */
198 	smi_rmw(dev, RTL8366_PVCR_REG(0),
199 		RTL8366_PVCR_VAL(0, RTL8366_PVCR_PORT_MASK),
200 		RTL8366_PVCR_VAL(0, 1), RTL_WAITOK);
201 }
202 
203 static int
204 rtl8366rb_attach(device_t dev)
205 {
206 	struct rtl8366rb_softc *sc;
207 	uint16_t rev = 0;
208 	char name[IFNAMSIZ];
209 	int err = 0;
210 	int i;
211 
212 	sc = device_get_softc(dev);
213 
214 	sc->dev = dev;
215 	mtx_init(&sc->sc_mtx, "rtl8366rb", NULL, MTX_DEF);
216 	sc->smi_acquired = 0;
217 	mtx_init(&sc->callout_mtx, "rtl8366rbcallout", NULL, MTX_DEF);
218 
219 	rtl8366rb_init(dev);
220 	smi_read(dev, RTL8366_CVCR, &rev, RTL_WAITOK);
221 	device_printf(dev, "rev. %d\n", rev & 0x000f);
222 
223 	sc->phy4cpu = 0;
224 	(void) resource_int_value(device_get_name(dev), device_get_unit(dev),
225 	    "phy4cpu", &sc->phy4cpu);
226 
227 	sc->numphys = sc->phy4cpu ? RTL8366_NUM_PHYS - 1 : RTL8366_NUM_PHYS;
228 
229 	sc->info.es_nports = sc->numphys + 1;
230 	sc->info.es_nvlangroups = RTL8366_NUM_VLANS;
231 	sc->info.es_vlan_caps = ETHERSWITCH_VLAN_DOT1Q;
232 	if (sc->chip_type == RTL8366RB)
233 		sprintf(sc->info.es_name, "Realtek RTL8366RB");
234 	else
235 		sprintf(sc->info.es_name, "Realtek RTL8366SR");
236 
237 	/* attach miibus and phys */
238 	/* PHYs need an interface, so we generate a dummy one */
239 	for (i = 0; i < sc->numphys; i++) {
240 		sc->ifp[i] = if_alloc(IFT_ETHER);
241 		if (sc->ifp[i] == NULL) {
242 			device_printf(dev, "couldn't allocate ifnet structure\n");
243 			err = ENOMEM;
244 			break;
245 		}
246 
247 		if_setsoftc(sc->ifp[i], sc);
248 		if_setflagbits(sc->ifp[i], IFF_UP | IFF_BROADCAST | IFF_DRV_RUNNING
249 			| IFF_SIMPLEX, 0);
250 		snprintf(name, IFNAMSIZ, "%sport", device_get_nameunit(dev));
251 		sc->ifname[i] = malloc(strlen(name)+1, M_DEVBUF, M_WAITOK);
252 		bcopy(name, sc->ifname[i], strlen(name)+1);
253 		if_initname(sc->ifp[i], sc->ifname[i], i);
254 		err = mii_attach(dev, &sc->miibus[i], sc->ifp[i], rtl8366rb_ifmedia_upd, \
255 			rtl8366rb_ifmedia_sts, BMSR_DEFCAPMASK, \
256 			i, MII_OFFSET_ANY, 0);
257 		if (err != 0) {
258 			device_printf(dev, "attaching PHY %d failed\n", i);
259 			return (err);
260 		}
261 	}
262 
263 	bus_generic_probe(dev);
264 	bus_enumerate_hinted_children(dev);
265 	err = bus_generic_attach(dev);
266 	if (err != 0)
267 		return (err);
268 
269 	callout_init_mtx(&sc->callout_tick, &sc->callout_mtx, 0);
270 	rtl8366rb_tick(sc);
271 
272 	return (err);
273 }
274 
275 static int
276 rtl8366rb_detach(device_t dev)
277 {
278 	struct rtl8366rb_softc *sc;
279 	int i;
280 
281 	sc = device_get_softc(dev);
282 
283 	for (i=0; i < sc->numphys; i++) {
284 		if (sc->miibus[i])
285 			device_delete_child(dev, sc->miibus[i]);
286 		if (sc->ifp[i] != NULL)
287 			if_free(sc->ifp[i]);
288 		free(sc->ifname[i], M_DEVBUF);
289 	}
290 	bus_generic_detach(dev);
291 	callout_drain(&sc->callout_tick);
292 	mtx_destroy(&sc->callout_mtx);
293 	mtx_destroy(&sc->sc_mtx);
294 
295 	return (0);
296 }
297 
298 static void
299 rtl8366rb_update_ifmedia(int portstatus, u_int *media_status, u_int *media_active)
300 {
301 	*media_active = IFM_ETHER;
302 	*media_status = IFM_AVALID;
303 	if ((portstatus & RTL8366_PLSR_LINK) != 0)
304 		*media_status |= IFM_ACTIVE;
305 	else {
306 		*media_active |= IFM_NONE;
307 		return;
308 	}
309 	switch (portstatus & RTL8366_PLSR_SPEED_MASK) {
310 	case RTL8366_PLSR_SPEED_10:
311 		*media_active |= IFM_10_T;
312 		break;
313 	case RTL8366_PLSR_SPEED_100:
314 		*media_active |= IFM_100_TX;
315 		break;
316 	case RTL8366_PLSR_SPEED_1000:
317 		*media_active |= IFM_1000_T;
318 		break;
319 	}
320 	if ((portstatus & RTL8366_PLSR_FULLDUPLEX) != 0)
321 		*media_active |= IFM_FDX;
322 	else
323 		*media_active |= IFM_HDX;
324 	if ((portstatus & RTL8366_PLSR_TXPAUSE) != 0)
325 		*media_active |= IFM_ETH_TXPAUSE;
326 	if ((portstatus & RTL8366_PLSR_RXPAUSE) != 0)
327 		*media_active |= IFM_ETH_RXPAUSE;
328 }
329 
330 static void
331 rtl833rb_miipollstat(struct rtl8366rb_softc *sc)
332 {
333 	int i;
334 	struct mii_data *mii;
335 	struct mii_softc *miisc;
336 	uint16_t value;
337 	int portstatus;
338 
339 	for (i = 0; i < sc->numphys; i++) {
340 		mii = device_get_softc(sc->miibus[i]);
341 		if ((i % 2) == 0) {
342 			if (smi_read(sc->dev, RTL8366_PLSR_BASE + i/2, &value, RTL_NOWAIT) != 0) {
343 				DEBUG_INCRVAR(callout_blocked);
344 				return;
345 			}
346 			portstatus = value & 0xff;
347 		} else {
348 			portstatus = (value >> 8) & 0xff;
349 		}
350 		rtl8366rb_update_ifmedia(portstatus, &mii->mii_media_status, &mii->mii_media_active);
351 		LIST_FOREACH(miisc, &mii->mii_phys, mii_list) {
352 			if (IFM_INST(mii->mii_media.ifm_cur->ifm_media) != miisc->mii_inst)
353 				continue;
354 			mii_phy_update(miisc, MII_POLLSTAT);
355 		}
356 	}
357 }
358 
359 static void
360 rtl8366rb_tick(void *arg)
361 {
362 	struct rtl8366rb_softc *sc;
363 
364 	sc = arg;
365 
366 	rtl833rb_miipollstat(sc);
367 	callout_reset(&sc->callout_tick, hz, rtl8366rb_tick, sc);
368 }
369 
370 static int
371 smi_probe(device_t dev)
372 {
373 	struct rtl8366rb_softc *sc;
374 	device_t iicbus, iicha;
375 	int err, i, j;
376 	uint16_t chipid;
377 	char bytes[2];
378 	int xferd;
379 
380 	sc = device_get_softc(dev);
381 
382 	iicbus = device_get_parent(dev);
383 	iicha = device_get_parent(iicbus);
384 
385 	for (i = 0; i < 2; ++i) {
386 		iicbus_reset(iicbus, IIC_FASTEST, RTL8366_IIC_ADDR, NULL);
387 		for (j=3; j--; ) {
388 			IICBUS_STOP(iicha);
389 			/*
390 			 * we go directly to the host adapter because iicbus.c
391 			 * only issues a stop on a bus that was successfully started.
392 			 */
393 		}
394 		err = iicbus_request_bus(iicbus, dev, IIC_WAIT);
395 		if (err != 0)
396 			goto out;
397 		err = iicbus_start(iicbus, RTL8366_IIC_ADDR | RTL_IICBUS_READ, RTL_IICBUS_TIMEOUT);
398 		if (err != 0)
399 			goto out;
400 		if (i == 0) {
401 			bytes[0] = RTL8366RB_CIR & 0xff;
402 			bytes[1] = (RTL8366RB_CIR >> 8) & 0xff;
403 		} else {
404 			bytes[0] = RTL8366SR_CIR & 0xff;
405 			bytes[1] = (RTL8366SR_CIR >> 8) & 0xff;
406 		}
407 		err = iicbus_write(iicbus, bytes, 2, &xferd, RTL_IICBUS_TIMEOUT);
408 		if (err != 0)
409 			goto out;
410 		err = iicbus_read(iicbus, bytes, 2, &xferd, IIC_LAST_READ, 0);
411 		if (err != 0)
412 			goto out;
413 		chipid = ((bytes[1] & 0xff) << 8) | (bytes[0] & 0xff);
414 		if (i == 0 && chipid == RTL8366RB_CIR_ID8366RB) {
415 			DPRINTF(dev, "chip id 0x%04x\n", chipid);
416 			sc->chip_type = RTL8366RB;
417 			err = 0;
418 			break;
419 		}
420 		if (i == 1 && chipid == RTL8366SR_CIR_ID8366SR) {
421 			DPRINTF(dev, "chip id 0x%04x\n", chipid);
422 			sc->chip_type = RTL8366SR;
423 			err = 0;
424 			break;
425 		}
426 		if (i == 0) {
427 			iicbus_stop(iicbus);
428 			iicbus_release_bus(iicbus, dev);
429 		}
430 	}
431 	if (i == 2)
432 		err = ENXIO;
433 out:
434 	iicbus_stop(iicbus);
435 	iicbus_release_bus(iicbus, dev);
436 	return (err == 0 ? 0 : ENXIO);
437 }
438 
439 static int
440 smi_acquire(struct rtl8366rb_softc *sc, int sleep)
441 {
442 	int r = 0;
443 	if (sleep == RTL_WAITOK)
444 		RTL_LOCK(sc);
445 	else
446 		if (RTL_TRYLOCK(sc) == 0)
447 			return (EWOULDBLOCK);
448 	if (sc->smi_acquired == RTL_SMI_ACQUIRED)
449 		r = EBUSY;
450 	else {
451 		r = iicbus_request_bus(device_get_parent(sc->dev), sc->dev, \
452 			sleep == RTL_WAITOK ? IIC_WAIT : IIC_DONTWAIT);
453 		if (r == 0)
454 			sc->smi_acquired = RTL_SMI_ACQUIRED;
455 	}
456 	RTL_UNLOCK(sc);
457 	return (r);
458 }
459 
460 static int
461 smi_release(struct rtl8366rb_softc *sc, int sleep)
462 {
463 	if (sleep == RTL_WAITOK)
464 		RTL_LOCK(sc);
465 	else
466 		if (RTL_TRYLOCK(sc) == 0)
467 			return (EWOULDBLOCK);
468 	RTL_SMI_ACQUIRED_ASSERT(sc);
469 	iicbus_release_bus(device_get_parent(sc->dev), sc->dev);
470 	sc->smi_acquired = 0;
471 	RTL_UNLOCK(sc);
472 	return (0);
473 }
474 
475 static int
476 smi_select(device_t dev, int op, int sleep)
477 {
478 	struct rtl8366rb_softc *sc;
479 	int err, i;
480 	device_t iicbus;
481 	struct iicbus_ivar *devi;
482 	int slave;
483 
484 	sc = device_get_softc(dev);
485 
486 	iicbus = device_get_parent(dev);
487 	devi = IICBUS_IVAR(dev);
488 	slave = devi->addr;
489 
490 	RTL_SMI_ACQUIRED_ASSERT((struct rtl8366rb_softc *)device_get_softc(dev));
491 
492 	if (sc->chip_type == RTL8366SR) {   // RTL8366SR work around
493 		// this is same work around at probe
494 		for (int i=3; i--; )
495 			IICBUS_STOP(device_get_parent(device_get_parent(dev)));
496 	}
497 	/*
498 	 * The chip does not use clock stretching when it is busy,
499 	 * instead ignoring the command. Retry a few times.
500 	 */
501 	for (i = RTL_IICBUS_RETRIES; i--; ) {
502 		err = iicbus_start(iicbus, slave | op, RTL_IICBUS_TIMEOUT);
503 		if (err != IIC_ENOACK)
504 			break;
505 		if (sleep == RTL_WAITOK) {
506 			DEBUG_INCRVAR(iic_select_retries);
507 			pause("smi_select", RTL_IICBUS_RETRY_SLEEP);
508 		} else
509 			break;
510 	}
511 	return (err);
512 }
513 
514 static int
515 smi_read_locked(struct rtl8366rb_softc *sc, uint16_t addr, uint16_t *data, int sleep)
516 {
517 	int err;
518 	device_t iicbus;
519 	char bytes[2];
520 	int xferd;
521 
522 	iicbus = device_get_parent(sc->dev);
523 
524 	RTL_SMI_ACQUIRED_ASSERT(sc);
525 	bytes[0] = addr & 0xff;
526 	bytes[1] = (addr >> 8) & 0xff;
527 	err = smi_select(sc->dev, RTL_IICBUS_READ, sleep);
528 	if (err != 0)
529 		goto out;
530 	err = iicbus_write(iicbus, bytes, 2, &xferd, RTL_IICBUS_TIMEOUT);
531 	if (err != 0)
532 		goto out;
533 	err = iicbus_read(iicbus, bytes, 2, &xferd, IIC_LAST_READ, 0);
534 	if (err != 0)
535 		goto out;
536 	*data = ((bytes[1] & 0xff) << 8) | (bytes[0] & 0xff);
537 
538 out:
539 	iicbus_stop(iicbus);
540 	return (err);
541 }
542 
543 static int
544 smi_write_locked(struct rtl8366rb_softc *sc, uint16_t addr, uint16_t data, int sleep)
545 {
546 	int err;
547 	device_t iicbus;
548 	char bytes[4];
549 	int xferd;
550 
551 	iicbus = device_get_parent(sc->dev);
552 
553 	RTL_SMI_ACQUIRED_ASSERT(sc);
554 	bytes[0] = addr & 0xff;
555 	bytes[1] = (addr >> 8) & 0xff;
556 	bytes[2] = data & 0xff;
557 	bytes[3] = (data >> 8) & 0xff;
558 
559 	err = smi_select(sc->dev, RTL_IICBUS_WRITE, sleep);
560 	if (err == 0)
561 		err = iicbus_write(iicbus, bytes, 4, &xferd, RTL_IICBUS_TIMEOUT);
562 	iicbus_stop(iicbus);
563 
564 	return (err);
565 }
566 
567 static int
568 smi_read(device_t dev, uint16_t addr, uint16_t *data, int sleep)
569 {
570 	struct rtl8366rb_softc *sc;
571 	int err;
572 
573 	sc = device_get_softc(dev);
574 
575 	err = smi_acquire(sc, sleep);
576 	if (err != 0)
577 		return (EBUSY);
578 	err = smi_read_locked(sc, addr, data, sleep);
579 	smi_release(sc, sleep);
580 	DEVERR(dev, err, "smi_read()=%d: addr=%04x\n", addr);
581 	return (err == 0 ? 0 : EIO);
582 }
583 
584 static int
585 smi_write(device_t dev, uint16_t addr, uint16_t data, int sleep)
586 {
587 	struct rtl8366rb_softc *sc;
588 	int err;
589 
590 	sc = device_get_softc(dev);
591 
592 	err = smi_acquire(sc, sleep);
593 	if (err != 0)
594 		return (EBUSY);
595 	err = smi_write_locked(sc, addr, data, sleep);
596 	smi_release(sc, sleep);
597 	DEVERR(dev, err, "smi_write()=%d: addr=%04x\n", addr);
598 	return (err == 0 ? 0 : EIO);
599 }
600 
601 static int
602 smi_rmw(device_t dev, uint16_t addr, uint16_t mask, uint16_t data, int sleep)
603 {
604 	struct rtl8366rb_softc *sc;
605 	int err;
606 	uint16_t oldv, newv;
607 
608 	sc = device_get_softc(dev);
609 
610 	err = smi_acquire(sc, sleep);
611 	if (err != 0)
612 		return (EBUSY);
613 	if (err == 0) {
614 		err = smi_read_locked(sc, addr, &oldv, sleep);
615 		if (err == 0) {
616 			newv = oldv & ~mask;
617 			newv |= data & mask;
618 			if (newv != oldv)
619 				err = smi_write_locked(sc, addr, newv, sleep);
620 		}
621 	}
622 	smi_release(sc, sleep);
623 	DEVERR(dev, err, "smi_rmw()=%d: addr=%04x\n", addr);
624 	return (err == 0 ? 0 : EIO);
625 }
626 
627 static etherswitch_info_t *
628 rtl_getinfo(device_t dev)
629 {
630 	struct rtl8366rb_softc *sc;
631 
632 	sc = device_get_softc(dev);
633 
634 	return (&sc->info);
635 }
636 
637 static int
638 rtl_readreg(device_t dev, int reg)
639 {
640 	uint16_t data;
641 
642 	data = 0;
643 
644 	smi_read(dev, reg, &data, RTL_WAITOK);
645 	return (data);
646 }
647 
648 static int
649 rtl_writereg(device_t dev, int reg, int value)
650 {
651 	return (smi_write(dev, reg, value, RTL_WAITOK));
652 }
653 
654 static int
655 rtl_getport(device_t dev, etherswitch_port_t *p)
656 {
657 	struct rtl8366rb_softc *sc;
658 	struct ifmedia *ifm;
659 	struct mii_data *mii;
660 	struct ifmediareq *ifmr;
661 	uint16_t v;
662 	int err, vlangroup;
663 
664 	sc = device_get_softc(dev);
665 
666 	ifmr = &p->es_ifmr;
667 
668 	if (p->es_port < 0 || p->es_port >= (sc->numphys + 1))
669 		return (ENXIO);
670 	if (sc->phy4cpu && p->es_port == sc->numphys) {
671 		vlangroup = RTL8366_PVCR_GET(p->es_port + 1,
672 		    rtl_readreg(dev, RTL8366_PVCR_REG(p->es_port + 1)));
673 	} else {
674 		vlangroup = RTL8366_PVCR_GET(p->es_port,
675 		    rtl_readreg(dev, RTL8366_PVCR_REG(p->es_port)));
676 	}
677 	p->es_pvid = sc->vid[vlangroup] & ETHERSWITCH_VID_MASK;
678 
679 	if (p->es_port < sc->numphys) {
680 		mii = device_get_softc(sc->miibus[p->es_port]);
681 		ifm = &mii->mii_media;
682 		err = ifmedia_ioctl(sc->ifp[p->es_port], &p->es_ifr, ifm, SIOCGIFMEDIA);
683 		if (err)
684 			return (err);
685 	} else {
686 		/* fill in fixed values for CPU port */
687 		p->es_flags |= ETHERSWITCH_PORT_CPU;
688 		smi_read(dev, RTL8366_PLSR_BASE + (RTL8366_NUM_PHYS)/2, &v, RTL_WAITOK);
689 		v = v >> (8 * ((RTL8366_NUM_PHYS) % 2));
690 		rtl8366rb_update_ifmedia(v, &ifmr->ifm_status, &ifmr->ifm_active);
691 		ifmr->ifm_current = ifmr->ifm_active;
692 		ifmr->ifm_mask = 0;
693 		ifmr->ifm_status = IFM_ACTIVE | IFM_AVALID;
694 		/* Return our static media list. */
695 		if (ifmr->ifm_count > 0) {
696 			ifmr->ifm_count = 1;
697 			ifmr->ifm_ulist[0] = IFM_MAKEWORD(IFM_ETHER, IFM_1000_T,
698 			    IFM_FDX, 0);
699 		} else
700 			ifmr->ifm_count = 0;
701 	}
702 	return (0);
703 }
704 
705 static int
706 rtl_setport(device_t dev, etherswitch_port_t *p)
707 {
708 	struct rtl8366rb_softc *sc;
709 	int i, err, vlangroup;
710 	struct ifmedia *ifm;
711 	struct mii_data *mii;
712 	int port;
713 
714 	sc = device_get_softc(dev);
715 
716 	if (p->es_port < 0 || p->es_port >= (sc->numphys + 1))
717 		return (ENXIO);
718 	vlangroup = -1;
719 	for (i = 0; i < RTL8366_NUM_VLANS; i++) {
720 		if ((sc->vid[i] & ETHERSWITCH_VID_MASK) == p->es_pvid) {
721 			vlangroup = i;
722 			break;
723 		}
724 	}
725 	if (vlangroup == -1)
726 		return (ENXIO);
727 	if (sc->phy4cpu && p->es_port == sc->numphys) {
728 		port = p->es_port + 1;
729 	} else {
730 		port = p->es_port;
731 	}
732 	err = smi_rmw(dev, RTL8366_PVCR_REG(port),
733 	    RTL8366_PVCR_VAL(port, RTL8366_PVCR_PORT_MASK),
734 	    RTL8366_PVCR_VAL(port, vlangroup), RTL_WAITOK);
735 	if (err)
736 		return (err);
737 	/* CPU Port */
738 	if (p->es_port == sc->numphys)
739 		return (0);
740 	mii = device_get_softc(sc->miibus[p->es_port]);
741 	ifm = &mii->mii_media;
742 	err = ifmedia_ioctl(sc->ifp[p->es_port], &p->es_ifr, ifm, SIOCSIFMEDIA);
743 	return (err);
744 }
745 
746 static int
747 rtl_getvgroup(device_t dev, etherswitch_vlangroup_t *vg)
748 {
749 	struct rtl8366rb_softc *sc;
750 	uint16_t vmcr[3];
751 	int i;
752 	int member, untagged;
753 
754 	sc = device_get_softc(dev);
755 
756 	for (i=0; i<RTL8366_VMCR_MULT; i++)
757 		vmcr[i] = rtl_readreg(dev, RTL8366_VMCR(i, vg->es_vlangroup));
758 
759 	vg->es_vid = sc->vid[vg->es_vlangroup];
760 	member = RTL8366_VMCR_MEMBER(vmcr);
761 	untagged = RTL8366_VMCR_UNTAG(vmcr);
762 	if (sc->phy4cpu) {
763 		vg->es_member_ports = ((member & 0x20) >> 1) | (member & 0x0f);
764 		vg->es_untagged_ports = ((untagged & 0x20) >> 1) | (untagged & 0x0f);
765 	} else {
766 		vg->es_member_ports = member;
767 		vg->es_untagged_ports = untagged;
768 	}
769 	vg->es_fid = RTL8366_VMCR_FID(vmcr);
770 	return (0);
771 }
772 
773 static int
774 rtl_setvgroup(device_t dev, etherswitch_vlangroup_t *vg)
775 {
776 	struct rtl8366rb_softc *sc;
777 	int g;
778 	int member, untagged;
779 
780 	sc = device_get_softc(dev);
781 
782 	g = vg->es_vlangroup;
783 
784 	sc->vid[g] = vg->es_vid;
785 	/* VLAN group disabled ? */
786 	if (vg->es_member_ports == 0 && vg->es_untagged_ports == 0 && vg->es_vid == 0)
787 		return (0);
788 	sc->vid[g] |= ETHERSWITCH_VID_VALID;
789 	rtl_writereg(dev, RTL8366_VMCR(RTL8366_VMCR_DOT1Q_REG, g),
790 		(vg->es_vid << RTL8366_VMCR_DOT1Q_VID_SHIFT) & RTL8366_VMCR_DOT1Q_VID_MASK);
791 	if (sc->phy4cpu) {
792 		/* add space at phy4 */
793 		member = (vg->es_member_ports & 0x0f) |
794 		    ((vg->es_member_ports & 0x10) << 1);
795 		untagged = (vg->es_untagged_ports & 0x0f) |
796 		    ((vg->es_untagged_ports & 0x10) << 1);
797 	} else {
798 		member = vg->es_member_ports;
799 		untagged = vg->es_untagged_ports;
800 	}
801 	if (sc->chip_type == RTL8366RB) {
802 		rtl_writereg(dev, RTL8366_VMCR(RTL8366_VMCR_MU_REG, g),
803 	 	    ((member << RTL8366_VMCR_MU_MEMBER_SHIFT) & RTL8366_VMCR_MU_MEMBER_MASK) |
804 		    ((untagged << RTL8366_VMCR_MU_UNTAG_SHIFT) & RTL8366_VMCR_MU_UNTAG_MASK));
805 		rtl_writereg(dev, RTL8366_VMCR(RTL8366_VMCR_FID_REG, g),
806 		    vg->es_fid);
807 	} else {
808 		rtl_writereg(dev, RTL8366_VMCR(RTL8366_VMCR_MU_REG, g),
809 		    ((member << RTL8366_VMCR_MU_MEMBER_SHIFT) & RTL8366_VMCR_MU_MEMBER_MASK) |
810 		    ((untagged << RTL8366_VMCR_MU_UNTAG_SHIFT) & RTL8366_VMCR_MU_UNTAG_MASK) |
811 		    ((vg->es_fid << RTL8366_VMCR_FID_FID_SHIFT) & RTL8366_VMCR_FID_FID_MASK));
812 	}
813 	return (0);
814 }
815 
816 static int
817 rtl_getconf(device_t dev, etherswitch_conf_t *conf)
818 {
819 
820 	/* Return the VLAN mode. */
821 	conf->cmd = ETHERSWITCH_CONF_VLAN_MODE;
822 	conf->vlan_mode = ETHERSWITCH_VLAN_DOT1Q;
823 
824 	return (0);
825 }
826 
827 static int
828 rtl_readphy(device_t dev, int phy, int reg)
829 {
830 	struct rtl8366rb_softc *sc;
831 	uint16_t data;
832 	int err, i, sleep;
833 
834 	sc = device_get_softc(dev);
835 
836 	data = 0;
837 
838 	if (phy < 0 || phy >= RTL8366_NUM_PHYS)
839 		return (ENXIO);
840 	if (reg < 0 || reg >= RTL8366_NUM_PHY_REG)
841 		return (ENXIO);
842 	sleep = RTL_WAITOK;
843 	err = smi_acquire(sc, sleep);
844 	if (err != 0)
845 		return (EBUSY);
846 	for (i = RTL_IICBUS_RETRIES; i--; ) {
847 		err = smi_write_locked(sc, RTL8366_PACR, RTL8366_PACR_READ, sleep);
848 		if (err == 0)
849 			err = smi_write_locked(sc, RTL8366_PHYREG(phy, 0, reg), 0, sleep);
850 		if (err == 0) {
851 			err = smi_read_locked(sc, RTL8366_PADR, &data, sleep);
852 			break;
853 		}
854 		DEBUG_INCRVAR(phy_access_retries);
855 		DPRINTF(dev, "rtl_readphy(): chip not responsive, retrying %d more times\n", i);
856 		pause("rtl_readphy", RTL_IICBUS_RETRY_SLEEP);
857 	}
858 	smi_release(sc, sleep);
859 	DEVERR(dev, err, "rtl_readphy()=%d: phy=%d.%02x\n", phy, reg);
860 	return (data);
861 }
862 
863 static int
864 rtl_writephy(device_t dev, int phy, int reg, int data)
865 {
866 	struct rtl8366rb_softc *sc;
867 	int err, i, sleep;
868 
869 	sc = device_get_softc(dev);
870 
871 	if (phy < 0 || phy >= RTL8366_NUM_PHYS)
872 		return (ENXIO);
873 	if (reg < 0 || reg >= RTL8366_NUM_PHY_REG)
874 		return (ENXIO);
875 	sleep = RTL_WAITOK;
876 	err = smi_acquire(sc, sleep);
877 	if (err != 0)
878 		return (EBUSY);
879 	for (i = RTL_IICBUS_RETRIES; i--; ) {
880 		err = smi_write_locked(sc, RTL8366_PACR, RTL8366_PACR_WRITE, sleep);
881 		if (err == 0)
882 			err = smi_write_locked(sc, RTL8366_PHYREG(phy, 0, reg), data, sleep);
883 		if (err == 0) {
884 			break;
885 		}
886 		DEBUG_INCRVAR(phy_access_retries);
887 		DPRINTF(dev, "rtl_writephy(): chip not responsive, retrying %d more tiems\n", i);
888 		pause("rtl_writephy", RTL_IICBUS_RETRY_SLEEP);
889 	}
890 	smi_release(sc, sleep);
891 	DEVERR(dev, err, "rtl_writephy()=%d: phy=%d.%02x\n", phy, reg);
892 	return (err == 0 ? 0 : EIO);
893 }
894 
895 static int
896 rtl8366rb_ifmedia_upd(if_t ifp)
897 {
898 	struct rtl8366rb_softc *sc;
899 	struct mii_data *mii;
900 
901 	sc = if_getsoftc(ifp);
902 	mii = device_get_softc(sc->miibus[if_getdunit(ifp)]);
903 
904 	mii_mediachg(mii);
905 	return (0);
906 }
907 
908 static void
909 rtl8366rb_ifmedia_sts(if_t ifp, struct ifmediareq *ifmr)
910 {
911 	struct rtl8366rb_softc *sc;
912 	struct mii_data *mii;
913 
914 	sc = if_getsoftc(ifp);
915 	mii = device_get_softc(sc->miibus[if_getdunit(ifp)]);
916 
917 	mii_pollstat(mii);
918 	ifmr->ifm_active = mii->mii_media_active;
919 	ifmr->ifm_status = mii->mii_media_status;
920 }
921 
922 
923 static device_method_t rtl8366rb_methods[] = {
924 	/* Device interface */
925 	DEVMETHOD(device_identify,	rtl8366rb_identify),
926 	DEVMETHOD(device_probe,		rtl8366rb_probe),
927 	DEVMETHOD(device_attach,	rtl8366rb_attach),
928 	DEVMETHOD(device_detach,	rtl8366rb_detach),
929 
930 	/* bus interface */
931 	DEVMETHOD(bus_add_child,	device_add_child_ordered),
932 
933 	/* MII interface */
934 	DEVMETHOD(miibus_readreg,	rtl_readphy),
935 	DEVMETHOD(miibus_writereg,	rtl_writephy),
936 
937 	/* MDIO interface */
938 	DEVMETHOD(mdio_readreg,         rtl_readphy),
939 	DEVMETHOD(mdio_writereg,        rtl_writephy),
940 
941 	/* etherswitch interface */
942 	DEVMETHOD(etherswitch_getconf,	rtl_getconf),
943 	DEVMETHOD(etherswitch_getinfo,	rtl_getinfo),
944 	DEVMETHOD(etherswitch_readreg,	rtl_readreg),
945 	DEVMETHOD(etherswitch_writereg,	rtl_writereg),
946 	DEVMETHOD(etherswitch_readphyreg,	rtl_readphy),
947 	DEVMETHOD(etherswitch_writephyreg,	rtl_writephy),
948 	DEVMETHOD(etherswitch_getport,	rtl_getport),
949 	DEVMETHOD(etherswitch_setport,	rtl_setport),
950 	DEVMETHOD(etherswitch_getvgroup,	rtl_getvgroup),
951 	DEVMETHOD(etherswitch_setvgroup,	rtl_setvgroup),
952 
953 	DEVMETHOD_END
954 };
955 
956 DEFINE_CLASS_0(rtl8366rb, rtl8366rb_driver, rtl8366rb_methods,
957     sizeof(struct rtl8366rb_softc));
958 
959 DRIVER_MODULE(rtl8366rb, iicbus, rtl8366rb_driver, 0, 0);
960 DRIVER_MODULE(miibus, rtl8366rb, miibus_driver, 0, 0);
961 DRIVER_MODULE(mdio, rtl8366rb, mdio_driver, 0, 0);
962 DRIVER_MODULE(etherswitch, rtl8366rb, etherswitch_driver, 0, 0);
963 MODULE_VERSION(rtl8366rb, 1);
964 MODULE_DEPEND(rtl8366rb, iicbus, 1, 1, 1); /* XXX which versions? */
965 MODULE_DEPEND(rtl8366rb, miibus, 1, 1, 1); /* XXX which versions? */
966 MODULE_DEPEND(rtl8366rb, etherswitch, 1, 1, 1); /* XXX which versions? */
967