diff options
author | Chris Wilson <chris@chris-wilson.co.uk> | 2012-04-17 10:31:33 -0400 |
---|---|---|
committer | Daniel Vetter <daniel.vetter@ffwll.ch> | 2012-04-18 07:40:51 -0400 |
commit | 14415745b2518fc7309616a33ce8e656e79a4e05 (patch) | |
tree | 61d9026f557823e6db7a3b1b70ea935516c2317c /drivers/gpu/drm | |
parent | ada726c734e79c83f72676c02b5d68d4f9faead0 (diff) |
drm/i915: Refactor get_fence() to use the common fence writing routine
We can also take advantage of the new 'no retire' mode for seqno waiting
to avoid having to take a reference on the old fence object whilst
flushing an existing fence.
Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Diffstat (limited to 'drivers/gpu/drm')
-rw-r--r-- | drivers/gpu/drm/i915/i915_gem.c | 70 |
1 files changed, 27 insertions, 43 deletions
diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index e09ac3a95308..7bc4a40132ad 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c | |||
@@ -2361,7 +2361,7 @@ i915_gem_object_flush_fence(struct drm_i915_gem_object *obj) | |||
2361 | if (obj->last_fenced_seqno) { | 2361 | if (obj->last_fenced_seqno) { |
2362 | ret = i915_wait_request(obj->ring, | 2362 | ret = i915_wait_request(obj->ring, |
2363 | obj->last_fenced_seqno, | 2363 | obj->last_fenced_seqno, |
2364 | true); | 2364 | false); |
2365 | if (ret) | 2365 | if (ret) |
2366 | return ret; | 2366 | return ret; |
2367 | 2367 | ||
@@ -2449,63 +2449,47 @@ i915_gem_object_get_fence(struct drm_i915_gem_object *obj) | |||
2449 | { | 2449 | { |
2450 | struct drm_device *dev = obj->base.dev; | 2450 | struct drm_device *dev = obj->base.dev; |
2451 | struct drm_i915_private *dev_priv = dev->dev_private; | 2451 | struct drm_i915_private *dev_priv = dev->dev_private; |
2452 | bool enable = obj->tiling_mode != I915_TILING_NONE; | ||
2452 | struct drm_i915_fence_reg *reg; | 2453 | struct drm_i915_fence_reg *reg; |
2453 | int ret; | 2454 | int ret; |
2454 | 2455 | ||
2455 | if (obj->tiling_mode == I915_TILING_NONE) | 2456 | /* Have we updated the tiling parameters upon the object and so |
2456 | return i915_gem_object_put_fence(obj); | 2457 | * will need to serialise the write to the associated fence register? |
2458 | */ | ||
2459 | if (obj->tiling_changed) { | ||
2460 | ret = i915_gem_object_flush_fence(obj); | ||
2461 | if (ret) | ||
2462 | return ret; | ||
2463 | } | ||
2457 | 2464 | ||
2458 | /* Just update our place in the LRU if our fence is getting reused. */ | 2465 | /* Just update our place in the LRU if our fence is getting reused. */ |
2459 | if (obj->fence_reg != I915_FENCE_REG_NONE) { | 2466 | if (obj->fence_reg != I915_FENCE_REG_NONE) { |
2460 | reg = &dev_priv->fence_regs[obj->fence_reg]; | 2467 | reg = &dev_priv->fence_regs[obj->fence_reg]; |
2461 | list_move_tail(®->lru_list, &dev_priv->mm.fence_list); | 2468 | if (!obj->tiling_changed) { |
2469 | list_move_tail(®->lru_list, | ||
2470 | &dev_priv->mm.fence_list); | ||
2471 | return 0; | ||
2472 | } | ||
2473 | } else if (enable) { | ||
2474 | reg = i915_find_fence_reg(dev); | ||
2475 | if (reg == NULL) | ||
2476 | return -EDEADLK; | ||
2477 | |||
2478 | if (reg->obj) { | ||
2479 | struct drm_i915_gem_object *old = reg->obj; | ||
2462 | 2480 | ||
2463 | if (obj->tiling_changed) { | 2481 | ret = i915_gem_object_flush_fence(old); |
2464 | ret = i915_gem_object_flush_fence(obj); | ||
2465 | if (ret) | 2482 | if (ret) |
2466 | return ret; | 2483 | return ret; |
2467 | 2484 | ||
2468 | goto update; | 2485 | i915_gem_object_fence_lost(old); |
2469 | } | 2486 | } |
2470 | 2487 | } else | |
2471 | return 0; | 2488 | return 0; |
2472 | } | ||
2473 | |||
2474 | reg = i915_find_fence_reg(dev); | ||
2475 | if (reg == NULL) | ||
2476 | return -EDEADLK; | ||
2477 | |||
2478 | ret = i915_gem_object_flush_fence(obj); | ||
2479 | if (ret) | ||
2480 | return ret; | ||
2481 | |||
2482 | if (reg->obj) { | ||
2483 | struct drm_i915_gem_object *old = reg->obj; | ||
2484 | 2489 | ||
2485 | drm_gem_object_reference(&old->base); | 2490 | i915_gem_object_update_fence(obj, reg, enable); |
2486 | |||
2487 | if (old->tiling_mode) | ||
2488 | i915_gem_release_mmap(old); | ||
2489 | |||
2490 | ret = i915_gem_object_flush_fence(old); | ||
2491 | if (ret) { | ||
2492 | drm_gem_object_unreference(&old->base); | ||
2493 | return ret; | ||
2494 | } | ||
2495 | |||
2496 | old->fence_reg = I915_FENCE_REG_NONE; | ||
2497 | old->last_fenced_seqno = 0; | ||
2498 | |||
2499 | drm_gem_object_unreference(&old->base); | ||
2500 | } | ||
2501 | |||
2502 | reg->obj = obj; | ||
2503 | list_move_tail(®->lru_list, &dev_priv->mm.fence_list); | ||
2504 | obj->fence_reg = reg - dev_priv->fence_regs; | ||
2505 | |||
2506 | update: | ||
2507 | obj->tiling_changed = false; | 2491 | obj->tiling_changed = false; |
2508 | i915_gem_write_fence(dev, reg - dev_priv->fence_regs, obj); | 2492 | |
2509 | return 0; | 2493 | return 0; |
2510 | } | 2494 | } |
2511 | 2495 | ||