⬢ DragonFlyBSD Kernel Audit
DF-3953 / fix.diff
← back to finding ↓ download raw
diff --git a/sys/dev/drm/radeon/kv_dpm.c b/sys/dev/drm/radeon/kv_dpm.c
index 1111111..2222222 100644
--- a/sys/dev/drm/radeon/kv_dpm.c
+++ b/sys/dev/drm/radeon/kv_dpm.c
@@ -1274,7 +1274,9 @@ int kv_dpm_enable(struct radeon_device *rdev)
 	ret = kv_smc_bapm_enable(rdev, false);
 	if (ret) {
 		DRM_ERROR("kv_smc_bapm_enable failed\n");
 		return ret;
 	}
 
-	kv_update_current_ps(rdev, rdev->pm.dpm.boot_ps);
+	if (rdev->pm.dpm.boot_ps)
+		kv_update_current_ps(rdev, rdev->pm.dpm.boot_ps);
+	else
+		DRM_ERROR("kv_dpm_enable: no boot power state in VBIOS table\n");
 
 	return ret;
 }
@@ -1323,7 +1325,9 @@ void kv_dpm_disable(struct radeon_device *rdev)
 	kv_reset_am(rdev);
 	kv_enable_thermal_int(rdev, false);
 
-	kv_update_current_ps(rdev, rdev->pm.dpm.boot_ps);
+	if (rdev->pm.dpm.boot_ps)
+		kv_update_current_ps(rdev, rdev->pm.dpm.boot_ps);
 }
 
 static int kv_dpm_hw_fini(struct radeon_device *rdev)
@@ -2878,7 +2882,8 @@ u32 kv_dpm_get_sclk(struct radeon_device *rdev, bool low)
 	struct kv_power_info *pi = kv_get_pi(rdev);
 	struct kv_ps *requested_state = kv_get_ps(&pi->requested_rps);
 
-	if (low)
+	/* requested_rps.ps_priv is NULL until the first successful
+	 * pre_set_power_state (pick_power_state may have returned NULL). */
+	if (!requested_state)
+		return pi->sys_info.bootup_sclk;
+	if (low)
 		return requested_state->levels[0].sclk;
 	else
 		return requested_state->levels[requested_state->num_levels - 1].sclk;
# NOTE (outside this file's audited scope, recommended companion change):
#  radeon_pm.c:1448 discards kv_dpm_init()'s return value:
#      radeon_dpm_init(rdev);
#  should become:
#      ret = rdev->asic->dpm.init(rdev);
#      if (ret)
#              goto dpm_failed;
#  so a failed power-table parse cannot flow into radeon_dpm_enable() with
#  boot_ps == NULL / dpm.ps dangling (also see DF-3955).