Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 8 Nov 2012 18:11:31 +0000 (UTC)
From:      Adrian Chadd <adrian@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r242782 - head/sys/dev/ath
Message-ID:  <201211081811.qA8IBVlj036201@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: adrian
Date: Thu Nov  8 18:11:31 2012
New Revision: 242782
URL: http://svnweb.freebsd.org/changeset/base/242782

Log:
  Add some hooks into the driver to attach, detach and record EDMA descriptor
  events.
  
  This is primarily for the TX EDMA and TX EDMA completion. I haven't yet
  tied it into the EDMA RX path or the legacy TX/RX path.
  
  Things that I don't quite like:
  
  * Make the pointer type 'void' in ath_softc and have if_ath_alq*()
    return a malloc'ed buffer.  That would remove the need to include
    if_ath_alq.h in if_athvar.h.
  * The sysctl setup needs to be cleaned up.

Modified:
  head/sys/dev/ath/if_ath_rx.c
  head/sys/dev/ath/if_ath_rx_edma.c
  head/sys/dev/ath/if_ath_sysctl.c
  head/sys/dev/ath/if_ath_tx.c
  head/sys/dev/ath/if_ath_tx_edma.c
  head/sys/dev/ath/if_athvar.h

Modified: head/sys/dev/ath/if_ath_rx.c
==============================================================================
--- head/sys/dev/ath/if_ath_rx.c	Thu Nov  8 18:07:29 2012	(r242781)
+++ head/sys/dev/ath/if_ath_rx.c	Thu Nov  8 18:11:31 2012	(r242782)
@@ -115,6 +115,10 @@ __FBSDID("$FreeBSD$");
 #include <dev/ath/ath_tx99/ath_tx99.h>
 #endif
 
+#ifdef	ATH_DEBUG_ALQ
+#include <dev/ath/if_ath_alq.h>
+#endif
+
 /*
  * Calculate the receive filter according to the
  * operating mode and state:

Modified: head/sys/dev/ath/if_ath_rx_edma.c
==============================================================================
--- head/sys/dev/ath/if_ath_rx_edma.c	Thu Nov  8 18:07:29 2012	(r242781)
+++ head/sys/dev/ath/if_ath_rx_edma.c	Thu Nov  8 18:11:31 2012	(r242782)
@@ -117,6 +117,10 @@ __FBSDID("$FreeBSD$");
 
 #include <dev/ath/if_ath_rx_edma.h>
 
+#ifdef	ATH_DEBUG_ALQ
+#include <dev/ath/if_ath_alq.h>
+#endif
+
 /*
  * some general macros
   */
