> -----Original Message----- > From: Intel-xe <intel-xe-bounces@xxxxxxxxxxxxxxxxxxxxx> On Behalf Of Maarten > Lankhorst > Sent: Wednesday, May 22, 2024 11:04 AM > To: intel-gfx@xxxxxxxxxxxxxxxxxxxxx > Cc: intel-xe@xxxxxxxxxxxxxxxxxxxxx; Maarten Lankhorst > <maarten.lankhorst@xxxxxxxxxxxxxxx>; Borah, Chaitanya Kumar > <chaitanya.kumar.borah@xxxxxxxxx> > Subject: [v6 1/3] drm: Add drm_vblank_work_flush_all(). Nit: Drop the "." from patch header > In some cases we want to flush all vblank work, right before vblank_off for > example. Add a simple function to make this possible. > > Check that both pending_work and running work are empty when flushing. Have been closely following the developments and approaches. This version looks good to me. Reviewed-by: Uma Shankar <uma.shankar@xxxxxxxxx> > Co-Developed-by: Chaitanya Kumar Borah <chaitanya.kumar.borah@xxxxxxxxx> > Signed-off-by: Maarten Lankhorst <maarten.lankhorst@xxxxxxxxxxxxxxx> > --- > drivers/gpu/drm/drm_vblank_work.c | 22 ++++++++++++++++++++++ > include/drm/drm_vblank_work.h | 2 ++ > 2 files changed, 24 insertions(+) > > diff --git a/drivers/gpu/drm/drm_vblank_work.c > b/drivers/gpu/drm/drm_vblank_work.c > index 4fe9b1d3b00f..1752ffb44e1d 100644 > --- a/drivers/gpu/drm/drm_vblank_work.c > +++ b/drivers/gpu/drm/drm_vblank_work.c > @@ -232,6 +232,28 @@ void drm_vblank_work_flush(struct drm_vblank_work > *work) } EXPORT_SYMBOL(drm_vblank_work_flush); > > +/** > + * drm_vblank_work_flush_all - flush all currently pending vblank work on crtc. > + * @crtc: crtc for which vblank work to flush > + * > + * Wait until all currently queued vblank work on @crtc > + * has finished executing once. > + */ > +void drm_vblank_work_flush_all(struct drm_crtc *crtc) { > + struct drm_device *dev = crtc->dev; > + struct drm_vblank_crtc *vblank = &dev->vblank[drm_crtc_index(crtc)]; > + > + spin_lock_irq(&dev->event_lock); > + wait_event_lock_irq(vblank->work_wait_queue, > + list_empty(&vblank->pending_work), > + dev->event_lock); > + spin_unlock_irq(&dev->event_lock); > + > + kthread_flush_worker(vblank->worker); > +} > +EXPORT_SYMBOL(drm_vblank_work_flush_all); > + > /** > * drm_vblank_work_init - initialize a vblank work item > * @work: vblank work item > diff --git a/include/drm/drm_vblank_work.h b/include/drm/drm_vblank_work.h > index eb41d0810c4f..e04d436b7297 100644 > --- a/include/drm/drm_vblank_work.h > +++ b/include/drm/drm_vblank_work.h > @@ -17,6 +17,7 @@ struct drm_crtc; > * drm_vblank_work_init() > * drm_vblank_work_cancel_sync() > * drm_vblank_work_flush() > + * drm_vblank_work_flush_all() > */ > struct drm_vblank_work { > /** > @@ -67,5 +68,6 @@ void drm_vblank_work_init(struct drm_vblank_work *work, > struct drm_crtc *crtc, > void (*func)(struct kthread_work *work)); bool > drm_vblank_work_cancel_sync(struct drm_vblank_work *work); void > drm_vblank_work_flush(struct drm_vblank_work *work); > +void drm_vblank_work_flush_all(struct drm_crtc *crtc); > > #endif /* !_DRM_VBLANK_WORK_H_ */ > -- > 2.43.0