* @disable_all_features_with_exception: Disable all features with
* exception to those in &mask.
*/
- int (*disable_all_features_with_exception)(struct smu_context *smu, enum smu_feature_mask mask);
+ int (*disable_all_features_with_exception)(struct smu_context *smu,
+ bool no_hw_disablement,
+ enum smu_feature_mask mask);
/**
* @notify_display_change: Enable fast memory clock switching.
if (smu->uploading_custom_pp_table &&
(adev->asic_type >= CHIP_NAVI10) &&
(adev->asic_type <= CHIP_DIMGREY_CAVEFISH))
- return 0;
+ return smu_disable_all_features_with_exception(smu,
+ true,
+ SMU_FEATURE_COUNT);
/*
* For Sienna_Cichlid, PMFW will handle the features disablement properly
*/
if ((adev->asic_type == CHIP_SIENNA_CICHLID) &&
use_baco)
- return 0;
+ return smu_disable_all_features_with_exception(smu,
+ true,
+ SMU_FEATURE_BACO_BIT);
/*
* For gpu reset, runpm and hibernation through BACO,
*/
if (use_baco && smu_feature_is_enabled(smu, SMU_FEATURE_BACO_BIT)) {
ret = smu_disable_all_features_with_exception(smu,
+ false,
SMU_FEATURE_BACO_BIT);
if (ret)
dev_err(adev->dev, "Failed to disable smu features except BACO.\n");
return ret;
}
+/**
+ * smu_cmn_disable_all_features_with_exception - disable all dpm features
+ * except this specified by
+ * @mask
+ *
+ * @smu: smu_context pointer
+ * @no_hw_disablement: whether real dpm disablement should be performed
+ * true: update the cache(about dpm enablement state) only
+ * false: real dpm disablement plus cache update
+ * @mask: the dpm feature which should not be disabled
+ * SMU_FEATURE_COUNT: no exception, all dpm features
+ * to disable
+ *
+ * Returns:
+ * 0 on success or a negative error code on failure.
+ */
int smu_cmn_disable_all_features_with_exception(struct smu_context *smu,
+ bool no_hw_disablement,
enum smu_feature_mask mask)
{
+ struct smu_feature *feature = &smu->smu_feature;
uint64_t features_to_disable = U64_MAX;
int skipped_feature_id;
- skipped_feature_id = smu_cmn_to_asic_specific_index(smu,
- CMN2ASIC_MAPPING_FEATURE,
- mask);
- if (skipped_feature_id < 0)
- return -EINVAL;
+ if (mask != SMU_FEATURE_COUNT) {
+ skipped_feature_id = smu_cmn_to_asic_specific_index(smu,
+ CMN2ASIC_MAPPING_FEATURE,
+ mask);
+ if (skipped_feature_id < 0)
+ return -EINVAL;
- features_to_disable &= ~(1ULL << skipped_feature_id);
+ features_to_disable &= ~(1ULL << skipped_feature_id);
+ }
- return smu_cmn_feature_update_enable_state(smu,
- features_to_disable,
- 0);
+ if (no_hw_disablement) {
+ mutex_lock(&feature->mutex);
+ bitmap_andnot(feature->enabled, feature->enabled,
+ (unsigned long *)(&features_to_disable), SMU_FEATURE_MAX);
+ mutex_unlock(&feature->mutex);
+
+ return 0;
+ } else {
+ return smu_cmn_feature_update_enable_state(smu,
+ features_to_disable,
+ 0);
+ }
}
int smu_cmn_get_smc_version(struct smu_context *smu,
uint64_t new_mask);
int smu_cmn_disable_all_features_with_exception(struct smu_context *smu,
+ bool no_hw_disablement,
enum smu_feature_mask mask);
int smu_cmn_get_smc_version(struct smu_context *smu,
#define smu_feature_set_allowed_mask(smu) smu_ppt_funcs(set_allowed_mask, 0, smu)
#define smu_feature_get_enabled_mask(smu, mask, num) smu_ppt_funcs(get_enabled_mask, 0, smu, mask, num)
#define smu_feature_is_enabled(smu, mask) smu_ppt_funcs(feature_is_enabled, 0, smu, mask)
-#define smu_disable_all_features_with_exception(smu, mask) smu_ppt_funcs(disable_all_features_with_exception, 0, smu, mask)
+#define smu_disable_all_features_with_exception(smu, no_hw_disablement, mask) smu_ppt_funcs(disable_all_features_with_exception, 0, smu, no_hw_disablement, mask)
#define smu_is_dpm_running(smu) smu_ppt_funcs(is_dpm_running, 0 , smu)
#define smu_notify_display_change(smu) smu_ppt_funcs(notify_display_change, 0, smu)
#define smu_populate_umd_state_clk(smu) smu_ppt_funcs(populate_umd_state_clk, 0, smu)