From: sashiko-bot@kernel.org
To: "Thomas Zimmermann" <tzimmermann@suse.de>
Cc: dri-devel@lists.freedesktop.org
Subject: Re: [PATCH 2/2] drm/vblank: Cancel vblank timer outside of critical section
Date: Thu, 05 Nov 2026 15:16:56 +0000 [thread overview]
Message-ID: <sashiko-outbox-199305@kernel.org> (raw)
In-Reply-To: <20261105145946.896674-3-tzimmermann@suse.de>
Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:
- [High] drm/vblank: uninitialized spinlock in drm_crtc_vblank_cancel_timer()
--
commit 0925c513110481f6c38259e0df588ad4194770ca
Author: Thomas Zimmermann <tzimmermann@suse.de>
drm/vblank: Cancel vblank timer outside of critical section
This commit introduces a sync_vblank callback in struct drm_crtc_funcs so
that vblank timers can be synchronously canceled via hrtimer_cancel() outside
of vblank_time_lock. It also adds drm_crtc_vblank_stop_canceled_timer() and
drm_crtc_vblank_stop_timer(), and updates vmwgfx and the vblank timer helpers
to use them.
> diff --git a/drivers/gpu/drm/drm_vblank.c b/drivers/gpu/drm/drm_vblank.c
> index 8cc8d018d353a..ca3a6f17564b5 100644
> --- a/drivers/gpu/drm/drm_vblank.c
> +++ b/drivers/gpu/drm/drm_vblank.c
[ ... ]
> @@ -2246,28 +2249,58 @@ EXPORT_SYMBOL(drm_crtc_vblank_start_timer);
> * @crtc: the CRTC
> *
> * Drivers should call this function from their CRTC's disable_vblank
> - * function to stop a vblank timer.
> + * function to stop a vblank timer. Only signals the timer to stop at
> + * the next invocation. Non-blocking. To fully stop the vblank timer,
> + * drivers should invoke drm_crtc_vblank_stop_timer().
> */
> void drm_crtc_vblank_cancel_timer(struct drm_crtc *crtc)
> {
> struct drm_vblank_crtc *vblank = drm_crtc_vblank_crtc(crtc);
> struct drm_vblank_crtc_timer *vtimer = &vblank->vblank_timer;
> - unsigned long flags;
>
> /*
> - * Calling hrtimer_cancel() can result in a deadlock with DRM's
> - * vblank_time_lime_lock and hrtimers' softirq_expiry_lock. So
> + * Calling hrtimer_cancel() here can result in a deadlock between
> + * DRM's vblank_time_lock and hrtimers' softirq_expiry_lock. So
> * clear interval and indicate cancellation. The timer function
> - * will cancel itself on the next invocation.
> + * will cancel itself on the next invocation. Otherwise cancel it
> + * in drm_crtc_vblank_stop_canceled_timer().
> */
> + scoped_guard(spinlock_irqsave, &vtimer->interval_lock)
> + vtimer->interval = 0;
> +}
> +EXPORT_SYMBOL(drm_crtc_vblank_cancel_timer);
> +
> +/**
> + * drm_crtc_vblank_stop_canceled_timer - Stops a CRTC's previously canceled vblank timer
> + * @crtc: the CRTC
> + *
> + * Drivers should call this function from their CRTC's sync_vblank
> + * function to fully stop a vblank timer. The timer must have been
> + * canceled before. Use drm_crtc_vblank_stop_timer() to stop a vblank
> + * timer unconditionally.
> + *
> + * The function blocks until a running timer function has returned.
> + */
> +void drm_crtc_vblank_stop_canceled_timer(struct drm_crtc *crtc)
> +{
> + struct drm_vblank_crtc *vblank = drm_crtc_vblank_crtc(crtc);
> + struct drm_vblank_crtc_timer *vtimer = &vblank->vblank_timer;
> + ktime_t interval;
>
> - spin_lock_irqsave(&vtimer->interval_lock, flags);
> - vtimer->interval = 0;
> - spin_unlock_irqrestore(&vtimer->interval_lock, flags);
> + if (!vtimer->crtc)
> + return;
[Severity: High]
Should drm_crtc_vblank_cancel_timer() also check for !vtimer->crtc before
acquiring vtimer->interval_lock?
In drm_vblank_init(), dev->vblank is allocated with drmm_kcalloc(), leaving
vtimer zero-initialized. Both vtimer->crtc and vtimer->interval_lock are
only initialized lazily on the first call to drm_crtc_vblank_start_timer():
drivers/gpu/drm/drm_vblank.c:drm_crtc_vblank_start_timer() {
if (!vtimer->crtc) {
/*
* Set up the data structures on the first invocation.
*/
vtimer->crtc = crtc;
spin_lock_init(&vtimer->interval_lock);
hrtimer_setup(&vtimer->timer, drm_vblank_timer_function,
CLOCK_MONOTONIC, HRTIMER_MODE_REL);
}
While drm_crtc_vblank_stop_canceled_timer() guards against an uninitialized
timer with if (!vtimer->crtc) return, drm_crtc_vblank_stop_timer() calls
drm_crtc_vblank_cancel_timer() first:
vmw_vkms_crtc_cleanup()
-> drm_crtc_vblank_stop_timer()
-> drm_crtc_vblank_cancel_timer()
-> scoped_guard(spinlock_irqsave, &vtimer->interval_lock)
-> drm_crtc_vblank_stop_canceled_timer()
When vmw_vkms_crtc_cleanup() runs during CRTC teardown on a display unit
where vblank was never enabled, wouldn't drm_crtc_vblank_cancel_timer() lock
vtimer->interval_lock before spin_lock_init() has ever been called on it?
--
Sashiko AI review · https://sashiko.dev/#/patchset/20261105145946.896674-1-tzimmermann@suse.de?part=2
prev parent reply other threads:[~2026-11-05 15:17 UTC|newest]
Thread overview: 4+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-11-05 14:41 [PATCH 0/2] drm/vblank: timer: Fix race condition in enable_vblank Thomas Zimmermann
2026-11-05 14:41 ` [PATCH 1/2] drm/vblank: timer: Do not block within critical section Thomas Zimmermann
2026-11-05 14:41 ` [PATCH 2/2] drm/vblank: Cancel vblank timer outside of " Thomas Zimmermann
2026-11-05 15:16 ` sashiko-bot [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=sashiko-outbox-199305@kernel.org \
--to=sashiko-bot@kernel.org \
--cc=dri-devel@lists.freedesktop.org \
--cc=sashiko-reviews@lists.linux.dev \
--cc=tzimmermann@suse.de \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox