Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 13 Apr 2018 15:59:25 +0000 (UTC)
From:      Ruslan Bukin <br@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r332474 - in head/sys: dev/altera/atse dts/mips mips/conf
Message-ID:  <201804131559.w3DFxPFl014741@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: br
Date: Fri Apr 13 15:59:24 2018
New Revision: 332474
URL: https://svnweb.freebsd.org/changeset/base/332474

Log:
  Convert atse(4) driver for Altera Triple-Speed Ethernet MegaCore to use
  xdma(4) interface.
  
  This allows us to switch between Altera mSGDMA or SoftDMA engines used by
  atse(4) device.
  
  This also makes atse(4) driver become 25% smaller.
  
  Sponsored by:	DARPA, AFRL
  Differential Revision:	https://reviews.freebsd.org/D9618

Modified:
  head/sys/dev/altera/atse/if_atse.c
  head/sys/dev/altera/atse/if_atse_fdt.c
  head/sys/dev/altera/atse/if_atse_nexus.c
  head/sys/dev/altera/atse/if_atsereg.h
  head/sys/dts/mips/beripad-de4.dts
  head/sys/mips/conf/BERI_DE4_BASE

Modified: head/sys/dev/altera/atse/if_atse.c
==============================================================================
--- head/sys/dev/altera/atse/if_atse.c	Fri Apr 13 15:18:06 2018	(r332473)
+++ head/sys/dev/altera/atse/if_atse.c	Fri Apr 13 15:59:24 2018	(r332474)
@@ -3,6 +3,7 @@
  *
  * Copyright (c) 2012, 2013 Bjoern A. Zeeb
  * Copyright (c) 2014 Robert N. M. Watson
+ * Copyright (c) 2016-2017 Ruslan Bukin <br@bsdpad.com>
  * All rights reserved.
  *
  * This software was developed by SRI International and the University of
@@ -88,29 +89,21 @@ __FBSDID("$FreeBSD$");
 #include <dev/mii/miivar.h>
 
 #include <dev/altera/atse/if_atsereg.h>
-#include <dev/altera/softdma/a_api.h>
+#include <dev/xdma/xdma.h>
 
-MODULE_DEPEND(atse, ether, 1, 1, 1);
-MODULE_DEPEND(atse, miibus, 1, 1, 1);
+#define	RX_QUEUE_SIZE		4096
+#define	TX_QUEUE_SIZE		4096
+#define	NUM_RX_MBUF		512
+#define	BUFRING_SIZE		8192
 
+#include <machine/cache.h>
 
-#define	ATSE_WATCHDOG_TIME	5
-
-#ifdef DEVICE_POLLING
-static poll_handler_t atse_poll;
-#endif
-
 /* XXX once we'd do parallel attach, we need a global lock for this. */
 #define	ATSE_ETHERNET_OPTION_BITS_UNDEF	0
 #define	ATSE_ETHERNET_OPTION_BITS_READ	1
 static int atse_ethernet_option_bits_flag = ATSE_ETHERNET_OPTION_BITS_UNDEF;
 static uint8_t atse_ethernet_option_bits[ALTERA_ETHERNET_OPTION_BITS_LEN];
 
-static int	atse_intr_debug_enable = 0;
-SYSCTL_INT(_debug, OID_AUTO, atse_intr_debug_enable, CTLFLAG_RW,
-    &atse_intr_debug_enable, 0,
-   "Extra debugging output for atse interrupts");
-
 /*
  * Softc and critical resource locking.
  */
@@ -118,155 +111,15 @@ SYSCTL_INT(_debug, OID_AUTO, atse_intr_debug_enable, C
 #define	ATSE_UNLOCK(_sc)	mtx_unlock(&(_sc)->atse_mtx)
 #define	ATSE_LOCK_ASSERT(_sc)	mtx_assert(&(_sc)->atse_mtx, MA_OWNED)
 
-#define	ATSE_TX_PENDING(sc)	(sc->atse_tx_m != NULL ||		\
-				    !IFQ_DRV_IS_EMPTY(&ifp->if_snd))
+#define ATSE_DEBUG
+#undef ATSE_DEBUG
 
-#ifdef DEBUG
+#ifdef ATSE_DEBUG
 #define	DPRINTF(format, ...)	printf(format, __VA_ARGS__)
 #else
 #define	DPRINTF(format, ...)
 #endif
 
