summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2016-04-06 22:50:28 +0100
committerChris Wilson <chris@chris-wilson.co.uk>2016-04-06 22:55:39 +0100
commit74b755fe0a786d330d121c435d274e2418003581 (patch)
tree46a926678c534d993a7c48849b5a889f72aa56cb /src
parent2077272b12ab299e1f25a16408476da0b51477b7 (diff)
sna/present: Clear flags on the vblank event's CRTC early
We store a flag on the vblank's CRTC to indicate whether we have marked the target CRTC as having an immediately pending vblank. We should clear this set of flags early so that we don't have to worry about the flag whilst processing the vblank, and so that we don't get confused if we have to requeue the vblank. Reported-by: Christoph Haag <haagch@frickel.club> Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=94829#c32 Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Diffstat (limited to 'src')
-rw-r--r--src/sna/sna_present.c14
1 files changed, 9 insertions, 5 deletions
diff --git a/src/sna/sna_present.c b/src/sna/sna_present.c
index 3998043a..6e1beaee 100644
--- a/src/sna/sna_present.c
+++ b/src/sna/sna_present.c
@@ -126,7 +126,7 @@ static void vblank_complete(struct sna_present_event *info,
DBG(("%s: %d events complete\n", __FUNCTION__, info->n_event_id));
for (n = 0; n < info->n_event_id; n++) {
DBG(("%s: pipe=%d tv=%d.%06d msc=%lld (target=%lld), event=%lld complete%s\n", __FUNCTION__,
- sna_crtc_pipe(unmask_crtc(info->crtc)),
+ sna_crtc_pipe(info->crtc),
(int)(ust / 1000000), (int)(ust % 1000000),
(long long)msc, (long long)info->target_msc,
(long long)info->event_id[n],
@@ -360,18 +360,22 @@ void
sna_present_vblank_handler(struct drm_event_vblank *event)
{
struct sna_present_event *info = to_present_event(event->user_data);
- xf86CrtcPtr crtc = info->crtc;
if (!info->queued) {
DBG(("%s: arrived unexpectedly early (not queued)\n", __FUNCTION__));
+ assert(!has_vblank(info->crtc));
return;
}
+ if (has_vblank(info->crtc)) {
+ DBG(("%s: clearing immediate flag\n", __FUNCTION__));
+ info->crtc = unmask_crtc(info->crtc);
+ sna_crtc_clear_vblank(info->crtc);
+ }
+
vblank_complete(info,
ust64(event->tv_sec, event->tv_usec),
- sna_crtc_record_event(unmask_crtc(crtc), event));
- if (has_vblank(crtc))
- sna_crtc_clear_vblank(unmask_crtc(crtc));
+ sna_crtc_record_event(info->crtc, event));
}
static int