summaryrefslogtreecommitdiffstats
path: root/sys/dev/ste
diff options
context:
space:
mode:
authorjhb <jhb@FreeBSD.org>2009-11-19 22:06:40 +0000
committerjhb <jhb@FreeBSD.org>2009-11-19 22:06:40 +0000
commitaffabaa85e18565f9c0a68b33c5b0f2e0587f05a (patch)
tree8407585eec2a1c0c6cadd011a7eb682949649bde /sys/dev/ste
parentd49024b6f48c6368a3af0f695133bdc2a695e281 (diff)
downloadFreeBSD-src-affabaa85e18565f9c0a68b33c5b0f2e0587f05a.zip
FreeBSD-src-affabaa85e18565f9c0a68b33c5b0f2e0587f05a.tar.gz
- Add a private timer to drive the transmit watchdog instead of using
if_watchdog and if_timer. - Fix some issues in detach for sn(4), ste(4), and ti(4). Primarily this means calling ether_ifdetach() before anything else.
Diffstat (limited to 'sys/dev/ste')
-rw-r--r--sys/dev/ste/if_ste.c21
-rw-r--r--sys/dev/ste/if_stereg.h1
2 files changed, 11 insertions, 11 deletions
diff --git a/sys/dev/ste/if_ste.c b/sys/dev/ste/if_ste.c
index f68a97d..55b256f 100644
--- a/sys/dev/ste/if_ste.c
+++ b/sys/dev/ste/if_ste.c
@@ -108,7 +108,7 @@ static int ste_ioctl(struct ifnet *, u_long, caddr_t);
static int ste_encap(struct ste_softc *, struct ste_chain *, struct mbuf *);
static void ste_start(struct ifnet *);
static void ste_start_locked(struct ifnet *);
-static void ste_watchdog(struct ifnet *);
+static void ste_watchdog(struct ste_softc *);
static int ste_shutdown(device_t);
static int ste_newbuf(struct ste_softc *, struct ste_chain_onefrag *,
struct mbuf *);
@@ -924,7 +924,7 @@ ste_txeof(sc)
sc->ste_cdata.ste_tx_cons = idx;
if (idx == sc->ste_cdata.ste_tx_prod)
- ifp->if_timer = 0;
+ sc->ste_timer = 0;
}
static void
@@ -960,6 +960,8 @@ ste_stats_update(xsc)
}
}
+ if (sc->ste_timer > 0 && --sc->ste_timer == 0)
+ ste_watchdog(sc);
callout_reset(&sc->ste_stat_callout, hz, ste_stats_update, sc);
return;
@@ -1094,7 +1096,6 @@ ste_attach(dev)
ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
ifp->if_ioctl = ste_ioctl;
ifp->if_start = ste_start;
- ifp->if_watchdog = ste_watchdog;
ifp->if_init = ste_init;
IFQ_SET_MAXLEN(&ifp->if_snd, STE_TX_LIST_CNT - 1);
ifp->if_snd.ifq_drv_maxlen = STE_TX_LIST_CNT - 1;
@@ -1159,11 +1160,11 @@ ste_detach(dev)
/* These should only be active if attach succeeded */
if (device_is_attached(dev)) {
+ ether_ifdetach(ifp);
STE_LOCK(sc);
ste_stop(sc);
STE_UNLOCK(sc);
callout_drain(&sc->ste_stat_callout);
- ether_ifdetach(ifp);
}
if (sc->ste_miibus)
device_delete_child(dev, sc->ste_miibus);
@@ -1708,7 +1709,7 @@ ste_start_locked(ifp)
BPF_MTAP(ifp, cur_tx->ste_mbuf);
STE_INC(idx, STE_TX_LIST_CNT);
- ifp->if_timer = 5;
+ sc->ste_timer = 5;
}
sc->ste_cdata.ste_tx_prod = idx;
@@ -1716,13 +1717,12 @@ ste_start_locked(ifp)
}
static void
-ste_watchdog(ifp)
- struct ifnet *ifp;
+ste_watchdog(struct ste_softc *sc)
{
- struct ste_softc *sc;
+ struct ifnet *ifp;
- sc = ifp->if_softc;
- STE_LOCK(sc);
+ ifp = sc->ste_ifp;
+ STE_LOCK_ASSERT(sc);
ifp->if_oerrors++;
if_printf(ifp, "watchdog timeout\n");
@@ -1736,7 +1736,6 @@ ste_watchdog(ifp)
if (!IFQ_DRV_IS_EMPTY(&ifp->if_snd))
ste_start_locked(ifp);
- STE_UNLOCK(sc);
return;
}
diff --git a/sys/dev/ste/if_stereg.h b/sys/dev/ste/if_stereg.h
index 0114ebe..68d9674 100644
--- a/sys/dev/ste/if_stereg.h
+++ b/sys/dev/ste/if_stereg.h
@@ -517,6 +517,7 @@ struct ste_softc {
int ste_tx_thresh;
u_int8_t ste_link;
int ste_if_flags;
+ int ste_timer;
struct ste_chain *ste_tx_prev;
struct ste_list_data *ste_ldata;
struct ste_chain_data ste_cdata;
OpenPOWER on IntegriCloud