-/* a_api.c functions; factor out? */
-static inline void
-a_onchip_fifo_mem_core_write(struct resource *res, uint32_t off,
-    uint32_t val4, const char *desc, const char *f, const int l)
-{
-
-	val4 = htole32(val4);
-	DPRINTF("[%s:%d] FIFOW %s 0x%08x = 0x%08x\n", f, l, desc, off, val4);
-	bus_write_4(res, off, val4);
-}
-
-static inline uint32_t
-a_onchip_fifo_mem_core_read(struct resource *res, uint32_t off,
-    const char *desc, const char *f, const int l)
-{
-	uint32_t val4;
-
-	val4 = le32toh(bus_read_4(res, off));
-	DPRINTF("[%s:%d] FIFOR %s 0x%08x = 0x%08x\n", f, l, desc, off, val4);
-
-	return (val4);
-}
-
-/* The FIFO does an endian conversion, so we must not do it as well. */
-/* XXX-BZ in fact we should do a htobe32 so le would be fine as well? */
-#define	ATSE_TX_DATA_WRITE(sc, val4)					\
-	bus_write_4((sc)->atse_tx_mem_res, A_ONCHIP_FIFO_MEM_CORE_DATA, val4)
-
-#define	ATSE_TX_META_WRITE(sc, val4)					\
-	a_onchip_fifo_mem_core_write((sc)->atse_tx_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_METADATA,				\
-	    (val4), "TXM", __func__, __LINE__)
-#define	ATSE_TX_META_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_tx_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_METADATA,				\
-	    "TXM", __func__, __LINE__)
-
-#define	ATSE_TX_READ_FILL_LEVEL(sc)					\
-	a_onchip_fifo_mem_core_read((sc)->atse_txc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_FILL_LEVEL,		\
-	    "TX_FILL", __func__, __LINE__)
-#define	ATSE_RX_READ_FILL_LEVEL(sc)					\
-	a_onchip_fifo_mem_core_read((sc)->atse_rxc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_FILL_LEVEL,		\
-	    "RX_FILL", __func__, __LINE__)
-
-/* The FIFO does an endian conversion, so we must not do it as well. */
-/* XXX-BZ in fact we should do a htobe32 so le would be fine as well? */
-#define	ATSE_RX_DATA_READ(sc)						\
-	bus_read_4((sc)->atse_rx_mem_res, A_ONCHIP_FIFO_MEM_CORE_DATA)
-#define	ATSE_RX_META_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_rx_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_METADATA,				\
-	    "RXM", __func__, __LINE__)
-
-#define	ATSE_RX_STATUS_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_rxc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_I_STATUS,			\
-	    "RX_EVENT", __func__, __LINE__)
-
-#define	ATSE_TX_STATUS_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_txc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_I_STATUS,			\
-	    "TX_EVENT", __func__, __LINE__)
-
-#define	ATSE_RX_EVENT_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_rxc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_EVENT,			\
-	    "RX_EVENT", __func__, __LINE__)
-
-#define	ATSE_TX_EVENT_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_txc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_EVENT,			\
-	    "TX_EVENT", __func__, __LINE__)
-
-#define	ATSE_RX_EVENT_CLEAR(sc)						\
-	do {								\
-		uint32_t val4;						\
-									\
-		val4 = a_onchip_fifo_mem_core_read(			\
-		    (sc)->atse_rxc_mem_res,				\
-		    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_EVENT,		\
-		    "RX_EVENT", __func__, __LINE__);			\
-		if (val4 != 0x00)					\
-			a_onchip_fifo_mem_core_write(			\
-			    (sc)->atse_rxc_mem_res,			\
-			    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_EVENT,	\
-			    val4, "RX_EVENT", __func__, __LINE__);	\
-	} while(0)
-#define	ATSE_TX_EVENT_CLEAR(sc)						\
-	do {								\
-		uint32_t val4;						\
-									\
-		val4 = a_onchip_fifo_mem_core_read(			\
-		    (sc)->atse_txc_mem_res,				\
-		    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_EVENT,		\
-		    "TX_EVENT", __func__, __LINE__);			\
-		if (val4 != 0x00)					\
-			a_onchip_fifo_mem_core_write(			\
-			    (sc)->atse_txc_mem_res,			\
-			    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_EVENT,	\
-			    val4, "TX_EVENT", __func__, __LINE__);	\
-	} while(0)
-
-#define	ATSE_RX_EVENTS	(A_ONCHIP_FIFO_MEM_CORE_INTR_FULL |	\
-			    A_ONCHIP_FIFO_MEM_CORE_INTR_OVERFLOW |	\
-			    A_ONCHIP_FIFO_MEM_CORE_INTR_UNDERFLOW)
-#define	ATSE_RX_INTR_ENABLE(sc)						\
-	a_onchip_fifo_mem_core_write((sc)->atse_rxc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_INT_ENABLE,		\
-	    ATSE_RX_EVENTS,						\
-	    "RX_INTR", __func__, __LINE__)	/* XXX-BZ review later. */
-#define	ATSE_RX_INTR_DISABLE(sc)					\
-	a_onchip_fifo_mem_core_write((sc)->atse_rxc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_INT_ENABLE, 0,		\
-	    "RX_INTR", __func__, __LINE__)
-#define	ATSE_RX_INTR_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_rxc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_INT_ENABLE,		\
-	    "RX_INTR", __func__, __LINE__)
-
-#define	ATSE_TX_EVENTS	(A_ONCHIP_FIFO_MEM_CORE_INTR_EMPTY |		\
-			    A_ONCHIP_FIFO_MEM_CORE_INTR_OVERFLOW |	\
-			    A_ONCHIP_FIFO_MEM_CORE_INTR_UNDERFLOW)
-#define	ATSE_TX_INTR_ENABLE(sc)						\
-	a_onchip_fifo_mem_core_write((sc)->atse_txc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_INT_ENABLE,		\
-	    ATSE_TX_EVENTS,						\
-	    "TX_INTR", __func__, __LINE__)	/* XXX-BZ review later. */
-#define	ATSE_TX_INTR_DISABLE(sc)					\
-	a_onchip_fifo_mem_core_write((sc)->atse_txc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_INT_ENABLE, 0,		\
-	    "TX_INTR", __func__, __LINE__)
-#define	ATSE_TX_INTR_READ(sc)						\
-	a_onchip_fifo_mem_core_read((sc)->atse_txc_mem_res,		\
-	    A_ONCHIP_FIFO_MEM_CORE_STATUS_REG_INT_ENABLE,		\
-	    "TX_INTR", __func__, __LINE__)
-
-static int	atse_rx_locked(struct atse_softc *sc);
-
 /*
  * Register space access macros.
  */
