aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/gpu/drm/amd/amdgpu/dce_v8_0.c81
1 files changed, 57 insertions, 24 deletions
diff --git a/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c b/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c
index aaa6561e9fc8..d7f88f33cd73 100644
--- a/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/dce_v8_0.c
@@ -2449,11 +2449,23 @@ static int dce_v8_0_cursor_move_locked(struct drm_crtc *crtc,
2449 return 0; 2449 return 0;
2450} 2450}
2451 2451
2452static void dce_v8_0_set_cursor(struct drm_crtc *crtc, struct drm_gem_object *obj, 2452static int dce_v8_0_set_cursor(struct drm_crtc *crtc, struct drm_gem_object *obj,
2453 uint64_t gpu_addr, int hot_x, int hot_y) 2453 int hot_x, int hot_y)
2454{ 2454{
2455 struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc); 2455 struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc);
2456 struct amdgpu_device *adev = crtc->dev->dev_private; 2456 struct amdgpu_device *adev = crtc->dev->dev_private;
2457 struct amdgpu_bo *aobj = gem_to_amdgpu_bo(obj);
2458 uint64_t gpu_addr;
2459 int ret;
2460
2461 ret = amdgpu_bo_reserve(aobj, false);
2462 if (unlikely(ret != 0))
2463 goto fail;
2464
2465 ret = amdgpu_bo_pin(aobj, AMDGPU_GEM_DOMAIN_VRAM, &gpu_addr);
2466 amdgpu_bo_unreserve(aobj);
2467 if (ret)
2468 goto fail;
2457 2469
2458 WREG32(mmCUR_SURFACE_ADDRESS_HIGH + amdgpu_crtc->crtc_offset, 2470 WREG32(mmCUR_SURFACE_ADDRESS_HIGH + amdgpu_crtc->crtc_offset,
2459 upper_32_bits(gpu_addr)); 2471 upper_32_bits(gpu_addr));
@@ -2472,6 +2484,13 @@ static void dce_v8_0_set_cursor(struct drm_crtc *crtc, struct drm_gem_object *ob
2472 amdgpu_crtc->cursor_hot_x = hot_x; 2484 amdgpu_crtc->cursor_hot_x = hot_x;
2473 amdgpu_crtc->cursor_hot_y = hot_y; 2485 amdgpu_crtc->cursor_hot_y = hot_y;
2474 } 2486 }
2487
2488 return 0;
2489
2490fail:
2491 drm_gem_object_unreference_unlocked(obj);
2492
2493 return ret;
2475} 2494}
2476 2495
2477static int dce_v8_0_crtc_cursor_move(struct drm_crtc *crtc, 2496static int dce_v8_0_crtc_cursor_move(struct drm_crtc *crtc,
@@ -2496,8 +2515,6 @@ static int dce_v8_0_crtc_cursor_set2(struct drm_crtc *crtc,
2496{ 2515{
2497 struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc); 2516 struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc);
2498 struct drm_gem_object *obj; 2517 struct drm_gem_object *obj;
2499 struct amdgpu_bo *robj;
2500 uint64_t gpu_addr;
2501 int ret; 2518 int ret;
2502 2519
2503 if (!handle) { 2520 if (!handle) {
@@ -2519,41 +2536,56 @@ static int dce_v8_0_crtc_cursor_set2(struct drm_crtc *crtc,
2519 return -ENOENT; 2536 return -ENOENT;
2520 } 2537 }
2521 2538
2522 robj = gem_to_amdgpu_bo(obj);
2523 ret = amdgpu_bo_reserve(robj, false);
2524 if (unlikely(ret != 0))
2525 goto fail;
2526 ret = amdgpu_bo_pin_restricted(robj, AMDGPU_GEM_DOMAIN_VRAM,
2527 0, 0, &gpu_addr);
2528 amdgpu_bo_unreserve(robj);
2529 if (ret)
2530 goto fail;
2531
2532 amdgpu_crtc->cursor_width = width; 2539 amdgpu_crtc->cursor_width = width;
2533 amdgpu_crtc->cursor_height = height; 2540 amdgpu_crtc->cursor_height = height;
2534 2541
2535 dce_v8_0_lock_cursor(crtc, true); 2542 dce_v8_0_lock_cursor(crtc, true);
2536 dce_v8_0_set_cursor(crtc, obj, gpu_addr, hot_x, hot_y); 2543 ret = dce_v8_0_set_cursor(crtc, obj, hot_x, hot_y);
2537 dce_v8_0_show_cursor(crtc); 2544 if (ret)
2545 DRM_ERROR("dce_v8_0_set_cursor returned %d, not changing cursor\n",
2546 ret);
2547 else
2548 dce_v8_0_show_cursor(crtc);
2538 dce_v8_0_lock_cursor(crtc, false); 2549 dce_v8_0_lock_cursor(crtc, false);
2539 2550
2540unpin: 2551unpin:
2541 if (amdgpu_crtc->cursor_bo) { 2552 if (amdgpu_crtc->cursor_bo) {
2542 robj = gem_to_amdgpu_bo(amdgpu_crtc->cursor_bo); 2553 struct amdgpu_bo *aobj = gem_to_amdgpu_bo(amdgpu_crtc->cursor_bo);
2543 ret = amdgpu_bo_reserve(robj, false); 2554 ret = amdgpu_bo_reserve(aobj, false);
2544 if (likely(ret == 0)) { 2555 if (likely(ret == 0)) {
2545 amdgpu_bo_unpin(robj); 2556 amdgpu_bo_unpin(aobj);
2546 amdgpu_bo_unreserve(robj); 2557 amdgpu_bo_unreserve(aobj);
2547 } 2558 }
2548 drm_gem_object_unreference_unlocked(amdgpu_crtc->cursor_bo); 2559 if (amdgpu_crtc->cursor_bo != obj)
2560 drm_gem_object_unreference_unlocked(amdgpu_crtc->cursor_bo);
2549 } 2561 }
2550 2562
2551 amdgpu_crtc->cursor_bo = obj; 2563 amdgpu_crtc->cursor_bo = obj;
2552 return 0; 2564 return 0;
2553fail: 2565}
2554 drm_gem_object_unreference_unlocked(obj);
2555 2566
2556 return ret; 2567static void dce_v8_0_cursor_reset(struct drm_crtc *crtc)
2568{
2569 struct amdgpu_crtc *amdgpu_crtc = to_amdgpu_crtc(crtc);
2570 int ret;
2571
2572 if (amdgpu_crtc->cursor_bo) {
2573 dce_v8_0_lock_cursor(crtc, true);
2574
2575 dce_v8_0_cursor_move_locked(crtc, amdgpu_crtc->cursor_x,
2576 amdgpu_crtc->cursor_y);
2577
2578 ret = dce_v8_0_set_cursor(crtc, amdgpu_crtc->cursor_bo,
2579 amdgpu_crtc->cursor_hot_x,
2580 amdgpu_crtc->cursor_hot_y);
2581 if (ret)
2582 DRM_ERROR("dce_v8_0_set_cursor returned %d, not showing "
2583 "cursor\n", ret);
2584 else
2585 dce_v8_0_show_cursor(crtc);
2586
2587 dce_v8_0_lock_cursor(crtc, false);
2588 }
2557} 2589}
2558 2590
2559static void dce_v8_0_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, 2591static void dce_v8_0_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green,
@@ -2721,6 +2753,7 @@ static int dce_v8_0_crtc_mode_set(struct drm_crtc *crtc,
2721 dce_v8_0_crtc_do_set_base(crtc, old_fb, x, y, 0); 2753 dce_v8_0_crtc_do_set_base(crtc, old_fb, x, y, 0);
2722 amdgpu_atombios_crtc_overscan_setup(crtc, mode, adjusted_mode); 2754 amdgpu_atombios_crtc_overscan_setup(crtc, mode, adjusted_mode);
2723 amdgpu_atombios_crtc_scaler_setup(crtc); 2755 amdgpu_atombios_crtc_scaler_setup(crtc);
2756 dce_v8_0_cursor_reset(crtc);
2724 /* update the hw version fpr dpm */ 2757 /* update the hw version fpr dpm */
2725 amdgpu_crtc->hw_mode = *adjusted_mode; 2758 amdgpu_crtc->hw_mode = *adjusted_mode;
2726 2759