aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/i915/intel_ringbuffer.c
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2017-05-04 09:08:44 -0400
committerChris Wilson <chris@chris-wilson.co.uk>2017-05-04 10:40:38 -0400
commit605d5b3297687cce9d3c4298c699188e61486a4c (patch)
tree843b54037b92d5477ae26f5c3d68b44c68a0aea1 /drivers/gpu/drm/i915/intel_ringbuffer.c
parent266a240bf0abf1e00e72e571f3724ec753a35f19 (diff)
drm/i915: Avoid the branch in computing intel_ring_space()
Exploit the power-of-two ring size to compute the space across the wraparound using a mask rather than a if. Convert to unsigned integers so the operation is well defined. References: https://bugs.freedesktop.org/show_bug.cgi?id=99671 Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk> Cc: Mika Kuoppala <mika.kuoppala@intel.com> Reviewed-by: Mika Kuoppala <mika.kuoppala@intel.com> Link: http://patchwork.freedesktop.org/patch/msgid/20170504130846.4807-1-chris@chris-wilson.co.uk
Diffstat (limited to 'drivers/gpu/drm/i915/intel_ringbuffer.c')
-rw-r--r--drivers/gpu/drm/i915/intel_ringbuffer.c24
1 files changed, 13 insertions, 11 deletions
diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c
index 3ce1c87dec46..46f2696bf886 100644
--- a/drivers/gpu/drm/i915/intel_ringbuffer.c
+++ b/drivers/gpu/drm/i915/intel_ringbuffer.c
@@ -39,12 +39,17 @@
39 */ 39 */
40#define LEGACY_REQUEST_SIZE 200 40#define LEGACY_REQUEST_SIZE 200
41 41
42static int __intel_ring_space(int head, int tail, int size) 42static unsigned int __intel_ring_space(unsigned int head,
43 unsigned int tail,
44 unsigned int size)
43{ 45{
44 int space = head - tail; 46 /*
45 if (space <= 0) 47 * "If the Ring Buffer Head Pointer and the Tail Pointer are on the
46 space += size; 48 * same cacheline, the Head Pointer must not be greater than the Tail
47 return space - I915_RING_FREE_SPACE; 49 * Pointer."
50 */
51 GEM_BUG_ON(!is_power_of_2(size));
52 return (head - tail - CACHELINE_BYTES) & (size - 1);
48} 53}
49 54
50void intel_ring_update_space(struct intel_ring *ring) 55void intel_ring_update_space(struct intel_ring *ring)
@@ -1670,12 +1675,9 @@ static int wait_for_space(struct drm_i915_gem_request *req, int bytes)
1670 GEM_BUG_ON(!req->reserved_space); 1675 GEM_BUG_ON(!req->reserved_space);
1671 1676
1672 list_for_each_entry(target, &ring->request_list, ring_link) { 1677 list_for_each_entry(target, &ring->request_list, ring_link) {
1673 unsigned space;
1674
1675 /* Would completion of this request free enough space? */ 1678 /* Would completion of this request free enough space? */
1676 space = __intel_ring_space(target->postfix, ring->emit, 1679 if (bytes <= __intel_ring_space(target->postfix,
1677 ring->size); 1680 ring->emit, ring->size))
1678 if (space >= bytes)
1679 break; 1681 break;
1680 } 1682 }
1681 1683
@@ -1744,11 +1746,11 @@ u32 *intel_ring_begin(struct drm_i915_gem_request *req, int num_dwords)
1744 } 1746 }
1745 1747
1746 GEM_BUG_ON(ring->emit > ring->size - bytes); 1748 GEM_BUG_ON(ring->emit > ring->size - bytes);
1749 GEM_BUG_ON(ring->space < bytes);
1747 cs = ring->vaddr + ring->emit; 1750 cs = ring->vaddr + ring->emit;
1748 GEM_DEBUG_EXEC(memset(cs, POISON_INUSE, bytes)); 1751 GEM_DEBUG_EXEC(memset(cs, POISON_INUSE, bytes));
1749 ring->emit += bytes; 1752 ring->emit += bytes;
1750 ring->space -= bytes; 1753 ring->space -= bytes;
1751 GEM_BUG_ON(ring->space < 0);
1752 1754
1753 return cs; 1755 return cs;
1754} 1756}