@@ -345,146 +198,194 @@ static int atse_detach(device_t);
 devclass_t atse_devclass;
 
 static int
-atse_tx_locked(struct atse_softc *sc, int *sent)
+atse_rx_enqueue(struct atse_softc *sc, uint32_t n)
 {
 	struct mbuf *m;
-	uint32_t val4, fill_level;
-	int leftm;
-	int c;
+	int i;
 
-	ATSE_LOCK_ASSERT(sc);
+	for (i = 0; i < n; i++) {
+		m = m_getcl(M_NOWAIT, MT_DATA, M_PKTHDR);
+		if (m == NULL) {
+			device_printf(sc->dev,
+			    "%s: Can't alloc rx mbuf\n", __func__);
+			return (-1);
+		}
 
-	m = sc->atse_tx_m;
-	KASSERT(m != NULL, ("%s: m is null: sc=%p", __func__, sc));
-	KASSERT(m->m_flags & M_PKTHDR, ("%s: not a pkthdr: m=%p", __func__, m));
-
-	/*
-	 * Copy to buffer to minimize our pain as we can only store
-	 * double words which, after the first mbuf gets out of alignment
-	 * quite quickly.
-	 */
-	if (sc->atse_tx_m_offset == 0) {
-		m_copydata(m, 0, m->m_pkthdr.len, sc->atse_tx_buf);
-		sc->atse_tx_buf_len = m->m_pkthdr.len;
+		m->m_pkthdr.len = m->m_len = m->m_ext.ext_size;
+		xdma_enqueue_mbuf(sc->xchan_rx, &m, 0, 4, 4, XDMA_DEV_TO_MEM);
 	}
 
-	fill_level = ATSE_TX_READ_FILL_LEVEL(sc);
-#if 0	/* Returns 0xdeadc0de. */
-	val4 = ATSE_TX_META_READ(sc);
-#endif
-	if (sc->atse_tx_m_offset == 0) {
-		/* Write start of packet. */
-		val4 = A_ONCHIP_FIFO_MEM_CORE_SOP;
-		val4 &= ~A_ONCHIP_FIFO_MEM_CORE_EOP;
-		ATSE_TX_META_WRITE(sc, val4);
+	return (0);
+}
+
+static int
+atse_xdma_tx_intr(void *arg, xdma_transfer_status_t *status)
+{
+	xdma_transfer_status_t st;
+	struct atse_softc *sc;
+	struct ifnet *ifp;
+	struct mbuf *m;
+	int err;
+
+	sc = arg;
+
+	ATSE_LOCK(sc);
+
+	ifp = sc->atse_ifp;
+
+	for (;;) {
+		err = xdma_dequeue_mbuf(sc->xchan_tx, &m, &st);
+		if (err != 0) {
+			break;
+		}
+
+		if (st.error != 0) {
+			if_inc_counter(ifp, IFCOUNTER_OERRORS, 1);
+		}
+
+		m_freem(m);
+		sc->txcount--;
 	}
 
-	/* TX FIFO is single clock mode, so we have the full FIFO. */
-	c = 0;
-	while ((sc->atse_tx_buf_len - sc->atse_tx_m_offset) > 4 &&
-	     fill_level < AVALON_FIFO_TX_BASIC_OPTS_DEPTH) {
+	ifp->if_drv_flags &= ~IFF_DRV_OACTIVE;
 
-		bcopy(&sc->atse_tx_buf[sc->atse_tx_m_offset], &val4,
-		    sizeof(val4));
-		ATSE_TX_DATA_WRITE(sc, val4);
-		sc->atse_tx_m_offset += sizeof(val4);
-		c += sizeof(val4);
+	ATSE_UNLOCK(sc);
 
-		fill_level++;
-		if (fill_level == AVALON_FIFO_TX_BASIC_OPTS_DEPTH)
-			fill_level = ATSE_TX_READ_FILL_LEVEL(sc);
+	return (0);
+}
+
+static int
+atse_xdma_rx_intr(void *arg, xdma_transfer_status_t *status)
+{
+	xdma_transfer_status_t st;
+	struct atse_softc *sc;
+	struct ifnet *ifp;
+	struct mbuf *m;
+	int err;
+	uint32_t cnt_processed;
+
+	sc = arg;
+
+	ATSE_LOCK(sc);
+
+	ifp = sc->atse_ifp;
+
+	cnt_processed = 0;
+	for (;;) {
+		err = xdma_dequeue_mbuf(sc->xchan_rx, &m, &st);
+		if (err != 0) {
+			break;
+		}
+		cnt_processed++;
+
+		if (st.error != 0) {
+			if_inc_counter(ifp, IFCOUNTER_IERRORS, 1);
+			m_freem(m);
+			continue;
+		}
+
+		m->m_pkthdr.len = m->m_len = st.transferred;
+		m->m_pkthdr.rcvif = ifp;
+		m_adj(m, ETHER_ALIGN);
+		ATSE_UNLOCK(sc);
+		(*ifp->if_input)(ifp, m);
+		ATSE_LOCK(sc);
 	}
-	if (sent != NULL)
-		*sent += c;
 
-	/* Set EOP *before* writing the last symbol. */
-	if (sc->atse_tx_m_offset >= (sc->atse_tx_buf_len - 4) &&
-	    fill_level < AVALON_FIFO_TX_BASIC_OPTS_DEPTH) {
+	atse_rx_enqueue(sc, cnt_processed);
 
-		/* Set EndOfPacket. */
-		val4 = A_ONCHIP_FIFO_MEM_CORE_EOP;
+	ATSE_UNLOCK(sc);
 
-		/* Set EMPTY. */
-		leftm = sc->atse_tx_buf_len - sc->atse_tx_m_offset;
-		val4 |= ((4 - leftm) << A_ONCHIP_FIFO_MEM_CORE_EMPTY_SHIFT);
-		ATSE_TX_META_WRITE(sc, val4);
+	return (0);
+}
 
-		/* Write last symbol. */
-		val4 = 0;
-		bcopy(sc->atse_tx_buf + sc->atse_tx_m_offset, &val4, leftm);
-		ATSE_TX_DATA_WRITE(sc, val4);
+static int
+atse_transmit_locked(struct ifnet *ifp)
+{
+	struct atse_softc *sc;
+	struct mbuf *m;
+	struct buf_ring *br;
+	int error;
+	int enq;
 
-		if (sent != NULL)
-			*sent += leftm;
+	sc = ifp->if_softc;
+	br = sc->br;
 
-		/* OK, the packet is gone. */
-		sc->atse_tx_m = NULL;
-		sc->atse_tx_m_offset = 0;
+	enq = 0;
 
+	while ((m = drbr_peek(ifp, br)) != NULL) {
+		error = xdma_enqueue_mbuf(sc->xchan_tx, &m, 0, 4, 4, XDMA_MEM_TO_DEV);
+		if (error != 0) {
+			/* No space in request queue available yet. */
+			drbr_putback(ifp, br, m);
+			break;
+		}
+
+		drbr_advance(ifp, br);
+
+		sc->txcount++;
+		enq++;
+
 		/* If anyone is interested give them a copy. */
-		BPF_MTAP(sc->atse_ifp, m);
+		ETHER_BPF_MTAP(ifp, m);
+        }
 
-		m_freem(m);
-		return (0);
-	}
+	if (enq > 0)
+		xdma_queue_submit(sc->xchan_tx);
 
-	return (EBUSY);
+	return (0);
 }
 
-static void
-atse_start_locked(struct ifnet *ifp)
+static int
+atse_transmit(struct ifnet *ifp, struct mbuf *m)
 {
 	struct atse_softc *sc;
-	int error, sent;
+	struct buf_ring *br;
+	int error;
 
 	sc = ifp->if_softc;
-	ATSE_LOCK_ASSERT(sc);
+	br = sc->br;
 
-	if ((ifp->if_drv_flags & (IFF_DRV_RUNNING | IFF_DRV_OACTIVE)) !=
-	    IFF_DRV_RUNNING || (sc->atse_flags & ATSE_FLAGS_LINK) == 0)
-		return;
+	ATSE_LOCK(sc);
 
-#if 1
-	/*
-	 * Disable the watchdog while sending, we are batching packets.
-	 * Though we should never reach 5 seconds, and are holding the lock,
-	 * but who knows.
-	 */
-	sc->atse_watchdog_timer = 0;
-#endif
+	mtx_lock(&sc->br_mtx);
 
-	if (sc->atse_tx_m != NULL) {
-		error = atse_tx_locked(sc, &sent);
-		if (error != 0)
-			goto done;
+	if ((ifp->if_drv_flags & (IFF_DRV_RUNNING | IFF_DRV_OACTIVE)) != IFF_DRV_RUNNING) {
+		error = drbr_enqueue(ifp, sc->br, m);
+		mtx_unlock(&sc->br_mtx);
+		ATSE_UNLOCK(sc);
+		return (error);
 	}
-	/* We have more space to send so continue ... */
-	for (; !IFQ_DRV_IS_EMPTY(&ifp->if_snd); ) {
 
-		IFQ_DRV_DEQUEUE(&ifp->if_snd, sc->atse_tx_m);
-		sc->atse_tx_m_offset = 0;
-		if (sc->atse_tx_m == NULL)
-			break;
-		error = atse_tx_locked(sc, &sent);
-		if (error != 0)
-			goto done;
+	if ((sc->atse_flags & ATSE_FLAGS_LINK) == 0) {
+		error = drbr_enqueue(ifp, sc->br, m);
+		mtx_unlock(&sc->br_mtx);
+		ATSE_UNLOCK(sc);
+		return (error);
 	}
 
-done:
-	/* If the IP core walks into Nekromanteion try to bail out. */
-	if (sent > 0)
-		sc->atse_watchdog_timer = ATSE_WATCHDOG_TIME;
+	error = drbr_enqueue(ifp, br, m);
+	if (error) {
+		mtx_unlock(&sc->br_mtx);
+		ATSE_UNLOCK(sc);
+		return (error);
+	}
+	error = atse_transmit_locked(ifp);
+
+	mtx_unlock(&sc->br_mtx);
+	ATSE_UNLOCK(sc);
+
+	return (error);
 }
 
 static void
-atse_start(struct ifnet *ifp)
+atse_qflush(struct ifnet *ifp)
 {
 	struct atse_softc *sc;
 
 	sc = ifp->if_softc;
-	ATSE_LOCK(sc);
-	atse_start_locked(ifp);
-	ATSE_UNLOCK(sc);
+
+	printf("%s\n", __func__);
 }
 
 static int
@@ -496,36 +397,33 @@ atse_stop_locked(struct atse_softc *sc)
 
 	ATSE_LOCK_ASSERT(sc);
 
-	sc->atse_watchdog_timer = 0;
 	callout_stop(&sc->atse_tick);
 
 	ifp = sc->atse_ifp;
 	ifp->if_drv_flags &= ~(IFF_DRV_RUNNING | IFF_DRV_OACTIVE);
-	ATSE_RX_INTR_DISABLE(sc);
-	ATSE_TX_INTR_DISABLE(sc);
-	ATSE_RX_EVENT_CLEAR(sc);
-	ATSE_TX_EVENT_CLEAR(sc);
 
 	/* Disable MAC transmit and receive datapath. */
 	mask = BASE_CFG_COMMAND_CONFIG_TX_ENA|BASE_CFG_COMMAND_CONFIG_RX_ENA;
 	val4 = CSR_READ_4(sc, BASE_CFG_COMMAND_CONFIG);
 	val4 &= ~mask;
 	CSR_WRITE_4(sc, BASE_CFG_COMMAND_CONFIG, val4);
+
 	/* Wait for bits to be cleared; i=100 is excessive. */
 	for (i = 0; i < 100; i++) {
 		val4 = CSR_READ_4(sc, BASE_CFG_COMMAND_CONFIG);
-		if ((val4 & mask) == 0)
+		if ((val4 & mask) == 0) {
 			break;
+		}
 		DELAY(10);
 	}
-	if ((val4 & mask) != 0)
+
+	if ((val4 & mask) != 0) {
 		device_printf(sc->atse_dev, "Disabling MAC TX/RX timed out.\n");
 		/* Punt. */
+	}
 
 	sc->atse_flags &= ~ATSE_FLAGS_LINK;
 
-	/* XXX-BZ free the RX/TX rings. */
-
 	return (0);
 }
 
@@ -561,10 +459,11 @@ atse_rxfilter_locked(struct atse_softc *sc)
 		val4 &= ~BASE_CFG_COMMAND_CONFIG_MHASH_SEL;
 
 	ifp = sc->atse_ifp;
-	if (ifp->if_flags & IFF_PROMISC)
+	if (ifp->if_flags & IFF_PROMISC) {
 		val4 |= BASE_CFG_COMMAND_CONFIG_PROMIS_EN;
-	else
+	} else {
 		val4 &= ~BASE_CFG_COMMAND_CONFIG_PROMIS_EN;
+	}
 
 	CSR_WRITE_4(sc, BASE_CFG_COMMAND_CONFIG, val4);
 
@@ -587,16 +486,18 @@ atse_rxfilter_locked(struct atse_softc *sc)
 		 */
 		if_maddr_rlock(ifp);
 		TAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
-			if (ifma->ifma_addr->sa_family != AF_LINK)
+			if (ifma->ifma_addr->sa_family != AF_LINK) {
 				continue;
+			}
 
 			h |= (1 << atse_mchash(sc,
 			    LLADDR((struct sockaddr_dl *)ifma->ifma_addr)));
 		}
 		if_maddr_runlock(ifp);
-		for (i = 0; i <= MHASH_LEN; i++)
+		for (i = 0; i <= MHASH_LEN; i++) {
 			CSR_WRITE_4(sc, MHASH_START + i,
 			    (h & (1 << i)) ? 0x01 : 0x00);
+		}
 	}
 
 	return (0);
@@ -609,22 +510,26 @@ atse_ethernet_option_bits_read_fdt(device_t dev)
 	device_t fdev;
 	int i, rid;
 
-	if (atse_ethernet_option_bits_flag & ATSE_ETHERNET_OPTION_BITS_READ)
+	if (atse_ethernet_option_bits_flag & ATSE_ETHERNET_OPTION_BITS_READ) {
 		return (0);
+	}
 
 	fdev = device_find_child(device_get_parent(dev), "cfi", 0);
-	if (fdev == NULL)
+	if (fdev == NULL) {
 		return (ENOENT);
+	}
 
 	rid = 0;
 	res = bus_alloc_resource_any(fdev, SYS_RES_MEMORY, &rid,
 	    RF_ACTIVE | RF_SHAREABLE);
-	if (res == NULL)
+	if (res == NULL) {
 		return (ENXIO);
+	}
 
-	for (i = 0; i < ALTERA_ETHERNET_OPTION_BITS_LEN; i++)
+	for (i = 0; i < ALTERA_ETHERNET_OPTION_BITS_LEN; i++) {
 		atse_ethernet_option_bits[i] = bus_read_1(res,
 		    ALTERA_ETHERNET_OPTION_BITS_OFF + i);
+	}
 
 	bus_release_resource(fdev, SYS_RES_MEMORY, rid, res);
 	atse_ethernet_option_bits_flag |= ATSE_ETHERNET_OPTION_BITS_READ;
@@ -658,12 +563,14 @@ atse_get_eth_address(struct atse_softc *sc)
 	 * possibly change our ethernet address, which is not good at all.
 	 */
 	if (sc->atse_eth_addr[0] != 0x00 || sc->atse_eth_addr[1] != 0x00 ||
-	    sc->atse_eth_addr[2] != 0x00)
+	    sc->atse_eth_addr[2] != 0x00) {
 		return (0);
+	}
 
 	if ((atse_ethernet_option_bits_flag &
-	    ATSE_ETHERNET_OPTION_BITS_READ) == 0)
+	    ATSE_ETHERNET_OPTION_BITS_READ) == 0) {
 		goto get_random;
+	}
 
 	val4 = atse_ethernet_option_bits[0] << 24;
 	val4 |= atse_ethernet_option_bits[1] << 16;