@@ -357,7 +361,12 @@ ath_edma_recv_proc_queue(struct ath_soft
 #ifdef	ATH_DEBUG
 		if (sc->sc_debug & ATH_DEBUG_RECV_DESC)
 			ath_printrxbuf(sc, bf, 0, bf->bf_rxstatus == HAL_OK);
-#endif
+#endif /* ATH_DEBUG */
+#ifdef	ATH_DEBUG_ALQ
+		if (if_ath_alq_checkdebug(&sc->sc_alq, ATH_ALQ_EDMA_RXSTATUS))
+			if_ath_alq_post(&sc->sc_alq, ATH_ALQ_EDMA_RXSTATUS,
+			    sc->sc_rx_statuslen, (char *) ds);
+#endif /* ATH_DEBUG */
 		if (bf->bf_rxstatus == HAL_EINPROGRESS)
 			break;
 

Modified: head/sys/dev/ath/if_ath_sysctl.c
==============================================================================
--- head/sys/dev/ath/if_ath_sysctl.c	Thu Nov  8 18:07:29 2012	(r242781)
+++ head/sys/dev/ath/if_ath_sysctl.c	Thu Nov  8 18:11:31 2012	(r242782)
@@ -501,6 +501,57 @@ ath_sysctl_forcebstuck(SYSCTL_HANDLER_AR
 	return 0;
 }
 
+
+static int
+ath_sysctl_alq_log(SYSCTL_HANDLER_ARGS)
+{
+	struct ath_softc *sc = arg1;
+	int error, enable;
+
+	enable = (sc->sc_alq.sc_alq_isactive);
+
+	error = sysctl_handle_int(oidp, &enable, 0, req);
+	if (error || !req->newptr)
+		return (error);
+	else if (enable)
+		error = if_ath_alq_start(&sc->sc_alq);
+	else
+		error = if_ath_alq_stop(&sc->sc_alq);
+	return (error);
+}
+
+#ifdef	ATH_DEBUG
+/*
+ * Attach the ALQ debugging if required.
+ */
+static void
+ath_sysctl_alq_attach(struct ath_softc *sc)
+{
+	struct sysctl_oid *tree = device_get_sysctl_tree(sc->sc_dev);
+	struct sysctl_ctx_list *ctx = device_get_sysctl_ctx(sc->sc_dev);
+	struct sysctl_oid_list *child = SYSCTL_CHILDREN(tree);
+
+	tree = SYSCTL_ADD_NODE(ctx, child, OID_AUTO, "alq", CTLFLAG_RD,
+	    NULL, "Atheros ALQ logging parameters");
+	child = SYSCTL_CHILDREN(tree);
+
+	SYSCTL_ADD_STRING(ctx, child, OID_AUTO, "filename",
+	    CTLFLAG_RW, sc->sc_alq.sc_alq_filename, 0, "ALQ filename");
+
+	SYSCTL_ADD_PROC(ctx, SYSCTL_CHILDREN(tree), OID_AUTO,
+		"enable", CTLTYPE_INT | CTLFLAG_RW, sc, 0,
+		ath_sysctl_alq_log, "I", "");
+
+	SYSCTL_ADD_UINT(ctx, SYSCTL_CHILDREN(tree), OID_AUTO,
+		"debugmask", CTLFLAG_RW, &sc->sc_alq.sc_alq_debug, 0,
+		"ALQ debug mask");
+
+	SYSCTL_ADD_UINT(ctx, SYSCTL_CHILDREN(tree), OID_AUTO,
+		"numlost", CTLFLAG_RW, &sc->sc_alq.sc_alq_numlost, 0,
+		"number lost");
+}
+#endif
+
 void
 ath_sysctlattach(struct ath_softc *sc)
 {
@@ -655,6 +706,10 @@ ath_sysctlattach(struct ath_softc *sc)
 			ath_sysctl_setcca, "I", "enable CCA control");
 	}
 #endif
+
+#ifdef	ATH_DEBUG
+	ath_sysctl_alq_attach(sc);
+#endif
 }
 
 static int

Modified: head/sys/dev/ath/if_ath_tx.c
==============================================================================
--- head/sys/dev/ath/if_ath_tx.c	Thu Nov  8 18:07:29 2012	(r242781)
+++ head/sys/dev/ath/if_ath_tx.c	Thu Nov  8 18:11:31 2012	(r242782)
@@ -101,6 +101,10 @@ __FBSDID("$FreeBSD$");
 #include <dev/ath/if_ath_tx.h>
 #include <dev/ath/if_ath_tx_ht.h>
 
+#ifdef	ATH_DEBUG_ALQ
+#include <dev/ath/if_ath_alq.h>
+#endif
+
 /*
  * How many retries to perform in software
  */

Modified: head/sys/dev/ath/if_ath_tx_edma.c
==============================================================================
--- head/sys/dev/ath/if_ath_tx_edma.c	Thu Nov  8 18:07:29 2012	(r242781)
+++ head/sys/dev/ath/if_ath_tx_edma.c	Thu Nov  8 18:11:31 2012	(r242782)
@@ -117,6 +117,10 @@ __FBSDID("$FreeBSD$");
 
 #include <dev/ath/if_ath_tx_edma.h>
 
+#ifdef	ATH_DEBUG_ALQ
+#include <dev/ath/if_ath_alq.h>
+#endif
+
 /*
  * some general macros
  */
@@ -132,6 +136,37 @@ MALLOC_DECLARE(M_ATHDEV);
 
 static void ath_edma_tx_processq(struct ath_softc *sc, int dosched);
 
