Message ID | 1473872835-11882-1-git-send-email-imre.deak@intel.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Op 14-09-16 om 19:07 schreef Imre Deak: > While user space has control over the scheduling priority of its page > flipping thread, the corresponding work the driver schedules for MMIO > flips always runs from the generic system workqueue which has some > scheduling overhead due it being CPU bound. This would hinder an > application that wants more stringent guarantees over flip timing (to > avoid missing a flip at the next frame count). > > Fix this by scheduling the work from a dedicated, unbound workqueue > which provides for minimal scheduling latency. I think it should use the same wq as intel_atomic_commit, either page flip should use system_unbound_wq, or atomic_commit should use this one. ~Maarten
On Thu, 2016-09-15 at 10:44 +0200, Maarten Lankhorst wrote: > Op 14-09-16 om 19:07 schreef Imre Deak: > > While user space has control over the scheduling priority of its > > page > > flipping thread, the corresponding work the driver schedules for > > MMIO > > flips always runs from the generic system workqueue which has some > > scheduling overhead due it being CPU bound. This would hinder an > > application that wants more stringent guarantees over flip timing > > (to > > avoid missing a flip at the next frame count). > > > > Fix this by scheduling the work from a dedicated, unbound workqueue > > which provides for minimal scheduling latency. > I think it should use the same wq as intel_atomic_commit, either page > flip should use > system_unbound_wq, or atomic_commit should use this one. Hm, I didn't notice system_unbound_wq, and I suppose there is no advantage (smaller latency) in using a dedicated wq. So I can change this to use system_unbound_wq. --Imre
diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 7f4e8ad..b5445a1 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -755,8 +755,14 @@ static int i915_workqueues_init(struct drm_i915_private *dev_priv) if (dev_priv->hotplug.dp_wq == NULL) goto out_free_wq; + dev_priv->flip_wq = alloc_workqueue("i915-flip", WQ_UNBOUND, 0); + if (dev_priv->flip_wq == NULL) + goto out_free_dp_wq; + return 0; +out_free_dp_wq: + destroy_workqueue(dev_priv->hotplug.dp_wq); out_free_wq: destroy_workqueue(dev_priv->wq); out_err: @@ -767,6 +773,7 @@ out_err: static void i915_workqueues_cleanup(struct drm_i915_private *dev_priv) { + destroy_workqueue(dev_priv->flip_wq); destroy_workqueue(dev_priv->hotplug.dp_wq); destroy_workqueue(dev_priv->wq); } diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index d60ade9..cdd835b 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -1859,6 +1859,10 @@ struct drm_i915_private { * result in deadlocks. */ struct workqueue_struct *wq; + /** + * flip_wq - Low latency, unordered flip workqueue. + */ + struct workqueue_struct *flip_wq; /* Display functions */ struct drm_i915_display_funcs display; diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 7bb7874..7728c18 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -12266,7 +12266,7 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc, work->flip_queued_req = i915_gem_active_get(&obj->last_write, &obj->base.dev->struct_mutex); - schedule_work(&work->mmio_work); + queue_work(dev_priv->flip_wq, &work->mmio_work); } else { request = i915_gem_request_alloc(engine, engine->last_context); if (IS_ERR(request)) {