@@ -718,8 +625,9 @@ atse_get_eth_address(struct atse_softc *sc)
 	 * Ethernet, go to random.
 	 */
 	unit = device_get_unit(sc->atse_dev);
-	if (unit == 0x00)
+	if (unit == 0x00) {
 		return (0);
+	}
 
 	if (unit > 0x0f) {
 		device_printf(sc->atse_dev, "We do not support Ethernet "
@@ -831,8 +739,9 @@ atse_reset(struct atse_softc *sc)
 	/* Wait for reset bit to clear; i=100 is excessive. */
 	for (i = 0; i < 100; i++) {
 		val = PCS_READ_2(sc, PCS_CONTROL);
-		if ((val & PCS_CONTROL_RESET) == 0)
+		if ((val & PCS_CONTROL_RESET) == 0) {
 			break;
+		}
 		DELAY(10);
 	}
 
@@ -851,8 +760,9 @@ atse_reset(struct atse_softc *sc)
 	/* Wait for bits to be cleared; i=100 is excessive. */
 	for (i = 0; i < 100; i++) {
 		val4 = CSR_READ_4(sc, BASE_CFG_COMMAND_CONFIG);
-		if ((val4 & mask) == 0)
+		if ((val4 & mask) == 0) {
 			break;
+		}
 		DELAY(10);
 	}
 	if ((val4 & mask) != 0) {
@@ -926,8 +836,10 @@ atse_reset(struct atse_softc *sc)
 	val4 = CSR_READ_4(sc, TX_CMD_STAT);
 	val4 &= ~(TX_CMD_STAT_OMIT_CRC|TX_CMD_STAT_TX_SHIFT16);
 	CSR_WRITE_4(sc, TX_CMD_STAT, val4);
+
 	val4 = CSR_READ_4(sc, RX_CMD_STAT);
 	val4 &= ~RX_CMD_STAT_RX_SHIFT16;
+	val4 |= RX_CMD_STAT_RX_SHIFT16;
 	CSR_WRITE_4(sc, RX_CMD_STAT, val4);
 
 	/* e. Reset MAC. */
@@ -937,8 +849,9 @@ atse_reset(struct atse_softc *sc)
 	/* Wait for bits to be cleared; i=100 is excessive. */
 	for (i = 0; i < 100; i++) {
 		val4 = CSR_READ_4(sc, BASE_CFG_COMMAND_CONFIG);
-		if ((val4 & BASE_CFG_COMMAND_CONFIG_SW_RESET) == 0)
+		if ((val4 & BASE_CFG_COMMAND_CONFIG_SW_RESET) == 0) {
 			break;
+		}
 		DELAY(10);
 	}
 	if ((val4 & BASE_CFG_COMMAND_CONFIG_SW_RESET) != 0) {
@@ -954,8 +867,9 @@ atse_reset(struct atse_softc *sc)
 	/* Wait for bits to be cleared; i=100 is excessive. */
 	for (i = 0; i < 100; i++) {
 		val4 = CSR_READ_4(sc, BASE_CFG_COMMAND_CONFIG);
-		if ((val4 & mask) == mask)
+		if ((val4 & mask) == mask) {
 			break;
+		}
 		DELAY(10);
 	}
 	if ((val4 & mask) != mask) {
@@ -976,8 +890,9 @@ atse_init_locked(struct atse_softc *sc)
 	ATSE_LOCK_ASSERT(sc);
 	ifp = sc->atse_ifp;
 
-	if ((ifp->if_drv_flags & IFF_DRV_RUNNING) != 0)
+	if ((ifp->if_drv_flags & IFF_DRV_RUNNING) != 0) {
 		return;
+	}
 
 	/*
 	 * Must update the ether address if changed.  Given we do not handle
@@ -989,31 +904,14 @@ atse_init_locked(struct atse_softc *sc)
 
 	/* Make things frind to halt, cleanup, ... */
 	atse_stop_locked(sc);
-	/* ... reset, ... */
+
 	atse_reset(sc);
 
 	/* ... and fire up the engine again. */
 	atse_rxfilter_locked(sc);
 
-	/* Memory rings?  DMA engine? */
-
-	sc->atse_rx_buf_len = 0;
 	sc->atse_flags &= ATSE_FLAGS_LINK;	/* Preserve. */
 
-#ifdef DEVICE_POLLING
-	/* Only enable interrupts if we are not polling. */
-	if (ifp->if_capenable & IFCAP_POLLING) {
-		ATSE_RX_INTR_DISABLE(sc);
-		ATSE_TX_INTR_DISABLE(sc);
-		ATSE_RX_EVENT_CLEAR(sc);
-		ATSE_TX_EVENT_CLEAR(sc);
-	} else
-#endif
-	{
-		ATSE_RX_INTR_ENABLE(sc);
-		ATSE_TX_INTR_ENABLE(sc);
-	}
-
 	mii = device_get_softc(sc->atse_miibus);
 
 	sc->atse_flags &= ~ATSE_FLAGS_LINK;
@@ -1070,39 +968,6 @@ atse_ioctl(struct ifnet *ifp, u_long command, caddr_t 
 	case SIOCSIFCAP:
 		ATSE_LOCK(sc);
 		mask = ifr->ifr_reqcap ^ ifp->if_capenable;
-#ifdef DEVICE_POLLING
-		if ((mask & IFCAP_POLLING) != 0 &&
-		    (IFCAP_POLLING & ifp->if_capabilities) != 0) {
-			ifp->if_capenable ^= IFCAP_POLLING;
-			if ((IFCAP_POLLING & ifp->if_capenable) != 0) {
-
-				error = ether_poll_register(atse_poll, ifp);
-				if (error != 0) {
-					ATSE_UNLOCK(sc);
-					break;
-				}
-				/* Disable interrupts. */
-				ATSE_RX_INTR_DISABLE(sc);
-				ATSE_TX_INTR_DISABLE(sc);
-				ATSE_RX_EVENT_CLEAR(sc);
-				ATSE_TX_EVENT_CLEAR(sc);
-
-			/*
-			 * Do not allow disabling of polling if we do
-			 * not have interrupts.
-			 */
-			} else if (sc->atse_rx_irq_res != NULL ||
-			    sc->atse_tx_irq_res != NULL) {
-				error = ether_poll_deregister(ifp);
-				/* Enable interrupts. */
-				ATSE_RX_INTR_ENABLE(sc);
-				ATSE_TX_INTR_ENABLE(sc);
-			} else {
-				ifp->if_capenable ^= IFCAP_POLLING;
-				error = EINVAL;
-			}
-		}
-#endif /* DEVICE_POLLING */
 		ATSE_UNLOCK(sc);
 		break;
 	case SIOCADDMULTI:
@@ -1131,55 +996,6 @@ atse_ioctl(struct ifnet *ifp, u_long command, caddr_t 
 }
 
 static void
-atse_intr_debug(struct atse_softc *sc, const char *intrname)
-{
-	uint32_t rxs, rxe, rxi, rxf, txs, txe, txi, txf;
-
-	if (!atse_intr_debug_enable)
-		return;
-
-	rxs = ATSE_RX_STATUS_READ(sc);
-	rxe = ATSE_RX_EVENT_READ(sc);
-	rxi = ATSE_RX_INTR_READ(sc);
-	rxf = ATSE_RX_READ_FILL_LEVEL(sc);
-
-	txs = ATSE_TX_STATUS_READ(sc);
-	txe = ATSE_TX_EVENT_READ(sc);
-	txi = ATSE_TX_INTR_READ(sc);
-	txf = ATSE_TX_READ_FILL_LEVEL(sc);
-
-	printf(
-	    "%s - %s: "
-	    "rxs 0x%x rxe 0x%x rxi 0x%x rxf 0x%x "
-	    "txs 0x%x txe 0x%x txi 0x%x txf 0x%x\n",
-	    __func__, intrname,
-	    rxs, rxe, rxi, rxf,
-	    txs, txe, txi, txf);
-}
-
-static void
-atse_watchdog(struct atse_softc *sc)
-{
-
-	ATSE_LOCK_ASSERT(sc);
-
-	if (sc->atse_watchdog_timer == 0 || --sc->atse_watchdog_timer > 0)
-		return;
-
-	device_printf(sc->atse_dev, "watchdog timeout\n");
-	if_inc_counter(sc->atse_ifp, IFCOUNTER_OERRORS, 1);
-
-	atse_intr_debug(sc, "poll");
-
-	sc->atse_ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
-	atse_init_locked(sc);
-
-	atse_rx_locked(sc);
-	if (!IFQ_DRV_IS_EMPTY(&sc->atse_ifp->if_snd))
-		atse_start_locked(sc->atse_ifp);
-}
-
-static void
 atse_tick(void *xsc)
 {
 	struct atse_softc *sc;
@@ -1192,9 +1008,10 @@ atse_tick(void *xsc)
 
 	mii = device_get_softc(sc->atse_miibus);
 	mii_tick(mii);
-	atse_watchdog(sc);
-	if ((sc->atse_flags & ATSE_FLAGS_LINK) == 0)
+	if ((sc->atse_flags & ATSE_FLAGS_LINK) == 0) {
 		atse_miibus_statchg(sc->atse_dev);
+	}
+
 	callout_reset(&sc->atse_tick, hz, atse_tick, sc);
 }
 
@@ -1213,171 +1030,15 @@ atse_ifmedia_upd(struct ifnet *ifp)
 
 	ATSE_LOCK(sc);
 	mii = device_get_softc(sc->atse_miibus);
-	LIST_FOREACH(miisc, &mii->mii_phys, mii_list)
+	LIST_FOREACH(miisc, &mii->mii_phys, mii_list) {
 		PHY_RESET(miisc);
+	}
 	error = mii_mediachg(mii);
 	ATSE_UNLOCK(sc);
 
 	return (error);
 }
 
-static void
-atse_update_rx_err(struct atse_softc *sc, uint32_t mask)
-{
-	int i;
-
-	/* RX error are 6 bits, we only know 4 of them. */
-	for (i = 0; i < ATSE_RX_ERR_MAX; i++)
-		if ((mask & (1 << i)) != 0)
-			sc->atse_rx_err[i]++;
-}
-
-static int
-atse_rx_locked(struct atse_softc *sc)
-{
-	uint32_t fill, i, j;
-	uint32_t data, meta;
-	struct ifnet *ifp;
-	struct mbuf *m;
-	int rx_npkts;
-
-	ATSE_LOCK_ASSERT(sc);
-
-	ifp = sc->atse_ifp;
-	rx_npkts = 0;
-	j = 0;
-	meta = 0;
-	do {
-outer:
-		if (sc->atse_rx_m == NULL) {
-			m = m_getcl(M_NOWAIT, MT_DATA, M_PKTHDR);
-			if (m == NULL)
-				return (rx_npkts);
-			m->m_len = m->m_pkthdr.len = MCLBYTES;
-			/* Make sure upper layers will be aligned. */
-			m_adj(m, ETHER_ALIGN);
-			sc->atse_rx_m = m;
-		}
-
-		fill = ATSE_RX_READ_FILL_LEVEL(sc);
-		for (i = 0; i < fill; i++) {
-			/*
-			 * XXX-BZ for whatever reason the FIFO requires the
-			 * the data read before we can access the meta data.
-			 */
-			data = ATSE_RX_DATA_READ(sc);
-			meta = ATSE_RX_META_READ(sc);
-			if (meta & A_ONCHIP_FIFO_MEM_CORE_ERROR_MASK) {
-				/* XXX-BZ evaluate error. */
-				atse_update_rx_err(sc, ((meta &
-				    A_ONCHIP_FIFO_MEM_CORE_ERROR_MASK) >>
-				    A_ONCHIP_FIFO_MEM_CORE_ERROR_SHIFT) & 0xff);
-				if_inc_counter(ifp, IFCOUNTER_IERRORS, 1);
-				sc->atse_rx_buf_len = 0;
-				/*
-				 * Should still read till EOP or next SOP.
-				 *
-				 * XXX-BZ might also depend on
-				 * BASE_CFG_COMMAND_CONFIG_RX_ERR_DISC
-				 */
-				sc->atse_flags |= ATSE_FLAGS_ERROR;
-				return (rx_npkts);
-			}
-			if ((meta & A_ONCHIP_FIFO_MEM_CORE_CHANNEL_MASK) != 0)
-				device_printf(sc->atse_dev, "%s: unexpected "
-				    "channel %u\n", __func__, (meta &
-				    A_ONCHIP_FIFO_MEM_CORE_CHANNEL_MASK) >>
-				    A_ONCHIP_FIFO_MEM_CORE_CHANNEL_SHIFT);
-
-			if (meta & A_ONCHIP_FIFO_MEM_CORE_SOP) {
-				/*
-				 * There is no need to clear SOP between 1st
-				 * and subsequent packet data junks.
-				 */
-				if (sc->atse_rx_buf_len != 0 &&
-				    (sc->atse_flags & ATSE_FLAGS_SOP_SEEN) == 0)
-				{
-					device_printf(sc->atse_dev, "%s: SOP "
-					    "without empty buffer: %u\n",
-					    __func__, sc->atse_rx_buf_len);
-					/* XXX-BZ any better counter? */
-					if_inc_counter(ifp, IFCOUNTER_IERRORS, 1);
-				}
-
-				if ((sc->atse_flags & ATSE_FLAGS_SOP_SEEN) == 0)
-				{
-					sc->atse_flags |= ATSE_FLAGS_SOP_SEEN;
-					sc->atse_rx_buf_len = 0;
-				}
-			}
-#if 0 /* We had to read the data before we could access meta data. See above. */
-			data = ATSE_RX_DATA_READ(sc);
-#endif
-			/* Make sure to not overflow the mbuf data size. */
-			if (sc->atse_rx_buf_len >= sc->atse_rx_m->m_len -
-			    sizeof(data)) {
-				/*
-				 * XXX-BZ Error.  We need more mbufs and are
-				 * not setup for this yet.
-				 */
-				if_inc_counter(ifp, IFCOUNTER_IERRORS, 1);
-				sc->atse_flags |= ATSE_FLAGS_ERROR;
-			}
-			if ((sc->atse_flags & ATSE_FLAGS_ERROR) == 0)
-				/*
-				 * MUST keep this bcopy as m_data after m_adj
-				 * for IP header aligment is on half-word
-				 * and not word alignment.
-				 */
-				bcopy(&data, (uint8_t *)(sc->atse_rx_m->m_data +
-				    sc->atse_rx_buf_len), sizeof(data));
-			if (meta & A_ONCHIP_FIFO_MEM_CORE_EOP) {
-				uint8_t empty;
-
-				empty = (meta &
-				    A_ONCHIP_FIFO_MEM_CORE_EMPTY_MASK) >>
-				    A_ONCHIP_FIFO_MEM_CORE_EMPTY_SHIFT;
-				sc->atse_rx_buf_len += (4 - empty);
-
-				if_inc_counter(ifp, IFCOUNTER_IPACKETS, 1);
-				rx_npkts++;
-
-				m = sc->atse_rx_m;
-				m->m_pkthdr.len = m->m_len =
-				    sc->atse_rx_buf_len;
-				sc->atse_rx_m = NULL;
-
-				sc->atse_rx_buf_len = 0;
-				sc->atse_flags &= ~ATSE_FLAGS_SOP_SEEN;
-				if (sc->atse_flags & ATSE_FLAGS_ERROR) {
-					sc->atse_flags &= ~ATSE_FLAGS_ERROR;
-					m_freem(m);
-				} else {
-					m->m_pkthdr.rcvif = ifp;
-					ATSE_UNLOCK(sc);
-					(*ifp->if_input)(ifp, m);
-					ATSE_LOCK(sc);
-				}
-#ifdef DEVICE_POLLING
-				if (ifp->if_capenable & IFCAP_POLLING) {
-					if (sc->atse_rx_cycles <= 0)
-						return (rx_npkts);
-					sc->atse_rx_cycles--;

*** DIFF OUTPUT TRUNCATED AT 1000 LINES ***



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