Date: Thu, 9 Mar 2006 22:02:14 GMT From: Warner Losh <imp@FreeBSD.org> To: Perforce Change Reviews <perforce@freebsd.org> Subject: PERFORCE change 93067 for review Message-ID: <200603092202.k29M2E3w035541@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=93067 Change 93067 by imp@imp_Speedy on 2006/03/09 22:02:00 Do not 'break;' when we find one packet. Look for as many as we can each time through. We now keep getting packets until we panic, rather than stopping after a (short) while. Minor code shuffle to reduce indentation insanity. Affected files ... .. //depot/projects/arm/src/sys/arm/at91/if_ate.c#32 edit Differences ... ==== //depot/projects/arm/src/sys/arm/at91/if_ate.c#32 (text+ko) ==== @@ -368,9 +368,10 @@ else sc->rx_descs[i].addr = seg.ds_addr; sc->rx_descs[i].status = 0; + /* Flush the memory in the mbuf */ bus_dmamap_sync(sc->rxtag, sc->rx_map[i], BUS_DMASYNC_PREREAD); - bus_dmamap_sync(sc->rxtag, sc->rx_map[i], BUS_DMASYNC_PREWRITE); } + /* Flush the memory for the EMAC rx descriptor */ bus_dmamap_sync(sc->rx_desc_tag, sc->rx_desc_map, BUS_DMASYNC_PREWRITE); /* Write the descriptor queue address. */ WR4(sc, ETH_RBQP, sc->rx_desc_phys); @@ -578,6 +579,11 @@ struct ate_softc *sc = xsc; int status; int i; + struct mbuf *mb; + bus_dma_segment_t seg; + int rx_stat; + int nsegs; + status = RD4(sc, ETH_ISR); if (status == 0) @@ -588,86 +594,81 @@ bus_dmamap_sync(sc->rx_desc_tag, sc->rx_desc_map, BUS_DMASYNC_POSTREAD); for (i = 0; i < ATE_MAX_RX_BUFFERS; i++) { - if (sc->rx_descs[i].addr & ETH_CPU_OWNER) { - struct mbuf *mb = sc->rx_mbuf[i]; - bus_dma_segment_t seg; - int rx_stat; - int nsegs; + if ((sc->rx_descs[i].addr & ETH_CPU_OWNER) == 0) + continue; - bus_dmamap_sync(sc->rxtag, - sc->rx_map[i], BUS_DMASYNC_POSTREAD); - rx_stat = sc->rx_descs[i].status; - printf("GOT ONE %d %x\n", i, rx_stat); - if ((rx_stat & ETH_LEN_MASK) == 0) { - printf("ignoring bogus 0 len packet\n"); - bus_dmamap_load_mbuf_sg(sc->rxtag, - sc->rx_map[i], sc->rx_mbuf[i], - &seg, &nsegs, 0); - sc->rx_descs[i].status = 0; - sc->rx_descs[i].addr = seg.ds_addr; - if (i == ATE_MAX_RX_BUFFERS - 1) - sc->rx_descs[i].addr |= - ETH_WRAP_BIT; - bus_dmamap_sync(sc->rx_desc_tag, - sc->rx_desc_map, - BUS_DMASYNC_PREWRITE); - bus_dmamap_sync(sc->rxtag, - sc->rx_map[i], - BUS_DMASYNC_PREWRITE); - continue; - } - WR4(sc, ETH_RSR, RD4(sc, ETH_RSR)); - /* - * Allocate a new buffer to replace this one. - * if we cannot, then we drop this packet - * and keep the old buffer we had. Once allocated - * the new buffer is loaded for dma. - */ - sc->rx_mbuf[i] = m_getcl(M_DONTWAIT, MT_DATA, - M_PKTHDR); - sc->rx_mbuf[i]->m_len = - sc->rx_mbuf[i]->m_pkthdr.len = MCLBYTES; - if (!sc->rx_mbuf[i]) { - printf("Failed to get another mbuf -- discarding packet\n"); - sc->rx_mbuf[i] = mb; - sc->rx_descs[i].addr &= ~ETH_CPU_OWNER; - bus_dmamap_sync(sc->rx_desc_tag, - sc->rx_desc_map, - BUS_DMASYNC_PREWRITE); - continue; - } - bus_dmamap_unload(sc->rxtag, sc->rx_map[i]); - if (bus_dmamap_load_mbuf_sg(sc->rxtag, - sc->rx_map[i], - sc->rx_mbuf[i], &seg, &nsegs, 0) != 0) { - printf("Failed to load mbuf -- discarding packet -- reload old?\n"); - sc->rx_mbuf[i] = mb; - sc->rx_descs[i].addr &= ~ETH_CPU_OWNER; - bus_dmamap_sync(sc->rx_desc_tag, - sc->rx_desc_map, - BUS_DMASYNC_PREWRITE); - continue; - } - mb->m_len = rx_stat & ETH_LEN_MASK; - mb->m_pkthdr.len = mb->m_len; - mb->m_pkthdr.rcvif = sc->ifp; - /* - * For the last buffer, set the wrap bit so - * the controller restarts from the first - * descriptor. - */ + mb = sc->rx_mbuf[i]; + rx_stat = sc->rx_descs[i].status; + if ((rx_stat & ETH_LEN_MASK) == 0) { + printf("ignoring bogus 0 len packet\n"); + bus_dmamap_load_mbuf_sg(sc->rxtag, + sc->rx_map[i], sc->rx_mbuf[i], + &seg, &nsegs, 0); sc->rx_descs[i].status = 0; sc->rx_descs[i].addr = seg.ds_addr; if (i == ATE_MAX_RX_BUFFERS - 1) - sc->rx_descs[i].addr |= ETH_WRAP_BIT; - bus_dmamap_sync(sc->rx_desc_tag, - sc->rx_desc_map, - BUS_DMASYNC_PREWRITE); + sc->rx_descs[i].addr |= + ETH_WRAP_BIT; + /* Flush memory for mbuf */ + bus_dmamap_sync(sc->rxtag, sc->rx_map[i], + BUS_DMASYNC_PREREAD); + /* Flush rx dtor table rx_descs */ + bus_dmamap_sync(sc->rx_desc_tag, sc->rx_desc_map, + BUS_DMASYNC_PREWRITE); + continue; + } + + /* Flush memory for mbuf so we don't get stale bytes */ + bus_dmamap_sync(sc->rxtag, sc->rx_map[i], + BUS_DMASYNC_POSTREAD); + printf("GOT ONE %d %x %d\n", i, rx_stat, rx_stat & ETH_LEN_MASK); + WR4(sc, ETH_RSR, RD4(sc, ETH_RSR)); + /* + * Allocate a new buffer to replace this one. + * if we cannot, then we drop this packet + * and keep the old buffer we had. Once allocated + * the new buffer is loaded for dma. + */ + sc->rx_mbuf[i] = m_getcl(M_DONTWAIT, MT_DATA, M_PKTHDR); + if (!sc->rx_mbuf[i]) { + printf("Failed to get another mbuf -- discarding packet\n"); + sc->rx_mbuf[i] = mb; + sc->rx_descs[i].addr &= ~ETH_CPU_OWNER; + bus_dmamap_sync(sc->rxtag, sc->rx_map[i], + BUS_DMASYNC_PREREAD); + bus_dmamap_sync(sc->rx_desc_tag, sc->rx_desc_map, + BUS_DMASYNC_PREWRITE); + continue; + } + bus_dmamap_unload(sc->rxtag, sc->rx_map[i]); + if (bus_dmamap_load_mbuf_sg(sc->rxtag, sc->rx_map[i], + sc->rx_mbuf[i], &seg, &nsegs, 0) != 0) { + printf("Failed to load mbuf -- discarding packet -- reload old?\n"); + sc->rx_mbuf[i] = mb; + sc->rx_descs[i].addr &= ~ETH_CPU_OWNER; bus_dmamap_sync(sc->rxtag, sc->rx_map[i], + BUS_DMASYNC_PREREAD); + bus_dmamap_sync(sc->rx_desc_tag, sc->rx_desc_map, BUS_DMASYNC_PREWRITE); - (*sc->ifp->if_input)(sc->ifp, mb); - break; + continue; } + mb->m_len = rx_stat & ETH_LEN_MASK; + mb->m_pkthdr.len = mb->m_len; + mb->m_pkthdr.rcvif = sc->ifp; + /* + * For the last buffer, set the wrap bit so + * the controller restarts from the first + * descriptor. + */ + sc->rx_descs[i].status = 0; + sc->rx_descs[i].addr = seg.ds_addr; + if (i == ATE_MAX_RX_BUFFERS - 1) + sc->rx_descs[i].addr |= ETH_WRAP_BIT; + bus_dmamap_sync(sc->rxtag, sc->rx_map[i], + BUS_DMASYNC_PREREAD); + bus_dmamap_sync(sc->rx_desc_tag, sc->rx_desc_map, + BUS_DMASYNC_PREWRITE); + (*sc->ifp->if_input)(sc->ifp, mb); } } if (status & ETH_ISR_TCOM) {
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200603092202.k29M2E3w035541>