Get rid of the "I don't know what I was thinking / somebody should have
stopped me / does anybody read source-changes?" ATH_LOCK()/ATH_UNLOCK() and bracket with splnet()/splx() instead. This is still not *good*, since ifnet ioctls are not (yet) synchronized, but could be no worse than what we have, now. Survives light testing with my (forthcoming) ifnet ioctl synchronization patch.
This commit is contained in:
parent
2ed4138b61
commit
9d36091c67
|
@ -1,4 +1,4 @@
|
|||
/* $NetBSD: ath.c,v 1.111 2011/03/07 11:25:41 cegger Exp $ */
|
||||
/* $NetBSD: ath.c,v 1.112 2011/10/07 16:58:11 dyoung Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2002-2005 Sam Leffler, Errno Consulting
|
||||
|
@ -41,7 +41,7 @@
|
|||
__FBSDID("$FreeBSD: src/sys/dev/ath/if_ath.c,v 1.104 2005/09/16 10:09:23 ru Exp $");
|
||||
#endif
|
||||
#ifdef __NetBSD__
|
||||
__KERNEL_RCSID(0, "$NetBSD: ath.c,v 1.111 2011/03/07 11:25:41 cegger Exp $");
|
||||
__KERNEL_RCSID(0, "$NetBSD: ath.c,v 1.112 2011/10/07 16:58:11 dyoung Exp $");
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
@ -979,18 +979,18 @@ ath_init(struct ath_softc *sc)
|
|||
struct ieee80211com *ic = &sc->sc_ic;
|
||||
struct ath_hal *ah = sc->sc_ah;
|
||||
HAL_STATUS status;
|
||||
int error = 0;
|
||||
int error = 0, s;
|
||||
|
||||
DPRINTF(sc, ATH_DEBUG_ANY, "%s: if_flags 0x%x\n",
|
||||
__func__, ifp->if_flags);
|
||||
|
||||
if (device_is_active(sc->sc_dev)) {
|
||||
ATH_LOCK(sc);
|
||||
s = splnet();
|
||||
} else if (!pmf_device_subtree_resume(sc->sc_dev, &sc->sc_qual) ||
|
||||
!device_is_active(sc->sc_dev))
|
||||
return 0;
|
||||
else
|
||||
ATH_LOCK(sc);
|
||||
s = splnet();
|
||||
|
||||
/*
|
||||
* Stop anything previously setup. This is safe
|
||||
|
@ -1074,7 +1074,7 @@ ath_init(struct ath_softc *sc)
|
|||
} else
|
||||
ieee80211_new_state(ic, IEEE80211_S_RUN, -1);
|
||||
done:
|
||||
ATH_UNLOCK(sc);
|
||||
splx(s);
|
||||
return error;
|
||||
}
|
||||
|
||||
|
@ -1088,7 +1088,7 @@ ath_stop_locked(struct ifnet *ifp, int disable)
|
|||
DPRINTF(sc, ATH_DEBUG_ANY, "%s: invalid %d if_flags 0x%x\n",
|
||||
__func__, !device_is_enabled(sc->sc_dev), ifp->if_flags);
|
||||
|
||||
ATH_LOCK_ASSERT(sc);
|
||||
/* KASSERT() IPL_NET */
|
||||
if (ifp->if_flags & IFF_RUNNING) {
|
||||
/*
|
||||
* Shutdown the hardware and driver:
|
||||
|
@ -1137,11 +1137,11 @@ ath_stop_locked(struct ifnet *ifp, int disable)
|
|||
static void
|
||||
ath_stop(struct ifnet *ifp, int disable)
|
||||
{
|
||||
struct ath_softc *sc = ifp->if_softc;
|
||||
int s;
|
||||
|
||||
ATH_LOCK(sc);
|
||||
s = splnet();
|
||||
ath_stop_locked(ifp, disable);
|
||||
ATH_UNLOCK(sc);
|
||||
splx(s);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -4599,10 +4599,11 @@ ath_calibrate(void *arg)
|
|||
struct ath_softc *sc = arg;
|
||||
struct ath_hal *ah = sc->sc_ah;
|
||||
HAL_BOOL iqCalDone;
|
||||
int s;
|
||||
|
||||
sc->sc_stats.ast_per_cal++;
|
||||
|
||||
ATH_LOCK(sc);
|
||||
s = splnet();
|
||||
|
||||
if (ath_hal_getrfgain(ah) == HAL_RFGAIN_NEED_CHANGE) {
|
||||
/*
|
||||
|
@ -4648,7 +4649,7 @@ ath_calibrate(void *arg)
|
|||
sc->sc_caltries++;
|
||||
callout_reset(&sc->sc_cal_ch, sc->sc_calinterval * hz,
|
||||
ath_calibrate, sc);
|
||||
ATH_UNLOCK(sc);
|
||||
splx(s);
|
||||
}
|
||||
|
||||
static int
|
||||
|
@ -5300,9 +5301,9 @@ ath_ioctl(struct ifnet *ifp, u_long cmd, void *data)
|
|||
struct ath_softc *sc = ifp->if_softc;
|
||||
struct ieee80211com *ic = &sc->sc_ic;
|
||||
struct ifreq *ifr = (struct ifreq *)data;
|
||||
int error = 0;
|
||||
int error = 0, s;
|
||||
|
||||
ATH_LOCK(sc);
|
||||
s = splnet();
|
||||
switch (cmd) {
|
||||
case SIOCSIFFLAGS:
|
||||
if ((error = ifioctl_common(ifp, cmd, data)) != 0)
|
||||
|
@ -5348,7 +5349,7 @@ ath_ioctl(struct ifnet *ifp, u_long cmd, void *data)
|
|||
sc->sc_stats.ast_tx_packets = ifp->if_opackets;
|
||||
sc->sc_stats.ast_rx_packets = ifp->if_ipackets;
|
||||
sc->sc_stats.ast_rx_rssi = ieee80211_getrssi(ic);
|
||||
ATH_UNLOCK(sc);
|
||||
splx(s);
|
||||
/*
|
||||
* NB: Drop the softc lock in case of a page fault;
|
||||
* we'll accept any potential inconsisentcy in the
|
||||
|
@ -5371,7 +5372,7 @@ ath_ioctl(struct ifnet *ifp, u_long cmd, void *data)
|
|||
error = 0;
|
||||
break;
|
||||
}
|
||||
ATH_UNLOCK(sc);
|
||||
splx(s);
|
||||
return error;
|
||||
#undef IS_RUNNING
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $NetBSD: ath_netbsd.h,v 1.11 2011/01/21 17:46:19 dyoung Exp $ */
|
||||
/* $NetBSD: ath_netbsd.h,v 1.12 2011/10/07 16:58:11 dyoung Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2003, 2004 David Young
|
||||
|
@ -48,49 +48,19 @@ typedef struct ath_task {
|
|||
#define TASK_RUN_OR_ENQUEUE(__task) \
|
||||
((*(__task)->t_func)((__task)->t_context, 1))
|
||||
|
||||
struct ath_lock {
|
||||
int count;
|
||||
int ipl;
|
||||
};
|
||||
typedef kmutex_t ath_txq_lock_t;
|
||||
#define ATH_TXQ_LOCK_INIT(_sc, _tq) mutex_init(&(_tq)->axq_lock, MUTEX_DEFAULT, IPL_NET)
|
||||
#define ATH_TXQ_LOCK_DESTROY(_tq) mutex_destroy(&(_tq)->axq_lock)
|
||||
#define ATH_TXQ_LOCK(_tq) mutex_enter(&(_tq)->axq_lock)
|
||||
#define ATH_TXQ_UNLOCK(_tq) mutex_exit(&(_tq)->axq_lock)
|
||||
#define ATH_TXQ_LOCK_ASSERT(_tq) do { KASSERT(mutex_owned(&(_tq)->axq_lock), ("txq lock unheld")); } while (/*CONSTCOND*/true)
|
||||
|
||||
#define ATH_LOCK_INIT_IMPL(_obj, _member) \
|
||||
do { (_obj)->_member.count = 0; } while (0)
|
||||
#define ATH_LOCK_IMPL(_obj, _member) \
|
||||
do { \
|
||||
int __s = splnet(); \
|
||||
if ((_obj)->_member.count++ == 0) \
|
||||
(_obj)->_member.ipl = __s; \
|
||||
} while (0)
|
||||
#define ATH_UNLOCK_IMPL(_obj, _member) \
|
||||
do { \
|
||||
if (--(_obj)->_member.count == 0) \
|
||||
splx((_obj)->_member.ipl); \
|
||||
else { \
|
||||
KASSERT((_obj)->_member.count >= 0, \
|
||||
("%s: no ATH_LOCK holders", __func__)); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
typedef struct ath_lock ath_lock_t;
|
||||
#define ATH_LOCK_INIT(_sc) ATH_LOCK_INIT_IMPL(_sc, sc_mtx)
|
||||
#define ATH_LOCK_DESTROY(_sc)
|
||||
#define ATH_LOCK(_sc) ATH_LOCK_IMPL(_sc, sc_mtx)
|
||||
#define ATH_UNLOCK(_sc) ATH_UNLOCK_IMPL(_sc, sc_mtx)
|
||||
#define ATH_LOCK_ASSERT(_sc)
|
||||
|
||||
typedef struct ath_lock ath_txq_lock_t;
|
||||
#define ATH_TXQ_LOCK_INIT(_sc, _tq) ATH_LOCK_INIT_IMPL(_tq, axq_lock)
|
||||
#define ATH_TXQ_LOCK_DESTROY(_tq)
|
||||
#define ATH_TXQ_LOCK(_tq) ATH_LOCK_IMPL(_tq, axq_lock)
|
||||
#define ATH_TXQ_UNLOCK(_tq) ATH_UNLOCK_IMPL(_tq, axq_lock)
|
||||
#define ATH_TXQ_LOCK_ASSERT(_tq)
|
||||
|
||||
typedef struct ath_lock ath_txbuf_lock_t;
|
||||
#define ATH_TXBUF_LOCK_INIT(_sc) ATH_LOCK_INIT_IMPL(_sc, sc_txbuflock)
|
||||
#define ATH_TXBUF_LOCK_DESTROY(_sc)
|
||||
#define ATH_TXBUF_LOCK(_sc) ATH_LOCK_IMPL(_sc, sc_txbuflock)
|
||||
#define ATH_TXBUF_UNLOCK(_sc) ATH_UNLOCK_IMPL(_sc, sc_txbuflock)
|
||||
#define ATH_TXBUF_LOCK_ASSERT(_sc)
|
||||
typedef kmutex_t ath_txbuf_lock_t;
|
||||
#define ATH_TXBUF_LOCK_INIT(_sc) mutex_init(&(_sc)->sc_txbuflock, MUTEX_DEFAULT, IPL_NET)
|
||||
#define ATH_TXBUF_LOCK_DESTROY(_sc) mutex_destroy(&(_sc)->sc_txbuflock)
|
||||
#define ATH_TXBUF_LOCK(_sc) mutex_enter(&(_sc)->sc_txbuflock)
|
||||
#define ATH_TXBUF_UNLOCK(_sc) mutex_exit(&(_sc)->sc_txbuflock)
|
||||
#define ATH_TXBUF_LOCK_ASSERT(_sc) do { KASSERT(mutex_owned(&(_sc)->sc_txbuflock), ("txbuf lock unheld")); } while (/*CONSTCOND*/true)
|
||||
|
||||
#define NET_LOCK_GIANT()
|
||||
#define NET_UNLOCK_GIANT()
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $NetBSD: athvar.h,v 1.34 2011/03/07 11:25:41 cegger Exp $ */
|
||||
/* $NetBSD: athvar.h,v 1.35 2011/10/07 16:58:11 dyoung Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2002-2005 Sam Leffler, Errno Consulting
|
||||
|
@ -201,7 +201,6 @@ struct ath_softc {
|
|||
HAL_BUS_TAG sc_st; /* bus space tag */
|
||||
HAL_BUS_HANDLE sc_sh; /* bus space handle */
|
||||
bus_dma_tag_t sc_dmat; /* bus DMA tag */
|
||||
ath_lock_t sc_mtx; /* master lock (recursive) */
|
||||
struct ath_hal *sc_ah; /* Atheros HAL */
|
||||
struct ath_ratectrl *sc_rc; /* tx rate control support */
|
||||
struct ath_tx99 *sc_tx99; /* tx99 adjunct state */
|
||||
|
|
Loading…
Reference in New Issue