summaryrefslogtreecommitdiff
path: root/drivers/gpu/drm/radeon/radeon_pm.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu/drm/radeon/radeon_pm.c')
-rw-r--r--drivers/gpu/drm/radeon/radeon_pm.c27
1 files changed, 27 insertions, 0 deletions
diff --git a/drivers/gpu/drm/radeon/radeon_pm.c b/drivers/gpu/drm/radeon/radeon_pm.c
index f0234351fd57..6dbfdf48a5f5 100644
--- a/drivers/gpu/drm/radeon/radeon_pm.c
+++ b/drivers/gpu/drm/radeon/radeon_pm.c
@@ -22,6 +22,7 @@
*/
#include "drmP.h"
#include "radeon.h"
+#include "avivod.h"
#define RADEON_IDLE_LOOP_MS 100
#define RADEON_RECLOCK_DELAY_MS 200
@@ -283,6 +284,28 @@ void radeon_pm_compute_clocks(struct radeon_device *rdev)
mutex_unlock(&rdev->pm.mutex);
}
+static bool radeon_pm_debug_check_in_vbl(struct radeon_device *rdev, bool finish)
+{
+ u32 stat_crtc1 = 0, stat_crtc2 = 0;
+ bool in_vbl = true;
+
+ if (ASIC_IS_AVIVO(rdev)) {
+ if (rdev->pm.active_crtcs & (1 << 0)) {
+ stat_crtc1 = RREG32(D1CRTC_STATUS);
+ if (!(stat_crtc1 & 1))
+ in_vbl = false;
+ }
+ if (rdev->pm.active_crtcs & (1 << 1)) {
+ stat_crtc2 = RREG32(D2CRTC_STATUS);
+ if (!(stat_crtc2 & 1))
+ in_vbl = false;
+ }
+ }
+ if (in_vbl == false)
+ DRM_INFO("not in vbl for pm change %08x %08x at %s\n", stat_crtc1,
+ stat_crtc2, finish ? "exit" : "entry");
+ return in_vbl;
+}
static void radeon_pm_set_clocks_locked(struct radeon_device *rdev)
{
/*radeon_fence_wait_last(rdev);*/
@@ -299,7 +322,11 @@ static void radeon_pm_set_clocks_locked(struct radeon_device *rdev)
DRM_ERROR("%s: PM_ACTION_NONE\n", __func__);
break;
}
+
+ /* check if we are in vblank */
+ radeon_pm_debug_check_in_vbl(rdev, false);
radeon_set_power_state(rdev);
+ radeon_pm_debug_check_in_vbl(rdev, true);
rdev->pm.planned_action = PM_ACTION_NONE;
}