drm/radeon/kms/pm: add a proper pm profile init function for fusion
[pandora-kernel.git] / drivers / gpu / drm / radeon / evergreen.c
index c4ffa14..1d603a3 100644 (file)
@@ -39,7 +39,7 @@
 
 static void evergreen_gpu_init(struct radeon_device *rdev);
 void evergreen_fini(struct radeon_device *rdev);
-static void evergreen_pcie_gen2_enable(struct radeon_device *rdev);
+void evergreen_pcie_gen2_enable(struct radeon_device *rdev);
 
 void evergreen_fix_pci_max_read_req_size(struct radeon_device *rdev)
 {
@@ -157,6 +157,57 @@ int sumo_get_temp(struct radeon_device *rdev)
        return actual_temp * 1000;
 }
 
+void sumo_pm_init_profile(struct radeon_device *rdev)
+{
+       int idx;
+
+       /* default */
+       rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_off_ps_idx = rdev->pm.default_power_state_index;
+       rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_on_ps_idx = rdev->pm.default_power_state_index;
+       rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_off_cm_idx = 0;
+       rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_on_cm_idx = 0;
+
+       /* low,mid sh/mh */
+       if (rdev->flags & RADEON_IS_MOBILITY)
+               idx = radeon_pm_get_type_index(rdev, POWER_STATE_TYPE_BATTERY, 0);
+       else
+               idx = radeon_pm_get_type_index(rdev, POWER_STATE_TYPE_PERFORMANCE, 0);
+
+       rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_off_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_on_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_off_cm_idx = 0;
+       rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_on_cm_idx = 0;
+
+       rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_off_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_on_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_off_cm_idx = 0;
+       rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_on_cm_idx = 0;
+
+       rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_off_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_on_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_off_cm_idx = 0;
+       rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_on_cm_idx = 0;
+
+       rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_off_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_on_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_off_cm_idx = 0;
+       rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_on_cm_idx = 0;
+
+       /* high sh/mh */
+       idx = radeon_pm_get_type_index(rdev, POWER_STATE_TYPE_PERFORMANCE, 0);
+       rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_off_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_on_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_off_cm_idx = 0;
+       rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_on_cm_idx =
+               rdev->pm.power_state[idx].num_clock_modes - 1;
+
+       rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_off_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_on_ps_idx = idx;
+       rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_off_cm_idx = 0;
+       rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_on_cm_idx =
+               rdev->pm.power_state[idx].num_clock_modes - 1;
+}
+
 void evergreen_pm_misc(struct radeon_device *rdev)
 {
        int req_ps_idx = rdev->pm.requested_power_state_index;
@@ -353,6 +404,7 @@ void evergreen_hpd_init(struct radeon_device *rdev)
                default:
                        break;
                }
+               radeon_hpd_set_polarity(rdev, radeon_connector->hpd.hpd);
        }
        if (rdev->irq.installed)
                evergreen_irq_set(rdev);
@@ -893,7 +945,7 @@ int evergreen_pcie_gart_enable(struct radeon_device *rdev)
        u32 tmp;
        int r;
 
-       if (rdev->gart.table.vram.robj == NULL) {
+       if (rdev->gart.robj == NULL) {
                dev_err(rdev->dev, "No VRAM object for PCIE GART.\n");
                return -EINVAL;
        }
@@ -935,6 +987,9 @@ int evergreen_pcie_gart_enable(struct radeon_device *rdev)
        WREG32(VM_CONTEXT1_CNTL, 0);
 
        evergreen_pcie_gart_tlb_flush(rdev);
+       DRM_INFO("PCIE GART of %uM enabled (table at 0x%016llX).\n",
+                (unsigned)(rdev->mc.gtt_size >> 20),
+                (unsigned long long)rdev->gart.table_addr);
        rdev->gart.ready = true;
        return 0;
 }
@@ -942,7 +997,6 @@ int evergreen_pcie_gart_enable(struct radeon_device *rdev)
 void evergreen_pcie_gart_disable(struct radeon_device *rdev)
 {
        u32 tmp;
-       int r;
 
        /* Disable all tables */
        WREG32(VM_CONTEXT0_CNTL, 0);
@@ -962,14 +1016,7 @@ void evergreen_pcie_gart_disable(struct radeon_device *rdev)
        WREG32(MC_VM_MB_L1_TLB1_CNTL, tmp);
        WREG32(MC_VM_MB_L1_TLB2_CNTL, tmp);
        WREG32(MC_VM_MB_L1_TLB3_CNTL, tmp);
-       if (rdev->gart.table.vram.robj) {
-               r = radeon_bo_reserve(rdev->gart.table.vram.robj, false);
-               if (likely(r == 0)) {
-                       radeon_bo_kunmap(rdev->gart.table.vram.robj);
-                       radeon_bo_unpin(rdev->gart.table.vram.robj);
-                       radeon_bo_unreserve(rdev->gart.table.vram.robj);
-               }
-       }
+       radeon_gart_table_vram_unpin(rdev);
 }
 
 void evergreen_pcie_gart_fini(struct radeon_device *rdev)
@@ -1223,7 +1270,7 @@ void evergreen_mc_program(struct radeon_device *rdev)
                WREG32(MC_VM_SYSTEM_APERTURE_HIGH_ADDR,
                        rdev->mc.vram_end >> 12);
        }
