Commit a6910434 authored by Daniel Vetter's avatar Daniel Vetter Committed by Chris Wilson

drm/i915: only one interrupt per batchbuffer is not enough!

Previously I thought that one interrupt per batchbuffer should be
enough. Now tedious benchmarking showed this to be wrong.

Therefore track whether any commands have been isssued with a future
seqno (like pipelined fencing changes or flushes). If this is the case
emit a request before issueing the batchbuffer.
Signed-off-by: default avatarDaniel Vetter <daniel.vetter@ffwll.ch>
Signed-off-by: default avatarChris Wilson <chris@chris-wilson.co.uk>
parent 8bff917c
...@@ -293,9 +293,6 @@ typedef struct drm_i915_private { ...@@ -293,9 +293,6 @@ typedef struct drm_i915_private {
unsigned int sr01, adpa, ppcr, dvob, dvoc, lvds; unsigned int sr01, adpa, ppcr, dvob, dvoc, lvds;
int vblank_pipe; int vblank_pipe;
int num_pipe; int num_pipe;
u32 flush_rings;
#define FLUSH_RENDER_RING 0x1
#define FLUSH_BSD_RING 0x2
/* For hangcheck timer */ /* For hangcheck timer */
#define DRM_I915_HANGCHECK_PERIOD 75 /* in jiffies */ #define DRM_I915_HANGCHECK_PERIOD 75 /* in jiffies */
......
...@@ -1470,10 +1470,13 @@ i915_gem_object_put_pages(struct drm_gem_object *obj) ...@@ -1470,10 +1470,13 @@ i915_gem_object_put_pages(struct drm_gem_object *obj)
} }
static uint32_t static uint32_t
i915_gem_next_request_seqno(struct drm_device *dev) i915_gem_next_request_seqno(struct drm_device *dev,
struct intel_ring_buffer *ring)
{ {
drm_i915_private_t *dev_priv = dev->dev_private; drm_i915_private_t *dev_priv = dev->dev_private;
ring->outstanding_lazy_request = true;
return dev_priv->next_seqno; return dev_priv->next_seqno;
} }
...@@ -1495,7 +1498,7 @@ i915_gem_object_move_to_active(struct drm_gem_object *obj, uint32_t seqno, ...@@ -1495,7 +1498,7 @@ i915_gem_object_move_to_active(struct drm_gem_object *obj, uint32_t seqno,
/* Take the seqno of the next request if none is given */ /* Take the seqno of the next request if none is given */
if (seqno == 0) if (seqno == 0)
seqno = i915_gem_next_request_seqno(dev); seqno = i915_gem_next_request_seqno(dev, ring);
/* Move from whatever list we were on to the tail of execution. */ /* Move from whatever list we were on to the tail of execution. */
spin_lock(&dev_priv->mm.active_list_lock); spin_lock(&dev_priv->mm.active_list_lock);
...@@ -2979,7 +2982,6 @@ static void ...@@ -2979,7 +2982,6 @@ static void
i915_gem_object_set_to_gpu_domain(struct drm_gem_object *obj) i915_gem_object_set_to_gpu_domain(struct drm_gem_object *obj)
{ {
struct drm_device *dev = obj->dev; struct drm_device *dev = obj->dev;
drm_i915_private_t *dev_priv = dev->dev_private;
struct drm_i915_gem_object *obj_priv = to_intel_bo(obj); struct drm_i915_gem_object *obj_priv = to_intel_bo(obj);
uint32_t invalidate_domains = 0; uint32_t invalidate_domains = 0;
uint32_t flush_domains = 0; uint32_t flush_domains = 0;
...@@ -3042,13 +3044,6 @@ i915_gem_object_set_to_gpu_domain(struct drm_gem_object *obj) ...@@ -3042,13 +3044,6 @@ i915_gem_object_set_to_gpu_domain(struct drm_gem_object *obj)
obj->pending_write_domain = obj->write_domain; obj->pending_write_domain = obj->write_domain;
obj->read_domains = obj->pending_read_domains; obj->read_domains = obj->pending_read_domains;
if (flush_domains & I915_GEM_GPU_DOMAINS) {
if (obj_priv->ring == &dev_priv->render_ring)
dev_priv->flush_rings |= FLUSH_RENDER_RING;
else if (obj_priv->ring == &dev_priv->bsd_ring)
dev_priv->flush_rings |= FLUSH_BSD_RING;
}
dev->invalidate_domains |= invalidate_domains; dev->invalidate_domains |= invalidate_domains;
dev->flush_domains |= flush_domains; dev->flush_domains |= flush_domains;
#if WATCH_BUF #if WATCH_BUF
...@@ -3762,7 +3757,6 @@ i915_gem_do_execbuffer(struct drm_device *dev, void *data, ...@@ -3762,7 +3757,6 @@ i915_gem_do_execbuffer(struct drm_device *dev, void *data,
*/ */
dev->invalidate_domains = 0; dev->invalidate_domains = 0;
dev->flush_domains = 0; dev->flush_domains = 0;
dev_priv->flush_rings = 0;
for (i = 0; i < args->buffer_count; i++) { for (i = 0; i < args->buffer_count; i++) {
struct drm_gem_object *obj = object_list[i]; struct drm_gem_object *obj = object_list[i];
...@@ -3783,12 +3777,17 @@ i915_gem_do_execbuffer(struct drm_device *dev, void *data, ...@@ -3783,12 +3777,17 @@ i915_gem_do_execbuffer(struct drm_device *dev, void *data,
i915_gem_flush(dev, i915_gem_flush(dev,
dev->invalidate_domains, dev->invalidate_domains,
dev->flush_domains); dev->flush_domains);
if (dev_priv->flush_rings & FLUSH_RENDER_RING) }
if (dev_priv->render_ring.outstanding_lazy_request) {
(void)i915_add_request(dev, file_priv, 0, (void)i915_add_request(dev, file_priv, 0,
&dev_priv->render_ring); &dev_priv->render_ring);
if (dev_priv->flush_rings & FLUSH_BSD_RING) dev_priv->render_ring.outstanding_lazy_request = false;
}
if (dev_priv->bsd_ring.outstanding_lazy_request) {
(void)i915_add_request(dev, file_priv, 0, (void)i915_add_request(dev, file_priv, 0,
&dev_priv->bsd_ring); &dev_priv->bsd_ring);
dev_priv->bsd_ring.outstanding_lazy_request = false;
} }
for (i = 0; i < args->buffer_count; i++) { for (i = 0; i < args->buffer_count; i++) {
......
...@@ -83,6 +83,11 @@ struct intel_ring_buffer { ...@@ -83,6 +83,11 @@ struct intel_ring_buffer {
*/ */
struct list_head request_list; struct list_head request_list;
/**
* Do we have some not yet emitted requests outstanding?
*/
bool outstanding_lazy_request;
wait_queue_head_t irq_queue; wait_queue_head_t irq_queue;
drm_local_map_t map; drm_local_map_t map;
}; };
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment