Subject: Re: kern/37653: cdce fails with iPaq Linux
To: None <gnats-bugs@NetBSD.org>
From: Scott Ellis <scotte@warped.com>
List: netbsd-bugs
Date: 12/31/2007 10:02:40
This is a multi-part message in MIME format.
--------------030103050502070606030901
Content-Type: text/plain; charset=ISO-8859-1; format=flowed
Content-Transfer-Encoding: 7bit
Wrong diff was attahed to the original PR. Attached below is the
correct diff.
--------------030103050502070606030901
Content-Type: text/plain;
name="if_cdce.c.diff"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
filename="if_cdce.c.diff"
--- if_cdce.c 2007-12-31 10:00:00.000000000 -0800
+++ /home/scotte/if_cdce.c.scotte_ipaqlinux 2007-12-29 11:33:03.000000000 -0800
@@ -109,9 +109,9 @@
Static void cdce_txeof(usbd_xfer_handle, usbd_private_handle, usbd_status);
Static void cdce_start(struct ifnet *);
Static int cdce_ioctl(struct ifnet *, u_long, void *);
-Static void cdce_init(void *);
+Static int cdce_init(struct ifnet *);
Static void cdce_watchdog(struct ifnet *);
-Static void cdce_stop(struct cdce_softc *);
+Static void cdce_stop(struct ifnet *, int);
Static uint32_t cdce_crc32(const void *, size_t);
Static const struct cdce_type cdce_devs[] = {
@@ -121,6 +121,7 @@
{{ USB_VENDOR_SHARP, USB_PRODUCT_SHARP_SL5600 }, CDCE_ZAURUS | CDCE_NO_UNION },
{{ USB_VENDOR_SHARP, USB_PRODUCT_SHARP_C700 }, CDCE_ZAURUS | CDCE_NO_UNION },
{{ USB_VENDOR_SHARP, USB_PRODUCT_SHARP_C750 }, CDCE_ZAURUS | CDCE_NO_UNION },
+ {{ USB_VENDOR_COMPAQ, USB_PRODUCT_COMPAQ_IPAQLINUX }, CDCE_NO_UNION },
};
#define cdce_lookup(v, p) ((const struct cdce_type *)usb_lookup(cdce_devs, v, p))
@@ -272,6 +273,8 @@
ifp->if_ioctl = cdce_ioctl;
ifp->if_start = cdce_start;
ifp->if_watchdog = cdce_watchdog;
+ ifp->if_init = cdce_init;
+ ifp->if_stop = cdce_stop;
strncpy(ifp->if_xname, USBDEVNAME(sc->cdce_dev), IFNAMSIZ);
IFQ_SET_READY(&ifp->if_snd);
@@ -302,7 +305,7 @@
}
if (ifp->if_flags & IFF_RUNNING)
- cdce_stop(sc);
+ cdce_stop(ifp, 1);
ether_ifdetach(ifp);
@@ -368,7 +371,7 @@
m->m_pkthdr.len + extra, USBD_NO_COPY, 10000, cdce_txeof);
err = usbd_transfer(c->cdce_xfer);
if (err != USBD_IN_PROGRESS) {
- cdce_stop(sc);
+ cdce_stop(GET_IFP(sc), 0);
return (EIO);
}
@@ -378,10 +381,10 @@
}
Static void
-cdce_stop(struct cdce_softc *sc)
+cdce_stop(struct ifnet *ifp, int disable)
{
+ struct cdce_softc *sc = ifp->if_softc;
usbd_status err;
- struct ifnet *ifp = GET_IFP(sc);
int i;
ifp->if_timer = 0;
@@ -439,8 +442,6 @@
cdce_ioctl(struct ifnet *ifp, u_long command, void *data)
{
struct cdce_softc *sc = ifp->if_softc;
- struct ifaddr *ifa = (struct ifaddr *)data;
- struct ifreq *ifr = (struct ifreq *)data;
int s, error = 0;
if (sc->cdce_dying)
@@ -449,42 +450,11 @@
s = splnet();
switch(command) {
- case SIOCSIFADDR:
- ifp->if_flags |= IFF_UP;
- cdce_init(sc);
- switch (ifa->ifa_addr->sa_family) {
-#ifdef INET
- case AF_INET:
-#if defined(__NetBSD__)
- arp_ifinit(ifp, ifa);
-#else
- arp_ifinit(&sc->arpcom, ifa);
-#endif
- break;
-#endif /* INET */
- }
- break;
-
- case SIOCSIFMTU:
- if (ifr->ifr_mtu > ETHERMTU)
- error = EINVAL;
- else
- ifp->if_mtu = ifr->ifr_mtu;
- break;
-
- case SIOCSIFFLAGS:
- if (ifp->if_flags & IFF_UP) {
- if (!(ifp->if_flags & IFF_RUNNING))
- cdce_init(sc);
- } else {
- if (ifp->if_flags & IFF_RUNNING)
- cdce_stop(sc);
- }
- error = 0;
- break;
-
default:
- error = EINVAL;
+ error = ether_ioctl(ifp, command, data);
+ if (error == ENETRESET) {
+ error = 0;
+ }
break;
}
@@ -505,30 +475,29 @@
printf("%s: watchdog timeout\n", USBDEVNAME(sc->cdce_dev));
}
-Static void
-cdce_init(void *xsc)
+Static int
+cdce_init(struct ifnet *ifp)
{
- struct cdce_softc *sc = xsc;
- struct ifnet *ifp = GET_IFP(sc);
+ struct cdce_softc *sc = ifp->if_softc;
struct cdce_chain *c;
usbd_status err;
int s, i;
if (ifp->if_flags & IFF_RUNNING)
- return;
+ return (EIO);
s = splnet();
if (cdce_tx_list_init(sc) == ENOBUFS) {
printf("%s: tx list init failed\n", USBDEVNAME(sc->cdce_dev));
splx(s);
- return;
+ return (ENOMEM);
}
if (cdce_rx_list_init(sc) == ENOBUFS) {
printf("%s: rx list init failed\n", USBDEVNAME(sc->cdce_dev));
splx(s);
- return;
+ return (ENOMEM);
}
/* Maybe set multicast / broadcast here??? */
@@ -539,7 +508,7 @@
printf("%s: open rx pipe failed: %s\n", USBDEVNAME(sc->cdce_dev),
usbd_errstr(err));
splx(s);
- return;
+ return (EIO);
}
err = usbd_open_pipe(sc->cdce_data_iface, sc->cdce_bulkout_no,
@@ -548,7 +517,7 @@
printf("%s: open tx pipe failed: %s\n", USBDEVNAME(sc->cdce_dev),
usbd_errstr(err));
splx(s);
- return;
+ return (EIO);
}
for (i = 0; i < CDCE_RX_LIST_CNT; i++) {
@@ -563,6 +532,8 @@
ifp->if_flags &= ~IFF_OACTIVE;
splx(s);
+
+ return (0);
}
Static int
--------------030103050502070606030901--