xref: /openbsd-src/sys/dev/usb/if_url.c (revision db3296cf5c1dd9058ceecc3a29fe4aaa0bd26000)
1 /*	$OpenBSD: if_url.c,v 1.11 2003/05/07 04:33:33 deraadt Exp $ */
2 /*	$NetBSD: if_url.c,v 1.6 2002/09/29 10:19:21 martin Exp $	*/
3 /*
4  * Copyright (c) 2001, 2002
5  *     Shingo WATANABE <nabe@nabechan.org>.  All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  * 3. All advertising materials mentioning features or use of this software
16  *    must display the following acknowledgement:
17  *	This product includes software developed by Shingo WATANABE.
18  * 4. Neither the name of the author nor the names of any co-contributors
19  *    may be used to endorse or promote products derived from this software
20  *    without specific prior written permission.
21  *
22  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
23  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
26  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32  * SUCH DAMAGE.
33  *
34  */
35 
36 /*
37  * The RTL8150L(Realtek USB to fast ethernet controller) spec can be found at
38  *   ftp://ftp.realtek.com.tw/lancard/data_sheet/8150/8150v14.pdf
39  *   ftp://152.104.125.40/lancard/data_sheet/8150/8150v14.pdf
40  */
41 
42 /*
43  * TODO:
44  *	Interrupt Endpoint support
45  *	External PHYs
46  *	powerhook() support?
47  */
48 
49 #if defined(__NetBSD__)
50 #include "opt_inet.h"
51 #include "opt_ns.h"
52 #include "rnd.h"
53 #endif
54 
55 #include "bpfilter.h"
56 
57 #include <sys/param.h>
58 #include <sys/systm.h>
59 #include <sys/lock.h>
60 #include <sys/mbuf.h>
61 #include <sys/kernel.h>
62 #if defined(__OpenBSD__)
63 #include <sys/proc.h>
64 #endif
65 #include <sys/socket.h>
66 
67 #include <sys/device.h>
68 #if NRND > 0
69 #include <sys/rnd.h>
70 #endif
71 
72 #include <net/if.h>
73 #include <net/if_arp.h>
74 #include <net/if_dl.h>
75 #include <net/if_media.h>
76 
77 #if NBPFILTER > 0
78 #include <net/bpf.h>
79 #endif
80 #define	BPF_MTAP(ifp, m)	bpf_mtap((ifp)->if_bpf, (m))
81 
82 #if defined(__NetBSD__)
83 #include <net/if_ether.h>
84 #ifdef INET
85 #include <netinet/in.h>
86 #include <netinet/if_inarp.h>
87 #endif
88 #endif /* defined(__NetBSD__) */
89 
90 #if defined(__OpenBSD__)
91 #ifdef INET
92 #include <netinet/in.h>
93 #include <netinet/in_systm.h>
94 #include <netinet/in_var.h>
95 #include <netinet/ip.h>
96 #include <netinet/if_ether.h>
97 #endif
98 #endif /* defined(__OpenBSD__) */
99 
100 #ifdef NS
101 #include <netns/ns.h>
102 #include <netns/ns_if.h>
103 #endif
104 
105 #include <dev/mii/mii.h>
106 #include <dev/mii/miivar.h>
107 #include <dev/mii/urlphyreg.h>
108 
109 #include <dev/usb/usb.h>
110 #include <dev/usb/usbdi.h>
111 #include <dev/usb/usbdi_util.h>
112 #include <dev/usb/usbdevs.h>
113 
114 #include <dev/usb/if_urlreg.h>
115 
116 
117 /* Function declarations */
118 USB_DECLARE_DRIVER(url);
119 
120 Static int url_openpipes(struct url_softc *);
121 Static int url_rx_list_init(struct url_softc *);
122 Static int url_tx_list_init(struct url_softc *);
123 Static int url_newbuf(struct url_softc *, struct url_chain *, struct mbuf *);
124 Static void url_start(struct ifnet *);
125 Static int url_send(struct url_softc *, struct mbuf *, int);
126 Static void url_txeof(usbd_xfer_handle, usbd_private_handle, usbd_status);
127 Static void url_rxeof(usbd_xfer_handle, usbd_private_handle, usbd_status);
128 Static void url_tick(void *);
129 Static void url_tick_task(void *);
130 Static int url_ioctl(struct ifnet *, u_long, caddr_t);
131 Static void url_stop_task(struct url_softc *);
132 Static void url_stop(struct ifnet *, int);
133 Static void url_watchdog(struct ifnet *);
134 Static int url_ifmedia_change(struct ifnet *);
135 Static void url_ifmedia_status(struct ifnet *, struct ifmediareq *);
136 Static void url_lock_mii(struct url_softc *);
137 Static void url_unlock_mii(struct url_softc *);
138 Static int url_int_miibus_readreg(device_ptr_t, int, int);
139 Static void url_int_miibus_writereg(device_ptr_t, int, int, int);
140 Static void url_miibus_statchg(device_ptr_t);
141 Static int url_init(struct ifnet *);
142 Static void url_setmulti(struct url_softc *);
143 Static void url_reset(struct url_softc *);
144 
145 Static int url_csr_read_1(struct url_softc *, int);
146 Static int url_csr_read_2(struct url_softc *, int);
147 Static int url_csr_write_1(struct url_softc *, int, int);
148 Static int url_csr_write_2(struct url_softc *, int, int);
149 Static int url_csr_write_4(struct url_softc *, int, int);
150 Static int url_mem(struct url_softc *, int, int, void *, int);
151 
152 /* Macros */
153 #ifdef URL_DEBUG
154 #define DPRINTF(x)	if (urldebug) logprintf x
155 #define DPRINTFN(n,x)	if (urldebug >= (n)) logprintf x
156 int urldebug = 0;
157 #else
158 #define DPRINTF(x)
159 #define DPRINTFN(n,x)
160 #endif
161 
162 #define	URL_SETBIT(sc, reg, x)	\
163 	url_csr_write_1(sc, reg, url_csr_read_1(sc, reg) | (x))
164 
165 #define	URL_SETBIT2(sc, reg, x)	\
166 	url_csr_write_2(sc, reg, url_csr_read_2(sc, reg) | (x))
167 
168 #define	URL_CLRBIT(sc, reg, x)	\
169 	url_csr_write_1(sc, reg, url_csr_read_1(sc, reg) & ~(x))
170 
171 #define	URL_CLRBIT2(sc, reg, x)	\
172 	url_csr_write_2(sc, reg, url_csr_read_2(sc, reg) & ~(x))
173 
174 static const struct url_type {
175 	struct usb_devno url_dev;
176 	u_int16_t url_flags;
177 #define URL_EXT_PHY	0x0001
178 } url_devs [] = {
179 	/* MELCO LUA-KTX */
180 	{{ USB_VENDOR_MELCO, USB_PRODUCT_MELCO_LUAKTX }, 0},
181 	/* GREEN HOUSE USBKR100 */
182 	{{ USB_VENDOR_GREENHOUSE2, USB_PRODUCT_GREENHOUSE2_USBKR100}, 0}
183 };
184 #define url_lookup(v, p) ((struct url_type *)usb_lookup(url_devs, v, p))
185 
186 
187 /* Probe */
188 USB_MATCH(url)
189 {
190 	USB_MATCH_START(url, uaa);
191 
192 	if (uaa->iface != NULL)
193 		return (UMATCH_NONE);
194 
195 	return (url_lookup(uaa->vendor, uaa->product) != NULL ?
196 		UMATCH_VENDOR_PRODUCT : UMATCH_NONE);
197 }
198 /* Attach */
199 USB_ATTACH(url)
200 {
201 	USB_ATTACH_START(url, sc, uaa);
202 	usbd_device_handle dev = uaa->device;
203 	usbd_interface_handle iface;
204 	usbd_status err;
205 	usb_interface_descriptor_t *id;
206 	usb_endpoint_descriptor_t *ed;
207 	char devinfo[1024];
208 	char *devname = USBDEVNAME(sc->sc_dev);
209 	struct ifnet *ifp;
210 	struct mii_data *mii;
211 	u_char eaddr[ETHER_ADDR_LEN];
212 	int i, s;
213 
214 	usbd_devinfo(dev, 0, devinfo, sizeof devinfo);
215 	USB_ATTACH_SETUP;
216 	printf("%s: %s\n", devname, devinfo);
217 
218 	/* Move the device into the configured state. */
219 	err = usbd_set_config_no(dev, URL_CONFIG_NO, 1);
220 	if (err) {
221 		printf("%s: setting config no failed\n", devname);
222 		goto bad;
223 	}
224 
225 	usb_init_task(&sc->sc_tick_task, url_tick_task, sc);
226 	lockinit(&sc->sc_mii_lock, PZERO, "urlmii", 0, 0);
227 	usb_init_task(&sc->sc_stop_task, (void (*)(void *)) url_stop_task, sc);
228 
229 	/* get control interface */
230 	err = usbd_device2interface_handle(dev, URL_IFACE_INDEX, &iface);
231 	if (err) {
232 		printf("%s: failed to get interface, err=%s\n", devname,
233 		       usbd_errstr(err));
234 		goto bad;
235 	}
236 
237 	sc->sc_udev = dev;
238 	sc->sc_ctl_iface = iface;
239 	sc->sc_flags = url_lookup(uaa->vendor, uaa->product)->url_flags;
240 
241 	/* get interface descriptor */
242 	id = usbd_get_interface_descriptor(sc->sc_ctl_iface);
243 
244 	/* find endpoints */
245 	sc->sc_bulkin_no = sc->sc_bulkout_no = sc->sc_intrin_no = -1;
246 	for (i = 0; i < id->bNumEndpoints; i++) {
247 		ed = usbd_interface2endpoint_descriptor(sc->sc_ctl_iface, i);
248 		if (ed == NULL) {
249 			printf("%s: couldn't get endpoint %d\n", devname, i);
250 			goto bad;
251 		}
252 		if ((ed->bmAttributes & UE_XFERTYPE) == UE_BULK &&
253 		    UE_GET_DIR(ed->bEndpointAddress) == UE_DIR_IN)
254 			sc->sc_bulkin_no = ed->bEndpointAddress; /* RX */
255 		else if ((ed->bmAttributes & UE_XFERTYPE) == UE_BULK &&
256 			 UE_GET_DIR(ed->bEndpointAddress) == UE_DIR_OUT)
257 			sc->sc_bulkout_no = ed->bEndpointAddress; /* TX */
258 		else if ((ed->bmAttributes & UE_XFERTYPE) == UE_INTERRUPT &&
259 			 UE_GET_DIR(ed->bEndpointAddress) == UE_DIR_IN)
260 			sc->sc_intrin_no = ed->bEndpointAddress; /* Status */
261 	}
262 
263 	if (sc->sc_bulkin_no == -1 || sc->sc_bulkout_no == -1 ||
264 	    sc->sc_intrin_no == -1) {
265 		printf("%s: missing endpoint\n", devname);
266 		goto bad;
267 	}
268 
269 	s = splnet();
270 
271 	/* reset the adapter */
272 	url_reset(sc);
273 
274 	/* Get Ethernet Address */
275 	err = url_mem(sc, URL_CMD_READMEM, URL_IDR0, (void *)eaddr,
276 		      ETHER_ADDR_LEN);
277 	if (err) {
278 		printf("%s: read MAC address failed\n", devname);
279 		splx(s);
280 		goto bad;
281 	}
282 
283 	/* Print Ethernet Address */
284 	printf("%s: address %s\n", devname, ether_sprintf(eaddr));
285 
286 	/* initialize interface infomation */
287 	ifp = GET_IFP(sc);
288 	ifp->if_softc = sc;
289 	ifp->if_mtu = ETHERMTU;
290 	strncpy(ifp->if_xname, devname, IFNAMSIZ);
291 	ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
292 	ifp->if_start = url_start;
293 	ifp->if_ioctl = url_ioctl;
294 	ifp->if_watchdog = url_watchdog;
295 #if defined(__NetBSD__)
296 	ifp->if_init = url_init;
297 	ifp->if_stop = url_stop;
298 #endif
299 
300 	IFQ_SET_READY(&ifp->if_snd);
301 
302 	/*
303 	 * Do ifmedia setup.
304 	 */
305 	mii = &sc->sc_mii;
306 	mii->mii_ifp = ifp;
307 	mii->mii_readreg = url_int_miibus_readreg;
308 	mii->mii_writereg = url_int_miibus_writereg;
309 #if 0
310 	if (sc->sc_flags & URL_EXT_PHY) {
311 		mii->mii_readreg = url_ext_miibus_readreg;
312 		mii->mii_writereg = url_ext_miibus_writereg;
313 	}
314 #endif
315 	mii->mii_statchg = url_miibus_statchg;
316 	mii->mii_flags = MIIF_AUTOTSLEEP;
317 	ifmedia_init(&mii->mii_media, 0,
318 		     url_ifmedia_change, url_ifmedia_status);
319 	mii_attach(self, mii, 0xffffffff, MII_PHY_ANY, MII_OFFSET_ANY, 0);
320 	if (LIST_FIRST(&mii->mii_phys) == NULL) {
321 		ifmedia_add(&mii->mii_media, IFM_ETHER | IFM_NONE, 0, NULL);
322 		ifmedia_set(&mii->mii_media, IFM_ETHER | IFM_NONE);
323 	} else
324 		ifmedia_set(&mii->mii_media, IFM_ETHER | IFM_AUTO);
325 
326 	/* attach the interface */
327 	if_attach(ifp);
328 	Ether_ifattach(ifp, eaddr);
329 
330 #if NRND > 0
331 	rnd_attach_source(&sc->rnd_source, devname, RND_TYPE_NET, 0);
332 #endif
333 
334 	usb_callout_init(sc->sc_stat_ch);
335 	sc->sc_attached = 1;
336 	splx(s);
337 
338 	usbd_add_drv_event(USB_EVENT_DRIVER_ATTACH, dev, USBDEV(sc->sc_dev));
339 
340 	USB_ATTACH_SUCCESS_RETURN;
341 
342  bad:
343 	sc->sc_dying = 1;
344 	USB_ATTACH_ERROR_RETURN;
345 }
346 
347 /* detach */
348 USB_DETACH(url)
349 {
350 	USB_DETACH_START(url, sc);
351 	struct ifnet *ifp = GET_IFP(sc);
352 	int s;
353 
354 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
355 
356 	/* Detached before attached finished */
357 	if (!sc->sc_attached)
358 		return (0);
359 
360 	usb_uncallout(sc->sc_stat_ch, url_tick, sc);
361 
362 	/* Remove any pending tasks */
363 	usb_rem_task(sc->sc_udev, &sc->sc_tick_task);
364 	usb_rem_task(sc->sc_udev, &sc->sc_stop_task);
365 
366 	s = splusb();
367 
368 	if (--sc->sc_refcnt >= 0) {
369 		/* Wait for processes to go away */
370 		usb_detach_wait(USBDEV(sc->sc_dev));
371 	}
372 
373 	if (ifp->if_flags & IFF_RUNNING)
374 		url_stop(GET_IFP(sc), 1);
375 
376 #if NRND > 0
377 	rnd_detach_source(&sc->rnd_source);
378 #endif
379 	mii_detach(&sc->sc_mii, MII_PHY_ANY, MII_OFFSET_ANY);
380 	ifmedia_delete_instance(&sc->sc_mii.mii_media, IFM_INST_ANY);
381 	ether_ifdetach(ifp);
382 	if_detach(ifp);
383 
384 #ifdef DIAGNOSTIC
385 	if (sc->sc_pipe_tx != NULL)
386 		printf("%s: detach has active tx endpoint.\n",
387 		       USBDEVNAME(sc->sc_dev));
388 	if (sc->sc_pipe_rx != NULL)
389 		printf("%s: detach has active rx endpoint.\n",
390 		       USBDEVNAME(sc->sc_dev));
391 	if (sc->sc_pipe_intr != NULL)
392 		printf("%s: detach has active intr endpoint.\n",
393 		       USBDEVNAME(sc->sc_dev));
394 #endif
395 
396 	sc->sc_attached = 0;
397 
398 	splx(s);
399 
400 	usbd_add_drv_event(USB_EVENT_DRIVER_DETACH, sc->sc_udev,
401 			   USBDEV(sc->sc_dev));
402 
403 	return (0);
404 }
405 
406 /* read/write memory */
407 Static int
408 url_mem(struct url_softc *sc, int cmd, int offset, void *buf, int len)
409 {
410 	usb_device_request_t req;
411 	usbd_status err;
412 
413 	if (sc == NULL)
414 		return (0);
415 
416 	DPRINTFN(0x200,
417 		("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
418 
419 	if (sc->sc_dying)
420 		return (0);
421 
422 	if (cmd == URL_CMD_READMEM)
423 		req.bmRequestType = UT_READ_VENDOR_DEVICE;
424 	else
425 		req.bmRequestType = UT_WRITE_VENDOR_DEVICE;
426 	req.bRequest = URL_REQ_MEM;
427 	USETW(req.wValue, offset);
428 	USETW(req.wIndex, 0x0000);
429 	USETW(req.wLength, len);
430 
431 	sc->sc_refcnt++;
432 	err = usbd_do_request(sc->sc_udev, &req, buf);
433 	if (--sc->sc_refcnt < 0)
434 		usb_detach_wakeup(USBDEV(sc->sc_dev));
435 	if (err) {
436 		DPRINTF(("%s: url_mem(): %s failed. off=%04x, err=%d\n",
437 			 USBDEVNAME(sc->sc_dev),
438 			 cmd == URL_CMD_READMEM ? "read" : "write",
439 			 offset, err));
440 	}
441 
442 	return (err);
443 }
444 
445 /* read 1byte from register */
446 Static int
447 url_csr_read_1(struct url_softc *sc, int reg)
448 {
449 	u_int8_t val = 0;
450 
451 	DPRINTFN(0x100,
452 		 ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
453 
454 	if (sc->sc_dying)
455 		return (0);
456 
457 	return (url_mem(sc, URL_CMD_READMEM, reg, &val, 1) ? 0 : val);
458 }
459 
460 /* read 2bytes from register */
461 Static int
462 url_csr_read_2(struct url_softc *sc, int reg)
463 {
464 	uWord val;
465 
466 	DPRINTFN(0x100,
467 		 ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
468 
469 	if (sc->sc_dying)
470 		return (0);
471 
472 	USETW(val, 0);
473 	return (url_mem(sc, URL_CMD_READMEM, reg, &val, 2) ? 0 : UGETW(val));
474 }
475 
476 /* write 1byte to register */
477 Static int
478 url_csr_write_1(struct url_softc *sc, int reg, int aval)
479 {
480 	u_int8_t val = aval;
481 
482 	DPRINTFN(0x100,
483 		 ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
484 
485 	if (sc->sc_dying)
486 		return (0);
487 
488 	return (url_mem(sc, URL_CMD_WRITEMEM, reg, &val, 1) ? -1 : 0);
489 }
490 
491 /* write 2bytes to register */
492 Static int
493 url_csr_write_2(struct url_softc *sc, int reg, int aval)
494 {
495 	uWord val;
496 
497 	DPRINTFN(0x100,
498 		 ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
499 
500 	USETW(val, aval);
501 
502 	if (sc->sc_dying)
503 		return (0);
504 
505 	return (url_mem(sc, URL_CMD_WRITEMEM, reg, &val, 2) ? -1 : 0);
506 }
507 
508 /* write 4bytes to register */
509 Static int
510 url_csr_write_4(struct url_softc *sc, int reg, int aval)
511 {
512 	uDWord val;
513 
514 	DPRINTFN(0x100,
515 		 ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
516 
517 	USETDW(val, aval);
518 
519 	if (sc->sc_dying)
520 		return (0);
521 
522 	return (url_mem(sc, URL_CMD_WRITEMEM, reg, &val, 4) ? -1 : 0);
523 }
524 
525 Static int
526 url_init(struct ifnet *ifp)
527 {
528 	struct url_softc *sc = ifp->if_softc;
529 	struct mii_data *mii = GET_MII(sc);
530 	u_char *eaddr;
531 	int i, s;
532 
533 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
534 
535 	if (sc->sc_dying)
536 		return (EIO);
537 
538 	s = splnet();
539 
540 	/* Cancel pending I/O and free all TX/RX buffers */
541 	url_stop(ifp, 1);
542 
543 #if defined(__OpenBSD__)
544 	eaddr = sc->sc_ac.ac_enaddr;
545 #elif defined(__NetBSD__)
546 	eaddr = LLADDR(ifp->if_sadl);
547 #endif
548 	for (i = 0; i < ETHER_ADDR_LEN; i++)
549 		url_csr_write_1(sc, URL_IDR0 + i, eaddr[i]);
550 
551 	/* Init transmission control register */
552 	URL_CLRBIT(sc, URL_TCR,
553 		   URL_TCR_TXRR1 | URL_TCR_TXRR0 |
554 		   URL_TCR_IFG1 | URL_TCR_IFG0 |
555 		   URL_TCR_NOCRC);
556 
557 	/* Init receive control register */
558 	URL_SETBIT2(sc, URL_RCR, URL_RCR_TAIL | URL_RCR_AD);
559 	if (ifp->if_flags & IFF_BROADCAST)
560 		URL_SETBIT2(sc, URL_RCR, URL_RCR_AB);
561 	else
562 		URL_CLRBIT2(sc, URL_RCR, URL_RCR_AB);
563 
564 	/* If we want promiscuous mode, accept all physical frames. */
565 	if (ifp->if_flags & IFF_PROMISC)
566 		URL_SETBIT2(sc, URL_RCR, URL_RCR_AAM|URL_RCR_AAP);
567 	else
568 		URL_CLRBIT2(sc, URL_RCR, URL_RCR_AAM|URL_RCR_AAP);
569 
570 
571 	/* Initialize transmit ring */
572 	if (url_tx_list_init(sc) == ENOBUFS) {
573 		printf("%s: tx list init failed\n", USBDEVNAME(sc->sc_dev));
574 		splx(s);
575 		return (EIO);
576 	}
577 
578 	/* Initialize receive ring */
579 	if (url_rx_list_init(sc) == ENOBUFS) {
580 		printf("%s: rx list init failed\n", USBDEVNAME(sc->sc_dev));
581 		splx(s);
582 		return (EIO);
583 	}
584 
585 	/* Load the multicast filter */
586 	url_setmulti(sc);
587 
588 	/* Enable RX and TX */
589 	URL_SETBIT(sc, URL_CR, URL_CR_TE | URL_CR_RE);
590 
591 	mii_mediachg(mii);
592 
593 	if (sc->sc_pipe_tx == NULL || sc->sc_pipe_rx == NULL) {
594 		if (url_openpipes(sc)) {
595 			splx(s);
596 			return (EIO);
597 		}
598 	}
599 
600 	ifp->if_flags |= IFF_RUNNING;
601 	ifp->if_flags &= ~IFF_OACTIVE;
602 
603 	splx(s);
604 
605 	usb_callout(sc->sc_stat_ch, hz, url_tick, sc);
606 
607 	return (0);
608 }
609 
610 Static void
611 url_reset(struct url_softc *sc)
612 {
613 	int i;
614 
615 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
616 
617 	if (sc->sc_dying)
618 		return;
619 
620 	URL_SETBIT(sc, URL_CR, URL_CR_SOFT_RST);
621 
622 	for (i = 0; i < URL_TX_TIMEOUT; i++) {
623 		if (!(url_csr_read_1(sc, URL_CR) & URL_CR_SOFT_RST))
624 			break;
625 		delay(10);	/* XXX */
626 	}
627 
628 	delay(10000);		/* XXX */
629 }
630 
631 int
632 url_activate(device_ptr_t self, enum devact act)
633 {
634 	struct url_softc *sc = (struct url_softc *)self;
635 
636 	DPRINTF(("%s: %s: enter, act=%d\n", USBDEVNAME(sc->sc_dev),
637 		 __func__, act));
638 
639 	switch (act) {
640 	case DVACT_ACTIVATE:
641 		return (EOPNOTSUPP);
642 		break;
643 
644 	case DVACT_DEACTIVATE:
645 		if_deactivate(GET_IFP(sc));
646 		sc->sc_dying = 1;
647 		break;
648 	}
649 
650 	return (0);
651 }
652 
653 #define url_calchash(addr) (ether_crc32_be((addr), ETHER_ADDR_LEN) >> 26)
654 
655 
656 Static void
657 url_setmulti(struct url_softc *sc)
658 {
659 	struct ifnet *ifp;
660 	struct ether_multi *enm;
661 	struct ether_multistep step;
662 	u_int32_t hashes[2] = { 0, 0 };
663 	int h = 0;
664 	int mcnt = 0;
665 
666 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
667 
668 	if (sc->sc_dying)
669 		return;
670 
671 	ifp = GET_IFP(sc);
672 
673 	if (ifp->if_flags & IFF_PROMISC) {
674 		URL_SETBIT2(sc, URL_RCR, URL_RCR_AAM|URL_RCR_AAP);
675 		return;
676 	} else if (ifp->if_flags & IFF_ALLMULTI) {
677 	allmulti:
678 		ifp->if_flags |= IFF_ALLMULTI;
679 		URL_SETBIT2(sc, URL_RCR, URL_RCR_AAM);
680 		URL_CLRBIT2(sc, URL_RCR, URL_RCR_AAP);
681 		return;
682 	}
683 
684 	/* first, zot all the existing hash bits */
685 	url_csr_write_4(sc, URL_MAR0, 0);
686 	url_csr_write_4(sc, URL_MAR4, 0);
687 
688 	/* now program new ones */
689 	ETHER_FIRST_MULTI(step, &sc->sc_ac, enm);
690 	while (enm != NULL) {
691 		if (memcmp(enm->enm_addrlo, enm->enm_addrhi,
692 			   ETHER_ADDR_LEN) != 0)
693 			goto allmulti;
694 
695 		h = url_calchash(enm->enm_addrlo);
696 		if (h < 32)
697 			hashes[0] |= (1 << h);
698 		else
699 			hashes[1] |= (1 << (h -32));
700 		mcnt++;
701 		ETHER_NEXT_MULTI(step, enm);
702 	}
703 
704 	ifp->if_flags &= ~IFF_ALLMULTI;
705 
706 	URL_CLRBIT2(sc, URL_RCR, URL_RCR_AAM|URL_RCR_AAP);
707 
708 	if (mcnt){
709 		URL_SETBIT2(sc, URL_RCR, URL_RCR_AM);
710 	} else {
711 		URL_CLRBIT2(sc, URL_RCR, URL_RCR_AM);
712 	}
713 	url_csr_write_4(sc, URL_MAR0, hashes[0]);
714 	url_csr_write_4(sc, URL_MAR4, hashes[1]);
715 }
716 
717 Static int
718 url_openpipes(struct url_softc *sc)
719 {
720 	struct url_chain *c;
721 	usbd_status err;
722 	int i;
723 	int error = 0;
724 
725 	if (sc->sc_dying)
726 		return (EIO);
727 
728 	sc->sc_refcnt++;
729 
730 	/* Open RX pipe */
731 	err = usbd_open_pipe(sc->sc_ctl_iface, sc->sc_bulkin_no,
732 			     USBD_EXCLUSIVE_USE, &sc->sc_pipe_rx);
733 	if (err) {
734 		printf("%s: open rx pipe failed: %s\n",
735 		       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
736 		error = EIO;
737 		goto done;
738 	}
739 
740 	/* Open TX pipe */
741 	err = usbd_open_pipe(sc->sc_ctl_iface, sc->sc_bulkout_no,
742 			     USBD_EXCLUSIVE_USE, &sc->sc_pipe_tx);
743 	if (err) {
744 		printf("%s: open tx pipe failed: %s\n",
745 		       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
746 		error = EIO;
747 		goto done;
748 	}
749 
750 #if 0
751 	/* XXX: interrupt endpoint is not yet supported */
752 	/* Open Interrupt pipe */
753 	err = usbd_open_pipe_intr(sc->sc_ctl_iface, sc->sc_intrin_no,
754 				  USBD_EXCLUSIVE_USE, &sc->sc_pipe_intr, sc,
755 				  &sc->sc_cdata.url_ibuf, URL_INTR_PKGLEN,
756 				  url_intr, URL_INTR_INTERVAL);
757 	if (err) {
758 		printf("%s: open intr pipe failed: %s\n",
759 		       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
760 		error = EIO;
761 		goto done;
762 	}
763 #endif
764 
765 
766 	/* Start up the receive pipe. */
767 	for (i = 0; i < URL_RX_LIST_CNT; i++) {
768 		c = &sc->sc_cdata.url_rx_chain[i];
769 		usbd_setup_xfer(c->url_xfer, sc->sc_pipe_rx,
770 				c, c->url_buf, URL_BUFSZ,
771 				USBD_SHORT_XFER_OK | USBD_NO_COPY,
772 				USBD_NO_TIMEOUT, url_rxeof);
773 		(void)usbd_transfer(c->url_xfer);
774 		DPRINTF(("%s: %s: start read\n", USBDEVNAME(sc->sc_dev),
775 			 __func__));
776 	}
777 
778  done:
779 	if (--sc->sc_refcnt < 0)
780 		usb_detach_wakeup(USBDEV(sc->sc_dev));
781 
782 	return (error);
783 }
784 
785 Static int
786 url_newbuf(struct url_softc *sc, struct url_chain *c, struct mbuf *m)
787 {
788 	struct mbuf *m_new = NULL;
789 
790 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
791 
792 	if (m == NULL) {
793 		MGETHDR(m_new, M_DONTWAIT, MT_DATA);
794 		if (m_new == NULL) {
795 			printf("%s: no memory for rx list "
796 			       "-- packet dropped!\n", USBDEVNAME(sc->sc_dev));
797 			return (ENOBUFS);
798 		}
799 		MCLGET(m_new, M_DONTWAIT);
800 		if (!(m_new->m_flags & M_EXT)) {
801 			printf("%s: no memory for rx list "
802 			       "-- packet dropped!\n", USBDEVNAME(sc->sc_dev));
803 			m_freem(m_new);
804 			return (ENOBUFS);
805 		}
806 		m_new->m_len = m_new->m_pkthdr.len = MCLBYTES;
807 	} else {
808 		m_new = m;
809 		m_new->m_len = m_new->m_pkthdr.len = MCLBYTES;
810 		m_new->m_data = m_new->m_ext.ext_buf;
811 	}
812 
813 	m_adj(m_new, ETHER_ALIGN);
814 	c->url_mbuf = m_new;
815 
816 	return (0);
817 }
818 
819 
820 Static int
821 url_rx_list_init(struct url_softc *sc)
822 {
823 	struct url_cdata *cd;
824 	struct url_chain *c;
825 	int i;
826 
827 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
828 
829 	cd = &sc->sc_cdata;
830 	for (i = 0; i < URL_RX_LIST_CNT; i++) {
831 		c = &cd->url_rx_chain[i];
832 		c->url_sc = sc;
833 		c->url_idx = i;
834 		if (url_newbuf(sc, c, NULL) == ENOBUFS)
835 			return (ENOBUFS);
836 		if (c->url_xfer == NULL) {
837 			c->url_xfer = usbd_alloc_xfer(sc->sc_udev);
838 			if (c->url_xfer == NULL)
839 				return (ENOBUFS);
840 			c->url_buf = usbd_alloc_buffer(c->url_xfer, URL_BUFSZ);
841 			if (c->url_buf == NULL) {
842 				usbd_free_xfer(c->url_xfer);
843 				return (ENOBUFS);
844 			}
845 		}
846 	}
847 
848 	return (0);
849 }
850 
851 Static int
852 url_tx_list_init(struct url_softc *sc)
853 {
854 	struct url_cdata *cd;
855 	struct url_chain *c;
856 	int i;
857 
858 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
859 
860 	cd = &sc->sc_cdata;
861 	for (i = 0; i < URL_TX_LIST_CNT; i++) {
862 		c = &cd->url_tx_chain[i];
863 		c->url_sc = sc;
864 		c->url_idx = i;
865 		c->url_mbuf = NULL;
866 		if (c->url_xfer == NULL) {
867 			c->url_xfer = usbd_alloc_xfer(sc->sc_udev);
868 			if (c->url_xfer == NULL)
869 				return (ENOBUFS);
870 			c->url_buf = usbd_alloc_buffer(c->url_xfer, URL_BUFSZ);
871 			if (c->url_buf == NULL) {
872 				usbd_free_xfer(c->url_xfer);
873 				return (ENOBUFS);
874 			}
875 		}
876 	}
877 
878 	return (0);
879 }
880 
881 Static void
882 url_start(struct ifnet *ifp)
883 {
884 	struct url_softc *sc = ifp->if_softc;
885 	struct mbuf *m_head = NULL;
886 
887 	DPRINTF(("%s: %s: enter, link=%d\n", USBDEVNAME(sc->sc_dev),
888 		 __func__, sc->sc_link));
889 
890 	if (sc->sc_dying)
891 		return;
892 
893 	if (!sc->sc_link)
894 		return;
895 
896 	if (ifp->if_flags & IFF_OACTIVE)
897 		return;
898 
899 	IFQ_POLL(&ifp->if_snd, m_head);
900 	if (m_head == NULL)
901 		return;
902 
903 	if (url_send(sc, m_head, 0)) {
904 		ifp->if_flags |= IFF_OACTIVE;
905 		return;
906 	}
907 
908 	IFQ_DEQUEUE(&ifp->if_snd, m_head);
909 
910 #if NBPFILTER > 0
911 	if (ifp->if_bpf)
912 		bpf_mtap(ifp->if_bpf, m_head);
913 #endif
914 
915 	ifp->if_flags |= IFF_OACTIVE;
916 
917 	/* Set a timeout in case the chip goes out to lunch. */
918 	ifp->if_timer = 5;
919 }
920 
921 Static int
922 url_send(struct url_softc *sc, struct mbuf *m, int idx)
923 {
924 	int total_len;
925 	struct url_chain *c;
926 	usbd_status err;
927 
928 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev),__func__));
929 
930 	c = &sc->sc_cdata.url_tx_chain[idx];
931 
932 	/* Copy the mbuf data into a contiguous buffer */
933 	m_copydata(m, 0, m->m_pkthdr.len, c->url_buf);
934 	c->url_mbuf = m;
935 	total_len = m->m_pkthdr.len;
936 
937 	if (total_len < URL_MIN_FRAME_LEN) {
938 		bzero(c->url_buf + total_len, URL_MIN_FRAME_LEN - total_len);
939 		total_len = URL_MIN_FRAME_LEN;
940 	}
941 	usbd_setup_xfer(c->url_xfer, sc->sc_pipe_tx, c, c->url_buf, total_len,
942 			USBD_FORCE_SHORT_XFER | USBD_NO_COPY,
943 			URL_TX_TIMEOUT, url_txeof);
944 
945 	/* Transmit */
946 	sc->sc_refcnt++;
947 	err = usbd_transfer(c->url_xfer);
948 	if (--sc->sc_refcnt < 0)
949 		usb_detach_wakeup(USBDEV(sc->sc_dev));
950 	if (err != USBD_IN_PROGRESS) {
951 		printf("%s: url_send error=%s\n", USBDEVNAME(sc->sc_dev),
952 		       usbd_errstr(err));
953 		/* Stop the interface */
954 		usb_add_task(sc->sc_udev, &sc->sc_stop_task);
955 		return (EIO);
956 	}
957 
958 	DPRINTF(("%s: %s: send %d bytes\n", USBDEVNAME(sc->sc_dev),
959 		 __func__, total_len));
960 
961 	sc->sc_cdata.url_tx_cnt++;
962 
963 	return (0);
964 }
965 
966 Static void
967 url_txeof(usbd_xfer_handle xfer, usbd_private_handle priv, usbd_status status)
968 {
969 	struct url_chain *c = priv;
970 	struct url_softc *sc = c->url_sc;
971 	struct ifnet *ifp = GET_IFP(sc);
972 	int s;
973 
974 	if (sc->sc_dying)
975 		return;
976 
977 	s = splnet();
978 
979 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
980 
981 	ifp->if_timer = 0;
982 	ifp->if_flags &= ~IFF_OACTIVE;
983 
984 	if (status != USBD_NORMAL_COMPLETION) {
985 		if (status == USBD_NOT_STARTED || status == USBD_CANCELLED) {
986 			splx(s);
987 			return;
988 		}
989 		ifp->if_oerrors++;
990 		printf("%s: usb error on tx: %s\n", USBDEVNAME(sc->sc_dev),
991 		       usbd_errstr(status));
992 		if (status == USBD_STALLED) {
993 			sc->sc_refcnt++;
994 			usbd_clear_endpoint_stall(sc->sc_pipe_tx);
995 			if (--sc->sc_refcnt < 0)
996 				usb_detach_wakeup(USBDEV(sc->sc_dev));
997 		}
998 		splx(s);
999 		return;
1000 	}
1001 
1002 	ifp->if_opackets++;
1003 
1004 	m_freem(c->url_mbuf);
1005 	c->url_mbuf = NULL;
1006 
1007 	if (IFQ_IS_EMPTY(&ifp->if_snd) == 0)
1008 		url_start(ifp);
1009 
1010 	splx(s);
1011 }
1012 
1013 Static void
1014 url_rxeof(usbd_xfer_handle xfer, usbd_private_handle priv, usbd_status status)
1015 {
1016 	struct url_chain *c = priv;
1017 	struct url_softc *sc = c->url_sc;
1018 	struct ifnet *ifp = GET_IFP(sc);
1019 	struct mbuf *m;
1020 	u_int32_t total_len;
1021 	url_rxhdr_t rxhdr;
1022 	int s;
1023 
1024 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev),__func__));
1025 
1026 	if (sc->sc_dying)
1027 		return;
1028 
1029 	if (status != USBD_NORMAL_COMPLETION) {
1030 		if (status == USBD_NOT_STARTED || status == USBD_CANCELLED)
1031 			return;
1032 		sc->sc_rx_errs++;
1033 		if (usbd_ratecheck(&sc->sc_rx_notice)) {
1034 			printf("%s: %u usb errors on rx: %s\n",
1035 			       USBDEVNAME(sc->sc_dev), sc->sc_rx_errs,
1036 			       usbd_errstr(status));
1037 			sc->sc_rx_errs = 0;
1038 		}
1039 		if (status == USBD_STALLED) {
1040 			sc->sc_refcnt++;
1041 			usbd_clear_endpoint_stall(sc->sc_pipe_rx);
1042 			if (--sc->sc_refcnt < 0)
1043 				usb_detach_wakeup(USBDEV(sc->sc_dev));
1044 		}
1045 		goto done;
1046 	}
1047 
1048 	usbd_get_xfer_status(xfer, NULL, NULL, &total_len, NULL);
1049 
1050 	memcpy(mtod(c->url_mbuf, char *), c->url_buf, total_len);
1051 
1052 	if (total_len <= ETHER_CRC_LEN) {
1053 		ifp->if_ierrors++;
1054 		goto done;
1055 	}
1056 
1057 	memcpy(&rxhdr, c->url_buf + total_len - ETHER_CRC_LEN, sizeof(rxhdr));
1058 
1059 	DPRINTF(("%s: RX Status: %dbytes%s%s%s%s packets\n",
1060 		 USBDEVNAME(sc->sc_dev),
1061 		 UGETW(rxhdr) & URL_RXHDR_BYTEC_MASK,
1062 		 UGETW(rxhdr) & URL_RXHDR_VALID_MASK ? ", Valid" : "",
1063 		 UGETW(rxhdr) & URL_RXHDR_RUNTPKT_MASK ? ", Runt" : "",
1064 		 UGETW(rxhdr) & URL_RXHDR_PHYPKT_MASK ? ", Physical match" : "",
1065 		 UGETW(rxhdr) & URL_RXHDR_MCASTPKT_MASK ? ", Multicast" : ""));
1066 
1067 	if ((UGETW(rxhdr) & URL_RXHDR_VALID_MASK) == 0) {
1068 		ifp->if_ierrors++;
1069 		goto done;
1070 	}
1071 
1072 	ifp->if_ipackets++;
1073 	total_len -= ETHER_CRC_LEN;
1074 
1075 	m = c->url_mbuf;
1076 	m->m_pkthdr.len = m->m_len = total_len;
1077 	m->m_pkthdr.rcvif = ifp;
1078 
1079 	s = splnet();
1080 
1081 	if (url_newbuf(sc, c, NULL) == ENOBUFS) {
1082 		ifp->if_ierrors++;
1083 		goto done1;
1084 	}
1085 
1086 #if NBPFILTER > 0
1087 	if (ifp->if_bpf)
1088 		BPF_MTAP(ifp, m);
1089 #endif
1090 
1091 	DPRINTF(("%s: %s: deliver %d\n", USBDEVNAME(sc->sc_dev),
1092 		 __func__, m->m_len));
1093 	IF_INPUT(ifp, m);
1094 
1095  done1:
1096 	splx(s);
1097 
1098  done:
1099 	/* Setup new transfer */
1100 	usbd_setup_xfer(xfer, sc->sc_pipe_rx, c, c->url_buf, URL_BUFSZ,
1101 			USBD_SHORT_XFER_OK | USBD_NO_COPY,
1102 			USBD_NO_TIMEOUT, url_rxeof);
1103 	sc->sc_refcnt++;
1104 	usbd_transfer(xfer);
1105 	if (--sc->sc_refcnt < 0)
1106 		usb_detach_wakeup(USBDEV(sc->sc_dev));
1107 
1108 	DPRINTF(("%s: %s: start rx\n", USBDEVNAME(sc->sc_dev), __func__));
1109 }
1110 
1111 #if 0
1112 Static void url_intr()
1113 {
1114 }
1115 #endif
1116 
1117 Static int
1118 url_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
1119 {
1120 	struct url_softc *sc = ifp->if_softc;
1121 	struct ifaddr *ifa = (struct ifaddr *)data;
1122 	struct ifreq *ifr = (struct ifreq *)data;
1123 	struct mii_data *mii;
1124 	int s, error = 0;
1125 
1126 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
1127 
1128 	if (sc->sc_dying)
1129 		return (EIO);
1130 
1131 	s = splnet();
1132 
1133 	switch (cmd) {
1134 	case SIOCSIFADDR:
1135 		ifp->if_flags |= IFF_UP;
1136 		url_init(ifp);
1137 
1138 		switch (ifa->ifa_addr->sa_family) {
1139 #ifdef INET
1140 		case AF_INET:
1141 			arp_ifinit(&sc->sc_ac, ifa);
1142 			break;
1143 #endif /* INET */
1144 #ifdef NS
1145 		case AF_NS:
1146 		    {
1147 			struct ns_addr *ina = &IA_SNS(ifa)->sns_addr;
1148 
1149 			if (ns_nullhost(*ina))
1150 				ina->x_host = *(union ns_host *)
1151 					LLADDR(ifp->if_sadl);
1152 			else
1153 				memcpy(LLADDR(ifp->if_sadl),
1154 				       ina->x_host.c_host,
1155 				       ifp->if_addrlen);
1156 			break;
1157 		    }
1158 #endif /* NS */
1159 		}
1160 		break;
1161 
1162 	case SIOCSIFMTU:
1163 		if (ifr->ifr_mtu > ETHERMTU)
1164 			error = EINVAL;
1165 		else
1166 			ifp->if_mtu = ifr->ifr_mtu;
1167 		break;
1168 
1169 	case SIOCSIFFLAGS:
1170 		if (ifp->if_flags & IFF_UP) {
1171 			if (ifp->if_flags & IFF_RUNNING &&
1172 			    ifp->if_flags & IFF_PROMISC) {
1173 				URL_SETBIT2(sc, URL_RCR,
1174 					    URL_RCR_AAM|URL_RCR_AAP);
1175 			} else if (ifp->if_flags & IFF_RUNNING &&
1176 				   !(ifp->if_flags & IFF_PROMISC)) {
1177 				URL_CLRBIT2(sc, URL_RCR,
1178 					    URL_RCR_AAM|URL_RCR_AAP);
1179 			} else if (!(ifp->if_flags & IFF_RUNNING))
1180 				url_init(ifp);
1181 		} else {
1182 			if (ifp->if_flags & IFF_RUNNING)
1183 				url_stop(ifp, 1);
1184 		}
1185 		error = 0;
1186 		break;
1187 	case SIOCADDMULTI:
1188 	case SIOCDELMULTI:
1189 		error = (cmd == SIOCADDMULTI) ?
1190 			ether_addmulti(ifr, &sc->sc_ac) :
1191 			ether_delmulti(ifr, &sc->sc_ac);
1192 		if (error == ENETRESET) {
1193 			url_init(ifp);
1194 		}
1195 		url_setmulti(sc);
1196 		error = 0;
1197 		break;
1198 	case SIOCGIFMEDIA:
1199 	case SIOCSIFMEDIA:
1200 		mii = GET_MII(sc);
1201 		error = ifmedia_ioctl(ifp, ifr, &mii->mii_media, cmd);
1202 		break;
1203 	default:
1204 		error = EINVAL;
1205 		break;
1206 	}
1207 
1208 	splx(s);
1209 
1210 	return (error);
1211 }
1212 
1213 Static void
1214 url_watchdog(struct ifnet *ifp)
1215 {
1216 	struct url_softc *sc = ifp->if_softc;
1217 	struct url_chain *c;
1218 	usbd_status stat;
1219 	int s;
1220 
1221 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
1222 
1223 	ifp->if_oerrors++;
1224 	printf("%s: watchdog timeout\n", USBDEVNAME(sc->sc_dev));
1225 
1226 	s = splusb();
1227 	c = &sc->sc_cdata.url_tx_chain[0];
1228 	usbd_get_xfer_status(c->url_xfer, NULL, NULL, NULL, &stat);
1229 	url_txeof(c->url_xfer, c, stat);
1230 
1231 	if (IFQ_IS_EMPTY(&ifp->if_snd) == 0)
1232 		url_start(ifp);
1233 	splx(s);
1234 }
1235 
1236 Static void
1237 url_stop_task(struct url_softc *sc)
1238 {
1239 	url_stop(GET_IFP(sc), 1);
1240 }
1241 
1242 /* Stop the adapter and free any mbufs allocated to the RX and TX lists. */
1243 Static void
1244 url_stop(struct ifnet *ifp, int disable)
1245 {
1246 	struct url_softc *sc = ifp->if_softc;
1247 	usbd_status err;
1248 	int i;
1249 
1250 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
1251 
1252 	ifp->if_timer = 0;
1253 
1254 	url_reset(sc);
1255 
1256 	usb_uncallout(sc->sc_stat_ch, url_tick, sc);
1257 
1258 	/* Stop transfers */
1259 	/* RX endpoint */
1260 	if (sc->sc_pipe_rx != NULL) {
1261 		err = usbd_abort_pipe(sc->sc_pipe_rx);
1262 		if (err)
1263 			printf("%s: abort rx pipe failed: %s\n",
1264 			       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
1265 		err = usbd_close_pipe(sc->sc_pipe_rx);
1266 		if (err)
1267 			printf("%s: close rx pipe failed: %s\n",
1268 			       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
1269 		sc->sc_pipe_rx = NULL;
1270 	}
1271 
1272 	/* TX endpoint */
1273 	if (sc->sc_pipe_tx != NULL) {
1274 		err = usbd_abort_pipe(sc->sc_pipe_tx);
1275 		if (err)
1276 			printf("%s: abort tx pipe failed: %s\n",
1277 			       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
1278 		err = usbd_close_pipe(sc->sc_pipe_tx);
1279 		if (err)
1280 			printf("%s: close tx pipe failed: %s\n",
1281 			       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
1282 		sc->sc_pipe_tx = NULL;
1283 	}
1284 
1285 #if 0
1286 	/* XXX: Interrupt endpoint is not yet supported!! */
1287 	/* Interrupt endpoint */
1288 	if (sc->sc_pipe_intr != NULL) {
1289 		err = usbd_abort_pipe(sc->sc_pipe_intr);
1290 		if (err)
1291 			printf("%s: abort intr pipe failed: %s\n",
1292 			       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
1293 		err = usbd_close_pipe(sc->sc_pipe_intr);
1294 		if (err)
1295 			printf("%s: close intr pipe failed: %s\n",
1296 			       USBDEVNAME(sc->sc_dev), usbd_errstr(err));
1297 		sc->sc_pipe_intr = NULL;
1298 	}
1299 #endif
1300 
1301 	/* Free RX resources. */
1302 	for (i = 0; i < URL_RX_LIST_CNT; i++) {
1303 		if (sc->sc_cdata.url_rx_chain[i].url_mbuf != NULL) {
1304 			m_freem(sc->sc_cdata.url_rx_chain[i].url_mbuf);
1305 			sc->sc_cdata.url_rx_chain[i].url_mbuf = NULL;
1306 		}
1307 		if (sc->sc_cdata.url_rx_chain[i].url_xfer != NULL) {
1308 			usbd_free_xfer(sc->sc_cdata.url_rx_chain[i].url_xfer);
1309 			sc->sc_cdata.url_rx_chain[i].url_xfer = NULL;
1310 		}
1311 	}
1312 
1313 	/* Free TX resources. */
1314 	for (i = 0; i < URL_TX_LIST_CNT; i++) {
1315 		if (sc->sc_cdata.url_tx_chain[i].url_mbuf != NULL) {
1316 			m_freem(sc->sc_cdata.url_tx_chain[i].url_mbuf);
1317 			sc->sc_cdata.url_tx_chain[i].url_mbuf = NULL;
1318 		}
1319 		if (sc->sc_cdata.url_tx_chain[i].url_xfer != NULL) {
1320 			usbd_free_xfer(sc->sc_cdata.url_tx_chain[i].url_xfer);
1321 			sc->sc_cdata.url_tx_chain[i].url_xfer = NULL;
1322 		}
1323 	}
1324 
1325 	sc->sc_link = 0;
1326 	ifp->if_flags &= ~(IFF_RUNNING | IFF_OACTIVE);
1327 }
1328 
1329 /* Set media options */
1330 Static int
1331 url_ifmedia_change(struct ifnet *ifp)
1332 {
1333 	struct url_softc *sc = ifp->if_softc;
1334 	struct mii_data *mii = GET_MII(sc);
1335 
1336 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
1337 
1338 	if (sc->sc_dying)
1339 		return (0);
1340 
1341 	sc->sc_link = 0;
1342 	if (mii->mii_instance) {
1343 		struct mii_softc *miisc;
1344 		for (miisc = LIST_FIRST(&mii->mii_phys); miisc != NULL;
1345 		     miisc = LIST_NEXT(miisc, mii_list))
1346 			mii_phy_reset(miisc);
1347 	}
1348 
1349 	return (mii_mediachg(mii));
1350 }
1351 
1352 /* Report current media status. */
1353 Static void
1354 url_ifmedia_status(struct ifnet *ifp, struct ifmediareq *ifmr)
1355 {
1356 	struct url_softc *sc = ifp->if_softc;
1357 	struct mii_data *mii = GET_MII(sc);
1358 
1359 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
1360 
1361 	if (sc->sc_dying)
1362 		return;
1363 
1364 	if ((ifp->if_flags & IFF_RUNNING) == 0) {
1365 		ifmr->ifm_active = IFM_ETHER | IFM_NONE;
1366 		ifmr->ifm_status = 0;
1367 		return;
1368 	}
1369 
1370 	mii_pollstat(mii);
1371 	ifmr->ifm_active = mii->mii_media_active;
1372 	ifmr->ifm_status = mii->mii_media_status;
1373 }
1374 
1375 Static void
1376 url_tick(void *xsc)
1377 {
1378 	struct url_softc *sc = xsc;
1379 
1380 	if (sc == NULL)
1381 		return;
1382 
1383 	DPRINTFN(0xff, ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev),
1384 			__func__));
1385 
1386 	if (sc->sc_dying)
1387 		return;
1388 
1389 	/* Perform periodic stuff in process context */
1390 	usb_add_task(sc->sc_udev, &sc->sc_tick_task);
1391 }
1392 
1393 Static void
1394 url_tick_task(void *xsc)
1395 {
1396 	struct url_softc *sc = xsc;
1397 	struct ifnet *ifp;
1398 	struct mii_data *mii;
1399 	int s;
1400 
1401 	if (sc == NULL)
1402 		return;
1403 
1404 	DPRINTFN(0xff, ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev),
1405 			__func__));
1406 
1407 	if (sc->sc_dying)
1408 		return;
1409 
1410 	ifp = GET_IFP(sc);
1411 	mii = GET_MII(sc);
1412 
1413 	if (mii == NULL)
1414 		return;
1415 
1416 	s = splnet();
1417 
1418 	mii_tick(mii);
1419 	if (!sc->sc_link) {
1420 		mii_pollstat(mii);
1421 		if (mii->mii_media_status & IFM_ACTIVE &&
1422 		    IFM_SUBTYPE(mii->mii_media_active) != IFM_NONE) {
1423 			DPRINTF(("%s: %s: got link\n",
1424 				 USBDEVNAME(sc->sc_dev), __func__));
1425 			sc->sc_link++;
1426 			if (IFQ_IS_EMPTY(&ifp->if_snd) == 0)
1427 				   url_start(ifp);
1428 		}
1429 	}
1430 
1431 	usb_callout(sc->sc_stat_ch, hz, url_tick, sc);
1432 
1433 	splx(s);
1434 }
1435 
1436 /* Get exclusive access to the MII registers */
1437 Static void
1438 url_lock_mii(struct url_softc *sc)
1439 {
1440 	DPRINTFN(0xff, ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev),
1441 			__func__));
1442 
1443 	sc->sc_refcnt++;
1444 	usb_lockmgr(&sc->sc_mii_lock, LK_EXCLUSIVE, NULL, curproc);
1445 }
1446 
1447 Static void
1448 url_unlock_mii(struct url_softc *sc)
1449 {
1450 	DPRINTFN(0xff, ("%s: %s: enter\n", USBDEVNAME(sc->sc_dev),
1451 		       __func__));
1452 
1453 	usb_lockmgr(&sc->sc_mii_lock, LK_RELEASE, NULL, curproc);
1454 	if (--sc->sc_refcnt < 0)
1455 		usb_detach_wakeup(USBDEV(sc->sc_dev));
1456 }
1457 
1458 Static int
1459 url_int_miibus_readreg(device_ptr_t dev, int phy, int reg)
1460 {
1461 	struct url_softc *sc;
1462 	u_int16_t val;
1463 
1464 	if (dev == NULL)
1465 		return (0);
1466 
1467 	sc = USBGETSOFTC(dev);
1468 
1469 	DPRINTFN(0xff, ("%s: %s: enter, phy=%d reg=0x%04x\n",
1470 		 USBDEVNAME(sc->sc_dev), __func__, phy, reg));
1471 
1472 	if (sc->sc_dying) {
1473 #ifdef DIAGNOSTIC
1474 		printf("%s: %s: dying\n", USBDEVNAME(sc->sc_dev),
1475 		       __func__);
1476 #endif
1477 		return (0);
1478 	}
1479 
1480 	/* XXX: one PHY only for the RTL8150 internal PHY */
1481 	if (phy != 0) {
1482 		DPRINTFN(0xff, ("%s: %s: phy=%d is not supported\n",
1483 			 USBDEVNAME(sc->sc_dev), __func__, phy));
1484 		return (0);
1485 	}
1486 
1487 	url_lock_mii(sc);
1488 
1489 	switch (reg) {
1490 	case MII_BMCR:		/* Control Register */
1491 		reg = URL_BMCR;
1492 		break;
1493 	case MII_BMSR:		/* Status Register */
1494 		reg = URL_BMSR;
1495 		break;
1496 	case MII_PHYIDR1:
1497 	case MII_PHYIDR2:
1498 		val = 0;
1499 		goto R_DONE;
1500 		break;
1501 	case MII_ANAR:		/* Autonegotiation advertisement */
1502 		reg = URL_ANAR;
1503 		break;
1504 	case MII_ANLPAR:	/* Autonegotiation link partner abilities */
1505 		reg = URL_ANLP;
1506 		break;
1507 	case URLPHY_MSR:	/* Media Status Register */
1508 		reg = URL_MSR;
1509 		break;
1510 	default:
1511 		printf("%s: %s: bad register %04x\n",
1512 		       USBDEVNAME(sc->sc_dev), __func__, reg);
1513 		val = 0;
1514 		goto R_DONE;
1515 		break;
1516 	}
1517 
1518 	if (reg == URL_MSR)
1519 		val = url_csr_read_1(sc, reg);
1520 	else
1521 		val = url_csr_read_2(sc, reg);
1522 
1523  R_DONE:
1524 	DPRINTFN(0xff, ("%s: %s: phy=%d reg=0x%04x => 0x%04x\n",
1525 		 USBDEVNAME(sc->sc_dev), __func__, phy, reg, val));
1526 
1527 	url_unlock_mii(sc);
1528 	return (val);
1529 }
1530 
1531 Static void
1532 url_int_miibus_writereg(device_ptr_t dev, int phy, int reg, int data)
1533 {
1534 	struct url_softc *sc;
1535 
1536 	if (dev == NULL)
1537 		return;
1538 
1539 	sc = USBGETSOFTC(dev);
1540 
1541 	DPRINTFN(0xff, ("%s: %s: enter, phy=%d reg=0x%04x data=0x%04x\n",
1542 		 USBDEVNAME(sc->sc_dev), __func__, phy, reg, data));
1543 
1544 	if (sc->sc_dying) {
1545 #ifdef DIAGNOSTIC
1546 		printf("%s: %s: dying\n", USBDEVNAME(sc->sc_dev),
1547 		       __func__);
1548 #endif
1549 		return;
1550 	}
1551 
1552 	/* XXX: one PHY only for the RTL8150 internal PHY */
1553 	if (phy != 0) {
1554 		DPRINTFN(0xff, ("%s: %s: phy=%d is not supported\n",
1555 			 USBDEVNAME(sc->sc_dev), __func__, phy));
1556 		return;
1557 	}
1558 
1559 	url_lock_mii(sc);
1560 
1561 	switch (reg) {
1562 	case MII_BMCR:		/* Control Register */
1563 		reg = URL_BMCR;
1564 		break;
1565 	case MII_BMSR:		/* Status Register */
1566 		reg = URL_BMSR;
1567 		break;
1568 	case MII_PHYIDR1:
1569 	case MII_PHYIDR2:
1570 		goto W_DONE;
1571 		break;
1572 	case MII_ANAR:		/* Autonegotiation advertisement */
1573 		reg = URL_ANAR;
1574 		break;
1575 	case MII_ANLPAR:	/* Autonegotiation link partner abilities */
1576 		reg = URL_ANLP;
1577 		break;
1578 	case URLPHY_MSR:	/* Media Status Register */
1579 		reg = URL_MSR;
1580 		break;
1581 	default:
1582 		printf("%s: %s: bad register %04x\n",
1583 		       USBDEVNAME(sc->sc_dev), __func__, reg);
1584 		goto W_DONE;
1585 		break;
1586 	}
1587 
1588 	if (reg == URL_MSR)
1589 		url_csr_write_1(sc, reg, data);
1590 	else
1591 		url_csr_write_2(sc, reg, data);
1592  W_DONE:
1593 
1594 	url_unlock_mii(sc);
1595 	return;
1596 }
1597 
1598 Static void
1599 url_miibus_statchg(device_ptr_t dev)
1600 {
1601 #ifdef URL_DEBUG
1602 	struct url_softc *sc;
1603 
1604 	if (dev == NULL)
1605 		return;
1606 
1607 	sc = USBGETSOFTC(dev);
1608 	DPRINTF(("%s: %s: enter\n", USBDEVNAME(sc->sc_dev), __func__));
1609 #endif
1610 	/* Nothing to do */
1611 }
1612 
1613 #if 0
1614 /*
1615  * external PHYs support, but not test.
1616  */
1617 Static int
1618 url_ext_miibus_redreg(device_ptr_t dev, int phy, int reg)
1619 {
1620 	struct url_softc *sc = USBGETSOFTC(dev);
1621 	u_int16_t val;
1622 
1623 	DPRINTF(("%s: %s: enter, phy=%d reg=0x%04x\n",
1624 		 USBDEVNAME(sc->sc_dev), __func__, phy, reg));
1625 
1626 	if (sc->sc_dying) {
1627 #ifdef DIAGNOSTIC
1628 		printf("%s: %s: dying\n", USBDEVNAME(sc->sc_dev),
1629 		       __func__);
1630 #endif
1631 		return (0);
1632 	}
1633 
1634 	url_lock_mii(sc);
1635 
1636 	url_csr_write_1(sc, URL_PHYADD, phy & URL_PHYADD_MASK);
1637 	/*
1638 	 * RTL8150L will initiate a MII management data transaction
1639 	 * if PHYCNT_OWN bit is set 1 by software. After transaction,
1640 	 * this bit is auto cleared by TRL8150L.
1641 	 */
1642 	url_csr_write_1(sc, URL_PHYCNT,
1643 			(reg | URL_PHYCNT_PHYOWN) & ~URL_PHYCNT_RWCR);
1644 	for (i = 0; i < URL_TIMEOUT; i++) {
1645 		if ((url_csr_read_1(sc, URL_PHYCNT) & URL_PHYCNT_PHYOWN) == 0)
1646 			break;
1647 	}
1648 	if (i == URL_TIMEOUT) {
1649 		printf("%s: MII read timed out\n", USBDEVNAME(sc->sc_dev));
1650 	}
1651 
1652 	val = url_csr_read_2(sc, URL_PHYDAT);
1653 
1654 	DPRINTF(("%s: %s: phy=%d reg=0x%04x => 0x%04x\n",
1655 		 USBDEVNAME(sc->sc_dev), __func__, phy, reg, val));
1656 
1657 	url_unlock_mii(sc);
1658 	return (val);
1659 }
1660 
1661 Static void
1662 url_ext_miibus_writereg(device_ptr_t dev, int phy, int reg, int data)
1663 {
1664 	struct url_softc *sc = USBGETSOFTC(dev);
1665 
1666 	DPRINTF(("%s: %s: enter, phy=%d reg=0x%04x data=0x%04x\n",
1667 		 USBDEVNAME(sc->sc_dev), __func__, phy, reg, data));
1668 
1669 	if (sc->sc_dying) {
1670 #ifdef DIAGNOSTIC
1671 		printf("%s: %s: dying\n", USBDEVNAME(sc->sc_dev),
1672 		       __func__);
1673 #endif
1674 		return;
1675 	}
1676 
1677 	url_lock_mii(sc);
1678 
1679 	url_csr_write_2(sc, URL_PHYDAT, data);
1680 	url_csr_write_1(sc, URL_PHYADD, phy);
1681 	url_csr_write_1(sc, URL_PHYCNT, reg | URL_PHYCNT_RWCR);	/* Write */
1682 
1683 	for (i=0; i < URL_TIMEOUT; i++) {
1684 		if (url_csr_read_1(sc, URL_PHYCNT) & URL_PHYCNT_PHYOWN)
1685 			break;
1686 	}
1687 
1688 	if (i == URL_TIMEOUT) {
1689 		printf("%s: MII write timed out\n",
1690 		       USBDEVNAME(sc->sc_dev));
1691 	}
1692 
1693 	url_unlock_mii(sc);
1694 	return;
1695 }
1696 #endif
1697 
1698