aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/radeon/r600.c
diff options
context:
space:
mode:
authorAlex Deucher <alexander.deucher@amd.com>2013-06-26 00:11:19 -0400
committerAlex Deucher <alexander.deucher@amd.com>2013-06-27 19:14:59 -0400
commit66229b200598a3b66b839d1759ff3f5b17ac5639 (patch)
tree5bfb3d7ba630171afe67c9aeae007a1db03d22d3 /drivers/gpu/drm/radeon/r600.c
parent4a6369e9935e392402d4ccb67f5cddac953e8d3c (diff)
drm/radeon/kms: add dpm support for rv7xx (v4)
This adds dpm support for rv7xx asics. This includes: - clockgating - dynamic engine clock scaling - dynamic memory clock scaling - dynamic voltage scaling - dynamic pcie gen1/gen2 switching Set radeon.dpm=1 to enable. v2: reduce stack usage v3: fix 64 bit div v4: fix state enable Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
Diffstat (limited to 'drivers/gpu/drm/radeon/r600.c')
-rw-r--r--drivers/gpu/drm/radeon/r600.c48
1 files changed, 42 insertions, 6 deletions
diff --git a/drivers/gpu/drm/radeon/r600.c b/drivers/gpu/drm/radeon/r600.c
index ce5aa1febb80..a27d746386ae 100644
--- a/drivers/gpu/drm/radeon/r600.c
+++ b/drivers/gpu/drm/radeon/r600.c
@@ -57,10 +57,14 @@ MODULE_FIRMWARE("radeon/RS780_pfp.bin");
57MODULE_FIRMWARE("radeon/RS780_me.bin"); 57MODULE_FIRMWARE("radeon/RS780_me.bin");
58MODULE_FIRMWARE("radeon/RV770_pfp.bin"); 58MODULE_FIRMWARE("radeon/RV770_pfp.bin");
59MODULE_FIRMWARE("radeon/RV770_me.bin"); 59MODULE_FIRMWARE("radeon/RV770_me.bin");
60MODULE_FIRMWARE("radeon/RV770_smc.bin");
60MODULE_FIRMWARE("radeon/RV730_pfp.bin"); 61MODULE_FIRMWARE("radeon/RV730_pfp.bin");
61MODULE_FIRMWARE("radeon/RV730_me.bin"); 62MODULE_FIRMWARE("radeon/RV730_me.bin");
63MODULE_FIRMWARE("radeon/RV730_smc.bin");
64MODULE_FIRMWARE("radeon/RV740_smc.bin");
62MODULE_FIRMWARE("radeon/RV710_pfp.bin"); 65MODULE_FIRMWARE("radeon/RV710_pfp.bin");
63MODULE_FIRMWARE("radeon/RV710_me.bin"); 66MODULE_FIRMWARE("radeon/RV710_me.bin");
67MODULE_FIRMWARE("radeon/RV710_smc.bin");
64MODULE_FIRMWARE("radeon/R600_rlc.bin"); 68MODULE_FIRMWARE("radeon/R600_rlc.bin");
65MODULE_FIRMWARE("radeon/R700_rlc.bin"); 69MODULE_FIRMWARE("radeon/R700_rlc.bin");
66MODULE_FIRMWARE("radeon/CEDAR_pfp.bin"); 70MODULE_FIRMWARE("radeon/CEDAR_pfp.bin");
@@ -2139,7 +2143,8 @@ int r600_init_microcode(struct radeon_device *rdev)
2139 struct platform_device *pdev; 2143 struct platform_device *pdev;
2140 const char *chip_name; 2144 const char *chip_name;
2141 const char *rlc_chip_name; 2145 const char *rlc_chip_name;
2142 size_t pfp_req_size, me_req_size, rlc_req_size; 2146 const char *smc_chip_name = "RV770";
2147 size_t pfp_req_size, me_req_size, rlc_req_size, smc_req_size = 0;
2143 char fw_name[30]; 2148 char fw_name[30];
2144 int err; 2149 int err;
2145 2150
@@ -2185,15 +2190,26 @@ int r600_init_microcode(struct radeon_device *rdev)
2185 case CHIP_RV770: 2190 case CHIP_RV770:
2186 chip_name = "RV770"; 2191 chip_name = "RV770";
2187 rlc_chip_name = "R700"; 2192 rlc_chip_name = "R700";
2193 smc_chip_name = "RV770";
2194 smc_req_size = ALIGN(RV770_SMC_UCODE_SIZE, 4);
2188 break; 2195 break;
2189 case CHIP_RV730: 2196 case CHIP_RV730:
2190 case CHIP_RV740:
2191 chip_name = "RV730"; 2197 chip_name = "RV730";
2192 rlc_chip_name = "R700"; 2198 rlc_chip_name = "R700";
2199 smc_chip_name = "RV730";
2200 smc_req_size = ALIGN(RV730_SMC_UCODE_SIZE, 4);
2193 break; 2201 break;
2194 case CHIP_RV710: 2202 case CHIP_RV710:
2195 chip_name = "RV710"; 2203 chip_name = "RV710";
2196 rlc_chip_name = "R700"; 2204 rlc_chip_name = "R700";
2205 smc_chip_name = "RV710";
2206 smc_req_size = ALIGN(RV710_SMC_UCODE_SIZE, 4);
2207 break;
2208 case CHIP_RV740:
2209 chip_name = "RV730";
2210 rlc_chip_name = "R700";
2211 smc_chip_name = "RV740";
2212 smc_req_size = ALIGN(RV740_SMC_UCODE_SIZE, 4);
2197 break; 2213 break;
2198 case CHIP_CEDAR: 2214 case CHIP_CEDAR:
2199 chip_name = "CEDAR"; 2215 chip_name = "CEDAR";
@@ -2277,6 +2293,19 @@ int r600_init_microcode(struct radeon_device *rdev)
2277 err = -EINVAL; 2293 err = -EINVAL;
2278 } 2294 }
2279 2295
2296 if ((rdev->family >= CHIP_RV770) && (rdev->family <= CHIP_RV740)) {
2297 snprintf(fw_name, sizeof(fw_name), "radeon/%s_smc.bin", smc_chip_name);
2298 err = request_firmware(&rdev->smc_fw, fw_name, &pdev->dev);
2299 if (err)
2300 goto out;
2301 if (rdev->smc_fw->size != smc_req_size) {
2302 printk(KERN_ERR
2303 "smc: Bogus length %zu in firmware \"%s\"\n",
2304 rdev->smc_fw->size, fw_name);
2305 err = -EINVAL;
2306 }
2307 }
2308
2280out: 2309out:
2281 platform_device_unregister(pdev); 2310 platform_device_unregister(pdev);
2282 2311
@@ -2291,6 +2320,8 @@ out:
2291 rdev->me_fw = NULL; 2320 rdev->me_fw = NULL;
2292 release_firmware(rdev->rlc_fw); 2321 release_firmware(rdev->rlc_fw);
2293 rdev->rlc_fw = NULL; 2322 rdev->rlc_fw = NULL;
2323 release_firmware(rdev->smc_fw);
2324 rdev->smc_fw = NULL;
2294 } 2325 }
2295 return err; 2326 return err;
2296} 2327}
@@ -4039,10 +4070,13 @@ int r600_irq_set(struct radeon_device *rdev)
4039 if ((rdev->family > CHIP_R600) && (rdev->family < CHIP_RV770)) { 4070 if ((rdev->family > CHIP_R600) && (rdev->family < CHIP_RV770)) {
4040 thermal_int = RREG32(CG_THERMAL_INT) & 4071 thermal_int = RREG32(CG_THERMAL_INT) &
4041 ~(THERM_INT_MASK_HIGH | THERM_INT_MASK_LOW); 4072 ~(THERM_INT_MASK_HIGH | THERM_INT_MASK_LOW);
4042 if (rdev->irq.dpm_thermal) { 4073 } else if (rdev->family >= CHIP_RV770) {
4043 DRM_DEBUG("dpm thermal\n"); 4074 thermal_int = RREG32(RV770_CG_THERMAL_INT) &
4044 thermal_int |= THERM_INT_MASK_HIGH | THERM_INT_MASK_LOW; 4075 ~(THERM_INT_MASK_HIGH | THERM_INT_MASK_LOW);
4045 } 4076 }
4077 if (rdev->irq.dpm_thermal) {
4078 DRM_DEBUG("dpm thermal\n");
4079 thermal_int |= THERM_INT_MASK_HIGH | THERM_INT_MASK_LOW;
4046 } 4080 }
4047 4081
4048 if (atomic_read(&rdev->irq.ring_int[RADEON_RING_TYPE_GFX_INDEX])) { 4082 if (atomic_read(&rdev->irq.ring_int[RADEON_RING_TYPE_GFX_INDEX])) {
@@ -4128,6 +4162,8 @@ int r600_irq_set(struct radeon_device *rdev)
4128 } 4162 }
4129 if ((rdev->family > CHIP_R600) && (rdev->family < CHIP_RV770)) { 4163 if ((rdev->family > CHIP_R600) && (rdev->family < CHIP_RV770)) {
4130 WREG32(CG_THERMAL_INT, thermal_int); 4164 WREG32(CG_THERMAL_INT, thermal_int);
4165 } else if (rdev->family >= CHIP_RV770) {
4166 WREG32(RV770_CG_THERMAL_INT, thermal_int);
4131 } 4167 }
4132 4168
4133 return 0; 4169 return 0;