From owner-svn-src-head@freebsd.org Sat Nov 18 21:12:07 2017 Return-Path: Delivered-To: svn-src-head@mailman.ysv.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:1900:2254:206a::19:1]) by mailman.ysv.freebsd.org (Postfix) with ESMTP id A0811DDC78F; Sat, 18 Nov 2017 21:12:07 +0000 (UTC) (envelope-from manu@FreeBSD.org) Received: from repo.freebsd.org (repo.freebsd.org [IPv6:2610:1c1:1:6068::e6a:0]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by mx1.freebsd.org (Postfix) with ESMTPS id 6AABB7DD27; Sat, 18 Nov 2017 21:12:07 +0000 (UTC) (envelope-from manu@FreeBSD.org) Received: from repo.freebsd.org ([127.0.1.37]) by repo.freebsd.org (8.15.2/8.15.2) with ESMTP id vAILC6g2035147; Sat, 18 Nov 2017 21:12:06 GMT (envelope-from manu@FreeBSD.org) Received: (from manu@localhost) by repo.freebsd.org (8.15.2/8.15.2/Submit) id vAILC6C8035146; Sat, 18 Nov 2017 21:12:06 GMT (envelope-from manu@FreeBSD.org) Message-Id: <201711182112.vAILC6C8035146@repo.freebsd.org> X-Authentication-Warning: repo.freebsd.org: manu set sender to manu@FreeBSD.org using -f From: Emmanuel Vadot Date: Sat, 18 Nov 2017 21:12:06 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r325985 - head/sys/arm/allwinner X-SVN-Group: head X-SVN-Commit-Author: manu X-SVN-Commit-Paths: head/sys/arm/allwinner X-SVN-Commit-Revision: 325985 X-SVN-Commit-Repository: base MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.25 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sat, 18 Nov 2017 21:12:07 -0000 Author: manu Date: Sat Nov 18 21:12:06 2017 New Revision: 325985 URL: https://svnweb.freebsd.org/changeset/base/325985 Log: if_awg: drain tx buffers and clear rx buffers when stopping Stale packets should not be transmitted when the interface comes up after being down. Count the successfully transmitted ones for statistics and drop the rest. Submitted by: Guy Yur Differential Revision: https://reviews.freebsd.org/D12539 Modified: head/sys/arm/allwinner/if_awg.c Modified: head/sys/arm/allwinner/if_awg.c ============================================================================== --- head/sys/arm/allwinner/if_awg.c Sat Nov 18 21:08:18 2017 (r325984) +++ head/sys/arm/allwinner/if_awg.c Sat Nov 18 21:12:06 2017 (r325985) @@ -215,6 +215,8 @@ static struct resource_spec awg_spec[] = { { -1, 0 } }; +static void awg_txeof(struct awg_softc *sc); + static int awg_miibus_readreg(device_t dev, int phy, int reg) { @@ -809,6 +811,7 @@ awg_stop(struct awg_softc *sc) { if_t ifp; uint32_t val; + int i; AWG_ASSERT_LOCKED(sc); @@ -842,6 +845,39 @@ awg_stop(struct awg_softc *sc) WR4(sc, EMAC_RX_CTL_1, val & ~RX_DMA_EN); sc->link = 0; + + /* Finish handling transmitted buffers */ + awg_txeof(sc); + + /* Release any untransmitted buffers. */ + for (i = sc->tx.next; sc->tx.queued > 0; i = TX_NEXT(i)) { + val = le32toh(sc->tx.desc_ring[i].status); + if ((val & TX_DESC_CTL) != 0) + break; + awg_clean_txbuf(sc, i); + } + sc->tx.next = i; + for (; sc->tx.queued > 0; i = TX_NEXT(i)) { + sc->tx.desc_ring[i].status = 0; + awg_clean_txbuf(sc, i); + } + sc->tx.cur = sc->tx.next; + bus_dmamap_sync(sc->tx.desc_tag, sc->tx.desc_map, + BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE); + + /* Setup RX buffers for reuse */ + bus_dmamap_sync(sc->rx.desc_tag, sc->rx.desc_map, + BUS_DMASYNC_POSTREAD | BUS_DMASYNC_POSTWRITE); + + for (i = sc->rx.cur; ; i = RX_NEXT(i)) { + val = le32toh(sc->rx.desc_ring[i].status); + if ((val & RX_DESC_CTL) != 0) + break; + awg_reuse_rxdesc(sc, i); + } + sc->rx.cur = i; + bus_dmamap_sync(sc->rx.desc_tag, sc->rx.desc_map, + BUS_DMASYNC_PREREAD | BUS_DMASYNC_PREWRITE); if_setdrvflagbits(ifp, 0, IFF_DRV_RUNNING | IFF_DRV_OACTIVE); }