Date: Thu, 21 Nov 2019 02:49:41 +0000 (UTC) From: Kyle Evans <kevans@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r354933 - head/sys/arm/broadcom/bcm2835 Message-ID: <201911210249.xAL2ngIp046333@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: kevans Date: Thu Nov 21 02:49:41 2019 New Revision: 354933 URL: https://svnweb.freebsd.org/changeset/base/354933 Log: bcm2835_sdhci: clean up DMA segments in error handling path Later parts assume that this would've been done if interrupts are enabled, but this is the only case in which that wouldn't have been true. This commit also reorders operations such that we're done touching slot/slot->intmask before we call back into the SDHCI framework and exit. Modified: head/sys/arm/broadcom/bcm2835/bcm2835_sdhci.c Modified: head/sys/arm/broadcom/bcm2835/bcm2835_sdhci.c ============================================================================== --- head/sys/arm/broadcom/bcm2835/bcm2835_sdhci.c Thu Nov 21 02:47:55 2019 (r354932) +++ head/sys/arm/broadcom/bcm2835/bcm2835_sdhci.c Thu Nov 21 02:49:41 2019 (r354933) @@ -607,6 +607,25 @@ bcm_sdhci_dma_exit(struct bcm_sdhci_softc *sc) } static void +bcm_sdhci_dma_unload(struct bcm_sdhci_softc *sc) +{ + struct sdhci_slot *slot = &sc->sc_slot; + + if (sc->dmamap_seg_count == 0) + return; + if ((slot->curcmd->data->flags & MMC_DATA_READ) != 0) + bus_dmamap_sync(sc->sc_dma_tag, sc->sc_dma_map, + BUS_DMASYNC_POSTREAD); + else + bus_dmamap_sync(sc->sc_dma_tag, sc->sc_dma_map, + BUS_DMASYNC_POSTWRITE); + bus_dmamap_unload(sc->sc_dma_tag, sc->sc_dma_map); + + sc->dmamap_seg_count = 0; + sc->dmamap_seg_index = 0; +} + +static void bcm_sdhci_dma_intr(int ch, void *arg) { struct bcm_sdhci_softc *sc = (struct bcm_sdhci_softc *)arg; @@ -626,19 +645,8 @@ bcm_sdhci_dma_intr(int ch, void *arg) goto out; } - if (sc->dmamap_seg_count == 0) - return; - if ((slot->curcmd->data->flags & MMC_DATA_READ) != 0) - bus_dmamap_sync(sc->sc_dma_tag, sc->sc_dma_map, - BUS_DMASYNC_POSTREAD); - else - bus_dmamap_sync(sc->sc_dma_tag, sc->sc_dma_map, - BUS_DMASYNC_POSTWRITE); - bus_dmamap_unload(sc->sc_dma_tag, sc->sc_dma_map); + bcm_sdhci_dma_unload(sc); - sc->dmamap_seg_count = 0; - sc->dmamap_seg_index = 0; - /* * If we had no further segments pending, we need to determine how to * proceed next. If the 'data/space pending' bit is already set and we @@ -654,8 +662,10 @@ bcm_sdhci_dma_intr(int ch, void *arg) bcm_sdhci_start_dma(slot); if (slot->curcmd->error != 0) { - sdhci_finish_data(slot); + /* We won't recover from this error for this command. */ + bcm_sdhci_dma_unload(sc); bcm_sdhci_dma_exit(sc); + sdhci_finish_data(slot); } } else if ((reg & SDHCI_INT_DATA_END) != 0) { bcm_sdhci_dma_exit(sc); @@ -754,16 +764,7 @@ bcm_sdhci_finish_transfer(device_t dev, struct sdhci_s * regressed to SDHCI-driven PIO to finish the operation and * this is certainly caused by developer-error. */ - if (slot->curcmd->data->flags & MMC_DATA_READ) - bus_dmamap_sync(sc->sc_dma_tag, sc->sc_dma_map, - BUS_DMASYNC_POSTREAD); - else - bus_dmamap_sync(sc->sc_dma_tag, sc->sc_dma_map, - BUS_DMASYNC_POSTWRITE); - bus_dmamap_unload(sc->sc_dma_tag, sc->sc_dma_map); - - sc->dmamap_seg_count = 0; - sc->dmamap_seg_index = 0; + bcm_sdhci_dma_unload(sc); } sdhci_finish_data(slot);
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201911210249.xAL2ngIp046333>