On Wed, Oct 14, 2020 at 02:20:16PM -0700, Florian Fainelli wrote: > In bcm2835_spi_remove(), spi_controller_unregister() will free the ctlr > reference which will lead to an use after free in bcm2835_release_dma(). > > To avoid this use after free, allocate the bcm2835_spi structure with a > different lifecycle than the spi_controller structure such that we > unregister the SPI controller, free up all the resources and finally let > device managed allocations free the bcm2835_spi structure. [...] > - if (ctlr->dma_tx) { > - dmaengine_terminate_sync(ctlr->dma_tx); > + if (dma_tx) { > + dmaengine_terminate_sync(dma_tx); > > if (bs->fill_tx_desc) > dmaengine_desc_free(bs->fill_tx_desc); > > if (bs->fill_tx_addr) > - dma_unmap_page_attrs(ctlr->dma_tx->device->dev, > + dma_unmap_page_attrs(dma_tx->device->dev, > bs->fill_tx_addr, sizeof(u32), > DMA_TO_DEVICE, > DMA_ATTR_SKIP_CPU_SYNC); > > - dma_release_channel(ctlr->dma_tx); > - ctlr->dma_tx = NULL; > + dma_release_channel(dma_tx); > } You must set ctlr->dma_tx and ctlr->dma_rx to NULL because the driver checks their value in a couple of places. E.g. bcm2835_spi_setup() checks ctlr->dma_rx. Likewise, the error paths of bcm2835_dma_init() and bcm2835_spi_probe() call bcm2835_dma_release() and the latter checks ctlr->dma_tx and ctlr->dma_rx to determine whether DMA was set up, hence needs to be torn down. > + bs = devm_kzalloc(&pdev->dev, sizeof(*bs), GFP_KERNEL); > + if (!bs) > + return -ENOMEM; > + > ctlr = spi_alloc_master(&pdev->dev, ALIGN(sizeof(*bs), > dma_get_cache_alignment())); You can set the second argument to spi_alloc_master() to 0 to conserve memory. Thanks, Lukas