head -r356066 reaching kern.ipc.nmbclusters on Rock64 (CortexA53 with 4GiByte of RAM) while putting files on it via nfs: some evidence

Peter Jeremy peter at rulingia.com
Sat Jan 4 20:35:59 UTC 2020


Sorry for the delay in responding.

On 2019-Dec-27 21:59:49 -0800, Mark Millard via freebsd-arm <freebsd-arm at freebsd.org> wrote:
>The following sort of sequence leads to the Rock64 not
>responding on the console or over ethernet, after notifying
>of nmbclusters having been reached. (This limits what
>information I have of what things were like at the end.)

There's a bug in the dwc(4) driver such that it can leak mbuf clusters.
I've been running with the following patch but need to clean it up
samewhat before I can commit it:

Index: sys/dev/dwc/if_dwc.c
===================================================================
--- sys/dev/dwc/if_dwc.c	(revision 356350)
+++ sys/dev/dwc/if_dwc.c	(working copy)
@@ -755,7 +755,6 @@
 dwc_rxfinish_locked(struct dwc_softc *sc)
 {
 	struct ifnet *ifp;
-	struct mbuf *m0;
 	struct mbuf *m;
 	int error, idx, len;
 	uint32_t rdes0;
@@ -762,9 +761,8 @@
 
 	ifp = sc->ifp;
 
-	for (;;) {
+	for (; ; sc->rx_idx = next_rxidx(sc, sc->rx_idx)) {
 		idx = sc->rx_idx;
-
 		rdes0 = sc->rxdesc_ring[idx].tdes0;
 		if ((rdes0 & DDESC_RDES0_OWN) != 0)
 			break;
@@ -773,9 +771,9 @@
 		    BUS_DMASYNC_POSTREAD);
 		bus_dmamap_unload(sc->rxbuf_tag, sc->rxbuf_map[idx].map);
 
+		m = sc->rxbuf_map[idx].mbuf;
 		len = (rdes0 >> DDESC_RDES0_FL_SHIFT) & DDESC_RDES0_FL_MASK;
 		if (len != 0) {
-			m = sc->rxbuf_map[idx].mbuf;
 			m->m_pkthdr.rcvif = ifp;
 			m->m_pkthdr.len = len;
 			m->m_len = len;
@@ -784,24 +782,33 @@
 			/* Remove trailing FCS */
 			m_adj(m, -ETHER_CRC_LEN);
 
+			/* Consume the mbuf and mark it as consumed */
+			sc->rxbuf_map[idx].mbuf = NULL;
 			DWC_UNLOCK(sc);
 			(*ifp->if_input)(ifp, m);
 			DWC_LOCK(sc);
+			m = NULL;
 		} else {
 			/* XXX Zero-length packet ? */
 		}
 
-		if ((m0 = dwc_alloc_mbufcl(sc)) != NULL) {
-			if ((error = dwc_setup_rxbuf(sc, idx, m0)) != 0) {
-				/*
-				 * XXX Now what?
-				 * We've got a hole in the rx ring.
-				 */
+		if (m == NULL) {
+			if ((m = dwc_alloc_mbufcl(sc)) == NULL) {
+				if_inc_counter(sc->ifp, IFCOUNTER_IQDROPS, 1);
+				continue;
 			}
-		} else
+		}
+
+		if ((error = dwc_setup_rxbuf(sc, idx, m)) != 0) {
+			m_free(m);
+			device_printf(sc->dev,
+			    "dwc_setup_rxbuf returned %d\n", error);
 			if_inc_counter(sc->ifp, IFCOUNTER_IQDROPS, 1);
-
-		sc->rx_idx = next_rxidx(sc, sc->rx_idx);
+			/*
+			 * XXX Now what?
+			 * We've got a hole in the rx ring.
+			 */
+		}
 	}
 }

-- 
Peter Jeremy
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 963 bytes
Desc: not available
URL: <http://lists.freebsd.org/pipermail/freebsd-current/attachments/20200105/ea2db851/attachment.sig>


More information about the freebsd-current mailing list