-       WREG32(MC_VM_SYSTEM_APERTURE_DEFAULT_ADDR, 0);
+       WREG32(MC_VM_SYSTEM_APERTURE_DEFAULT_ADDR, rdev->vram_scratch.gpu_addr >> 12);
        if (rdev->flags & RADEON_IS_IGP) {
                tmp = RREG32(MC_FUS_VM_FB_OFFSET) & 0x000FFFFF;
                tmp |= ((rdev->mc.vram_end >> 20) & 0xF) << 24;
@@ -2586,7 +2633,7 @@ int evergreen_irq_set(struct radeon_device *rdev)
        return 0;
 }
 
-static inline void evergreen_irq_ack(struct radeon_device *rdev)
+static void evergreen_irq_ack(struct radeon_device *rdev)
 {
        u32 tmp;
 
@@ -2697,7 +2744,7 @@ void evergreen_irq_suspend(struct radeon_device *rdev)
        r600_rlc_stop(rdev);
 }
 
-static inline u32 evergreen_get_ih_wptr(struct radeon_device *rdev)
+static u32 evergreen_get_ih_wptr(struct radeon_device *rdev)
 {
        u32 wptr, tmp;
 
@@ -3003,8 +3050,7 @@ static int evergreen_startup(struct radeon_device *rdev)
        int r;
 
        /* enable pcie gen2 link */
-       if (!ASIC_IS_DCE5(rdev))
-               evergreen_pcie_gen2_enable(rdev);
+       evergreen_pcie_gen2_enable(rdev);
 
        if (ASIC_IS_DCE5(rdev)) {
                if (!rdev->me_fw || !rdev->pfp_fw || !rdev->rlc_fw || !rdev->mc_fw) {
@@ -3029,6 +3075,10 @@ static int evergreen_startup(struct radeon_device *rdev)
                }
        }
 
+       r = r600_vram_scratch_init(rdev);
+       if (r)
+               return r;
+
        evergreen_mc_program(rdev);
        if (rdev->flags & RADEON_IS_AGP) {
                evergreen_agp_enable(rdev);
@@ -3041,7 +3091,7 @@ static int evergreen_startup(struct radeon_device *rdev)
 
        r = evergreen_blit_init(rdev);
        if (r) {
-               evergreen_blit_fini(rdev);
+               r600_blit_fini(rdev);
                rdev->asic->copy = NULL;
                dev_warn(rdev->dev, "failed blitter (%d) falling back to memcpy\n", r);
        }
@@ -3107,45 +3157,14 @@ int evergreen_resume(struct radeon_device *rdev)
 
 int evergreen_suspend(struct radeon_device *rdev)
 {
-       int r;
-
        /* FIXME: we should wait for ring to be empty */
        r700_cp_stop(rdev);
        rdev->cp.ready = false;
        evergreen_irq_suspend(rdev);
        radeon_wb_disable(rdev);
        evergreen_pcie_gart_disable(rdev);
+       r600_blit_suspend(rdev);
 
-       /* unpin shaders bo */
-       r = radeon_bo_reserve(rdev->r600_blit.shader_obj, false);
-       if (likely(r == 0)) {
-               radeon_bo_unpin(rdev->r600_blit.shader_obj);
-               radeon_bo_unreserve(rdev->r600_blit.shader_obj);
-       }
-
-       return 0;
-}
-
-int evergreen_copy_blit(struct radeon_device *rdev,
-                       uint64_t src_offset,
-                       uint64_t dst_offset,
-                       unsigned num_gpu_pages,
-                       struct radeon_fence *fence)
-{
-       int r;
-
-       mutex_lock(&rdev->r600_blit.mutex);
-       rdev->r600_blit.vb_ib = NULL;
-       r = evergreen_blit_prepare_copy(rdev, num_gpu_pages * RADEON_GPU_PAGE_SIZE);
-       if (r) {
-               if (rdev->r600_blit.vb_ib)
-                       radeon_ib_free(rdev, &rdev->r600_blit.vb_ib);
-               mutex_unlock(&rdev->r600_blit.mutex);
-               return r;
-       }
-       evergreen_kms_blit_copy(rdev, src_offset, dst_offset, num_gpu_pages * RADEON_GPU_PAGE_SIZE);
-       evergreen_blit_done_copy(rdev, fence);
-       mutex_unlock(&rdev->r600_blit.mutex);
        return 0;
 }
 
@@ -3257,13 +3276,14 @@ int evergreen_init(struct radeon_device *rdev)
 
 void evergreen_fini(struct radeon_device *rdev)
 {
-       evergreen_blit_fini(rdev);
+       r600_blit_fini(rdev);
        r700_cp_fini(rdev);
        r600_irq_fini(rdev);
        radeon_wb_fini(rdev);
        radeon_ib_pool_fini(rdev);
        radeon_irq_kms_fini(rdev);
        evergreen_pcie_gart_fini(rdev);
+       r600_vram_scratch_fini(rdev);
        radeon_gem_fini(rdev);
        radeon_fence_driver_fini(rdev);
        radeon_agp_fini(rdev);
@@ -3273,7 +3293,7 @@ void evergreen_fini(struct radeon_device *rdev)
        rdev->bios = NULL;
 }
 
-static void evergreen_pcie_gen2_enable(struct radeon_device *rdev)
+void evergreen_pcie_gen2_enable(struct radeon_device *rdev)
 {
        u32 link_width_cntl, speed_cntl;