@@ -214,7 +214,8 @@ struct xilinx_dpdma_tx_desc {
214214 * @running: true if the channel is running
215215 * @first_frame: flag for the first frame of stream
216216 * @video_group: flag if multi-channel operation is needed for video channels
217- * @lock: lock to access struct xilinx_dpdma_chan
217+ * @lock: lock to access struct xilinx_dpdma_chan. Must be taken before
218+ * @vchan.lock, if both are to be held.
218219 * @desc_pool: descriptor allocation pool
219220 * @err_task: error IRQ bottom half handler
220221 * @desc: References to descriptors being processed
@@ -1175,12 +1176,14 @@ static void xilinx_dpdma_chan_vsync_irq(struct xilinx_dpdma_chan *chan)
11751176 * Complete the active descriptor, if any, promote the pending
11761177 * descriptor to active, and queue the next transfer, if any.
11771178 */
1179+ spin_lock (& chan -> vchan .lock );
11781180 if (chan -> desc .active )
11791181 vchan_cookie_complete (& chan -> desc .active -> vdesc );
11801182 chan -> desc .active = pending ;
11811183 chan -> desc .pending = NULL ;
11821184
11831185 xilinx_dpdma_chan_queue_transfer (chan );
1186+ spin_unlock (& chan -> vchan .lock );
11841187
11851188out :
11861189 spin_unlock_irqrestore (& chan -> lock , flags );
@@ -1359,10 +1362,12 @@ static void xilinx_dpdma_issue_pending(struct dma_chan *dchan)
13591362 struct xilinx_dpdma_chan * chan = to_xilinx_chan (dchan );
13601363 unsigned long flags ;
13611364
1362- spin_lock_irqsave (& chan -> vchan .lock , flags );
1365+ spin_lock_irqsave (& chan -> lock , flags );
1366+ spin_lock (& chan -> vchan .lock );
13631367 if (vchan_issue_pending (& chan -> vchan ))
13641368 xilinx_dpdma_chan_queue_transfer (chan );
1365- spin_unlock_irqrestore (& chan -> vchan .lock , flags );
1369+ spin_unlock (& chan -> vchan .lock );
1370+ spin_unlock_irqrestore (& chan -> lock , flags );
13661371}
13671372
13681373static int xilinx_dpdma_config (struct dma_chan * dchan ,
@@ -1590,7 +1595,9 @@ static void xilinx_dpdma_chan_err_task(struct tasklet_struct *t)
15901595 XILINX_DPDMA_EINTR_CHAN_ERR_MASK << chan -> id );
15911596
15921597 spin_lock_irqsave (& chan -> lock , flags );
1598+ spin_lock (& chan -> vchan .lock );
15931599 xilinx_dpdma_chan_queue_transfer (chan );
1600+ spin_unlock (& chan -> vchan .lock );
15941601 spin_unlock_irqrestore (& chan -> lock , flags );
15951602}
15961603
0 commit comments