From 102a0743326a03cd1a1202ceda21e175b7d3575c Mon Sep 17 00:00:00 2001
From: hc <hc@nodka.com>
Date: Tue, 20 Feb 2024 01:20:52 +0000
Subject: [PATCH] add new system file
---
kernel/drivers/gpu/arm/bifrost/backend/gpu/mali_kbase_pm_policy.c | 73 ++++++++++++++++++++++--------------
1 files changed, 45 insertions(+), 28 deletions(-)
diff --git a/kernel/drivers/gpu/arm/bifrost/backend/gpu/mali_kbase_pm_policy.c b/kernel/drivers/gpu/arm/bifrost/backend/gpu/mali_kbase_pm_policy.c
index 9b5006c..4788f04 100644
--- a/kernel/drivers/gpu/arm/bifrost/backend/gpu/mali_kbase_pm_policy.c
+++ b/kernel/drivers/gpu/arm/bifrost/backend/gpu/mali_kbase_pm_policy.c
@@ -1,7 +1,7 @@
// SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note
/*
*
- * (C) COPYRIGHT 2010-2021 ARM Limited. All rights reserved.
+ * (C) COPYRIGHT 2010-2022 ARM Limited. All rights reserved.
*
* This program is free software and is provided to you under the terms of the
* GNU General Public License version 2 as published by the Free Software
@@ -36,8 +36,13 @@
#include <linux/of.h>
static const struct kbase_pm_policy *const all_policy_list[] = {
+#if IS_ENABLED(CONFIG_MALI_BIFROST_NO_MALI)
+ &kbase_pm_always_on_policy_ops,
&kbase_pm_coarse_demand_policy_ops,
- &kbase_pm_always_on_policy_ops
+#else /* CONFIG_MALI_BIFROST_NO_MALI */
+ &kbase_pm_coarse_demand_policy_ops,
+ &kbase_pm_always_on_policy_ops,
+#endif /* CONFIG_MALI_BIFROST_NO_MALI */
};
void kbase_pm_policy_init(struct kbase_device *kbdev)
@@ -175,15 +180,14 @@
shaders_desired = kbdev->pm.backend.pm_current_policy->shaders_needed(kbdev);
- if (shaders_desired && kbase_pm_is_l2_desired(kbdev)) {
+ if (shaders_desired && kbase_pm_is_l2_desired(kbdev))
kbase_pm_update_state(kbdev);
- }
#endif
}
void kbase_pm_update_cores_state_nolock(struct kbase_device *kbdev)
{
- bool shaders_desired;
+ bool shaders_desired = false;
lockdep_assert_held(&kbdev->hwaccess_lock);
@@ -192,6 +196,7 @@
if (kbdev->pm.backend.poweroff_wait_in_progress)
return;
+#if !MALI_USE_CSF
if (kbdev->pm.backend.protected_transition_override)
/* We are trying to change in/out of protected mode - force all
* cores off so that the L2 powers down
@@ -199,15 +204,8 @@
shaders_desired = false;
else
shaders_desired = kbdev->pm.backend.pm_current_policy->shaders_needed(kbdev);
-
-#if MALI_USE_CSF
- /* On CSF GPUs, Host driver isn't supposed to do the power management
- * for shader cores. CSF firmware will power up the cores appropriately
- * and so from Driver's standpoint 'shaders_desired' flag shall always
- * remain 0.
- */
- shaders_desired = false;
#endif
+
if (kbdev->pm.backend.shaders_desired != shaders_desired) {
KBASE_KTRACE_ADD(kbdev, PM_CORES_CHANGE_DESIRED, NULL, kbdev->pm.backend.shaders_desired);
@@ -250,9 +248,8 @@
#if MALI_USE_CSF
static int policy_change_wait_for_L2_off(struct kbase_device *kbdev)
{
-#define WAIT_DURATION_MS (3000)
long remaining;
- long timeout = kbase_csf_timeout_in_jiffies(WAIT_DURATION_MS);
+ long timeout = kbase_csf_timeout_in_jiffies(kbase_get_timeout_ms(kbdev, CSF_PM_TIMEOUT));
int err = 0;
/* Wait for L2 becoming off, by which the MCU is also implicitly off
@@ -295,6 +292,8 @@
unsigned int new_policy_csf_pm_sched_flags;
bool sched_suspend;
bool reset_gpu = false;
+ bool reset_op_prevented = true;
+ struct kbase_csf_scheduler *scheduler = NULL;
#endif
KBASE_DEBUG_ASSERT(kbdev != NULL);
@@ -303,9 +302,23 @@
KBASE_KTRACE_ADD(kbdev, PM_SET_POLICY, NULL, new_policy->id);
#if MALI_USE_CSF
+ scheduler = &kbdev->csf.scheduler;
+ KBASE_DEBUG_ASSERT(scheduler != NULL);
+
/* Serialize calls on kbase_pm_set_policy() */
mutex_lock(&kbdev->pm.backend.policy_change_lock);
+ if (kbase_reset_gpu_prevent_and_wait(kbdev)) {
+ dev_warn(kbdev->dev, "Set PM policy failing to prevent gpu reset");
+ reset_op_prevented = false;
+ }
+
+ /* In case of CSF, the scheduler may be invoked to suspend. In that
+ * case, there is a risk that the L2 may be turned on by the time we
+ * check it here. So we hold the scheduler lock to avoid other operations
+ * interfering with the policy change and vice versa.
+ */
+ mutex_lock(&scheduler->lock);
spin_lock_irqsave(&kbdev->hwaccess_lock, flags);
/* policy_change_clamp_state_to_off, when needed, is set/cleared in
* this function, a very limited temporal scope for covering the
@@ -318,24 +331,22 @@
* the always_on policy, reflected by the CSF_DYNAMIC_PM_CORE_KEEP_ON
* flag bit.
*/
- sched_suspend = kbdev->csf.firmware_inited &&
+ sched_suspend = reset_op_prevented &&
(CSF_DYNAMIC_PM_CORE_KEEP_ON &
- (new_policy_csf_pm_sched_flags |
- kbdev->pm.backend.csf_pm_sched_flags));
+ (new_policy_csf_pm_sched_flags | kbdev->pm.backend.csf_pm_sched_flags));
spin_unlock_irqrestore(&kbdev->hwaccess_lock, flags);
- if (sched_suspend)
- kbase_csf_scheduler_pm_suspend(kbdev);
+ if (sched_suspend) {
+ /* Update the suspend flag to reflect actually suspend being done ! */
+ sched_suspend = !kbase_csf_scheduler_pm_suspend_no_lock(kbdev);
+ /* Set the reset recovery flag if the required suspend failed */
+ reset_gpu = !sched_suspend;
+ }
spin_lock_irqsave(&kbdev->hwaccess_lock, flags);
- /* If the current active policy is always_on, one needs to clamp the
- * MCU/L2 for reaching off-state
- */
- if (sched_suspend)
- kbdev->pm.backend.policy_change_clamp_state_to_off =
- CSF_DYNAMIC_PM_CORE_KEEP_ON & kbdev->pm.backend.csf_pm_sched_flags;
+ kbdev->pm.backend.policy_change_clamp_state_to_off = sched_suspend;
kbase_pm_update_state(kbdev);
spin_unlock_irqrestore(&kbdev->hwaccess_lock, flags);
@@ -394,13 +405,19 @@
#if MALI_USE_CSF
/* Reverse the suspension done */
+ if (sched_suspend)
+ kbase_csf_scheduler_pm_resume_no_lock(kbdev);
+ mutex_unlock(&scheduler->lock);
+
+ if (reset_op_prevented)
+ kbase_reset_gpu_allow(kbdev);
+
if (reset_gpu) {
dev_warn(kbdev->dev, "Resorting to GPU reset for policy change\n");
if (kbase_prepare_to_reset_gpu(kbdev, RESET_FLAGS_NONE))
kbase_reset_gpu(kbdev);
kbase_reset_gpu_wait(kbdev);
- } else if (sched_suspend)
- kbase_csf_scheduler_pm_resume(kbdev);
+ }
mutex_unlock(&kbdev->pm.backend.policy_change_lock);
#endif
--
Gitblit v1.6.2