From owner-svn-src-all@FreeBSD.ORG Sun Mar 25 03:14:31 2012 Return-Path: Delivered-To: svn-src-all@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id DA8B8106564A; Sun, 25 Mar 2012 03:14:31 +0000 (UTC) (envelope-from adrian@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:4f8:fff6::2c]) by mx1.freebsd.org (Postfix) with ESMTP id AB6D18FC18; Sun, 25 Mar 2012 03:14:31 +0000 (UTC) Received: from svn.freebsd.org (localhost [127.0.0.1]) by svn.freebsd.org (8.14.4/8.14.4) with ESMTP id q2P3EVX8061495; Sun, 25 Mar 2012 03:14:31 GMT (envelope-from adrian@svn.freebsd.org) Received: (from adrian@localhost) by svn.freebsd.org (8.14.4/8.14.4/Submit) id q2P3EVYt061493; Sun, 25 Mar 2012 03:14:31 GMT (envelope-from adrian@svn.freebsd.org) Message-Id: <201203250314.q2P3EVYt061493@svn.freebsd.org> From: Adrian Chadd Date: Sun, 25 Mar 2012 03:14:31 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Cc: Subject: svn commit: r233453 - head/sys/dev/ath X-BeenThere: svn-src-all@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: "SVN commit messages for the entire src tree \(except for " user" and " projects" \)" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 25 Mar 2012 03:14:31 -0000 Author: adrian Date: Sun Mar 25 03:14:31 2012 New Revision: 233453 URL: http://svn.freebsd.org/changeset/base/233453 Log: Add the new channel width change field to the ath(4) driver. This is not entirely correct as it simply resets the channel, flushing whatever is in the TX/RX queue. This can and will break aggregation BAW tracking. But the alternative (HT40 frames being sent with the hardware in HT20 mode) is even worse. There's still a small window between the htinfo being received (and the ni_chw field being updated) which could cause problems. I'll look at fleshing this out in follow-up commits. PR: kern/166286 Modified: head/sys/dev/ath/if_ath.c Modified: head/sys/dev/ath/if_ath.c ============================================================================== --- head/sys/dev/ath/if_ath.c Sun Mar 25 03:11:57 2012 (r233452) +++ head/sys/dev/ath/if_ath.c Sun Mar 25 03:14:31 2012 (r233453) @@ -199,6 +199,7 @@ static void ath_chan_change(struct ath_s static void ath_scan_start(struct ieee80211com *); static void ath_scan_end(struct ieee80211com *); static void ath_set_channel(struct ieee80211com *); +static void ath_update_chw(struct ieee80211com *); static void ath_calibrate(void *); static int ath_newstate(struct ieee80211vap *, enum ieee80211_state, int); static void ath_setup_stationkey(struct ieee80211_node *); @@ -794,6 +795,7 @@ ath_attach(u_int16_t devid, struct ath_s ic->ic_scan_start = ath_scan_start; ic->ic_scan_end = ath_scan_end; ic->ic_set_channel = ath_set_channel; + ic->ic_update_chw = ath_update_chw; /* 802.11n specific - but just override anyway */ sc->sc_addba_request = ic->ic_addba_request; @@ -5717,6 +5719,31 @@ ath_scan_end(struct ieee80211com *ic) sc->sc_curaid); } +/* + * For now, just do a channel change. + * + * Later, we'll go through the hard slog of suspending tx/rx, changing rate + * control state and resetting the hardware without dropping frames out + * of the queue. + * + * The unfortunate trouble here is making absolutely sure that the + * channel width change has propagated enough so the hardware + * absolutely isn't handed bogus frames for it's current operating + * mode. (Eg, 40MHz frames in 20MHz mode.) Since TX and RX can and + * does occur in parallel, we need to make certain we've blocked + * any further ongoing TX (and RX, that can cause raw TX) + * before we do this. + */ +static void +ath_update_chw(struct ieee80211com *ic) +{ + struct ifnet *ifp = ic->ic_ifp; + struct ath_softc *sc = ifp->if_softc; + + DPRINTF(sc, ATH_DEBUG_STATE, "%s: called\n", __func__); + ath_set_channel(ic); +} + static void ath_set_channel(struct ieee80211com *ic) {