+#ifdef	ATH_DEBUG_ALQ
+static void
+ath_edma_tx_alq_post(struct ath_softc *sc, struct ath_buf *bf_first)
+{
+	struct ath_buf *bf;
+	int i, n;
+	const char *ds;
+
+	/* XXX we should skip out early if debugging isn't enabled! */
+	bf = bf_first;
+
+	while (bf != NULL) {
+		/* XXX assume nmaps = 4! */
+		/* XXX should ensure bf_nseg > 0! */
+		if (bf->bf_nseg == 0)
+			break;
+		n = ((bf->bf_nseg - 1) / 4) + 1;
+		for (i = 0, ds = (const char *) bf->bf_desc;
+		    i < n;
+		    i++, ds += sc->sc_tx_desclen) {
+			if_ath_alq_post(&sc->sc_alq,
+			    ATH_ALQ_EDMA_TXDESC,
+			    96,
+			    ds);
+		}
+
+		bf = bf->bf_next;
+	}
+}
+#endif /* ATH_DEBUG_ALQ */
+
 static void
 ath_edma_tx_fifo_fill(struct ath_softc *sc, struct ath_txq *txq)
 {
@@ -149,7 +184,11 @@ ath_edma_tx_fifo_fill(struct ath_softc *
 #ifdef	ATH_DEBUG
 		if (sc->sc_debug & ATH_DEBUG_XMIT_DESC)
 			ath_printtxbuf(sc, bf, txq->axq_qnum, i, 0);
-#endif
+#endif/* ATH_DEBUG */
+#ifdef	ATH_DEBUG_ALQ
+		if (if_ath_alq_checkdebug(&sc->sc_alq, ATH_ALQ_EDMA_TXDESC))
+			ath_edma_tx_alq_post(sc, bf);
+#endif /* ATH_DEBUG_ALQ */
 		txq->axq_fifo_depth++;
 		i++;
 	}
@@ -163,10 +202,6 @@ ath_edma_tx_fifo_fill(struct ath_softc *
  *
  * This should only be called as part of the chip reset path, as it
  * assumes the FIFO is currently empty.
- *
- * TODO: verify that a cold/warm reset does clear the TX FIFO, so
- * writing in a partially-filled FIFO will not cause double-entries
- * to appear.
  */
 static void
 ath_edma_dma_restart(struct ath_softc *sc, struct ath_txq *txq)
@@ -222,7 +257,11 @@ ath_edma_xmit_handoff_hw(struct ath_soft
 #ifdef	ATH_DEBUG
 		if (sc->sc_debug & ATH_DEBUG_XMIT_DESC)
 			ath_printtxbuf(sc, bf, txq->axq_qnum, 0, 0);
-#endif	/* ATH_DEBUG */
+#endif /* ATH_DEBUG */
+#ifdef	ATH_DEBUG_ALQ
+		if (if_ath_alq_checkdebug(&sc->sc_alq, ATH_ALQ_EDMA_TXDESC))
+			ath_edma_tx_alq_post(sc, bf);
+#endif	/* ATH_DEBUG_ALQ */
 		ath_hal_puttxbuf(ah, txq->axq_qnum, bf->bf_daddr);
 		txq->axq_fifo_depth++;
 		ath_hal_txstart(ah, txq->axq_qnum);
@@ -368,7 +407,6 @@ ath_edma_dma_txsetup(struct ath_softc *s
 		ath_edma_setup_txfifo(sc, i);
 	}
 
-
 	return (0);
 }
 
@@ -489,6 +527,13 @@ ath_edma_tx_processq(struct ath_softc *s
 			continue;
 		}
 
+#ifdef	ATH_DEBUG_ALQ
+		if (if_ath_alq_checkdebug(&sc->sc_alq, ATH_ALQ_EDMA_TXSTATUS))
+			if_ath_alq_post(&sc->sc_alq, ATH_ALQ_EDMA_TXSTATUS,
+			    sc->sc_tx_statuslen,
+			    (char *) txstatus);
+#endif /* ATH_DEBUG_ALQ */
+
 		/*
 		 * At this point we have a valid status descriptor.
 		 * The QID and descriptor ID (which currently isn't set)

Modified: head/sys/dev/ath/if_athvar.h
==============================================================================
--- head/sys/dev/ath/if_athvar.h	Thu Nov  8 18:07:29 2012	(r242781)
+++ head/sys/dev/ath/if_athvar.h	Thu Nov  8 18:11:31 2012	(r242782)
@@ -42,6 +42,9 @@
 #include <net80211/ieee80211_radiotap.h>
 #include <dev/ath/if_athioctl.h>
 #include <dev/ath/if_athrate.h>
+#ifdef	ATH_DEBUG_ALQ
+#include <dev/ath/if_ath_alq.h>
+#endif
 
 #define	ATH_TIMEOUT		1000
 
@@ -770,6 +773,11 @@ struct ath_softc {
 	int			sc_dodfs;	/* Whether to enable DFS rx filter bits */
 	struct task		sc_dfstask;	/* DFS processing task */
 
+	/* ALQ */
+#ifdef	ATH_DEBUG
+	struct if_ath_alq sc_alq;
+#endif
+
 	/* TX AMPDU handling */
 	int			(*sc_addba_request)(struct ieee80211_node *,
 				    struct ieee80211_tx_ampdu *, int, int, int);



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201211081811.qA8IBVlj036201>