The proxy power domain enable path requests INT_MAX performance
state for every proxy PD. On Hawi, the NSP proxy power domain's
RPMH power domain has no OPP at INT_MAX, while CX and MXC accept
INT_MAX, mapping to their maximum supported level.

Introduce a proxy_pd_performance_states array in qcom_pas_data
to allow per-PD RPMH levels to be declared explicitly. Platforms
that omit this field retain the existing INT_MAX behaviour.

Add Hawi CDSP remoteproc support with the following proxy PD
performance states:

  CX:  RPMH_REGULATOR_LEVEL_TURBO
  MXC: RPMH_REGULATOR_LEVEL_TURBO
  NSP: RPMH_REGULATOR_LEVEL_NOM

Signed-off-by: Mukesh Ojha <[email protected]>
---
 drivers/remoteproc/qcom_q6v5_pas.c | 50 ++++++++++++++++++++++++++++--
 1 file changed, 48 insertions(+), 2 deletions(-)

diff --git a/drivers/remoteproc/qcom_q6v5_pas.c 
b/drivers/remoteproc/qcom_q6v5_pas.c
index 01dc0194e130..c8bba2418d0d 100644
--- a/drivers/remoteproc/qcom_q6v5_pas.c
+++ b/drivers/remoteproc/qcom_q6v5_pas.c
@@ -28,6 +28,7 @@
 #include <linux/soc/qcom/mdt_loader.h>
 #include <linux/soc/qcom/smem.h>
 #include <linux/soc/qcom/smem_state.h>
+#include <dt-bindings/power/qcom,rpmhpd.h>
 
 #include "qcom_common.h"
 #include "qcom_pil_info.h"
@@ -51,6 +52,8 @@ struct qcom_pas_data {
        bool decrypt_shutdown;
 
        char **proxy_pd_names;
+       const unsigned int *proxy_pd_performance_states;
+       unsigned int num_proxy_pd_performance_states;
 
        const char *load_state;
        const char *ssr_name;
@@ -79,6 +82,7 @@ struct qcom_pas {
        struct regulator *px_supply;
 
        struct device *proxy_pds[3];
+       const unsigned int *proxy_pd_performance_states;
 
        int proxy_pd_count;
 
@@ -167,11 +171,16 @@ static int qcom_pas_pds_enable(struct qcom_pas *pas, 
struct device **pds,
        int i;
 
        for (i = 0; i < pd_count; i++) {
-               ret = dev_pm_genpd_set_performance_state(pds[i], INT_MAX);
+               unsigned int state = INT_MAX;
+
+               if (pas->proxy_pd_performance_states)
+                       state = pas->proxy_pd_performance_states[i];
+
+               ret = dev_pm_genpd_set_performance_state(pds[i], state);
                if (ret)
                        dev_warn(pas->dev,
                                 "failed to set proxy PD %d state %u: %d\n",
-                                i, INT_MAX, ret);
+                                i, state, ret);
                ret = pm_runtime_get_sync(pds[i]);
                if (ret < 0) {
                        pm_runtime_put_noidle(pds[i]);
@@ -877,6 +886,7 @@ static int qcom_pas_probe(struct platform_device *pdev)
        pas->info_name = desc->sysmon_name;
        pas->smem_host_id = desc->smem_host_id;
        pas->decrypt_shutdown = desc->decrypt_shutdown;
+       pas->proxy_pd_performance_states = desc->proxy_pd_performance_states;
        pas->region_assign_idx = desc->region_assign_idx;
        pas->region_assign_count = min_t(int, MAX_ASSIGN_COUNT, 
desc->region_assign_count);
        pas->region_assign_vmid = desc->region_assign_vmid;
@@ -912,6 +922,14 @@ static int qcom_pas_probe(struct platform_device *pdev)
                goto unassign_mem;
        pas->proxy_pd_count = ret;
 
+       if (WARN(desc->proxy_pd_performance_states &&
+                desc->num_proxy_pd_performance_states != pas->proxy_pd_count,
+                "proxy_pd_performance_states count %u != pd count %d\n",
+                desc->num_proxy_pd_performance_states, pas->proxy_pd_count)) {
+               ret = -EINVAL;
+               goto detach_proxy_pds;
+       }
+
        ret = qcom_q6v5_init(&pas->q6v5, pdev, rproc, desc->crash_reason_smem,
                             desc->load_state, qcom_pas_handover);
        if (ret)
@@ -1802,6 +1820,33 @@ static const struct qcom_pas_data glymur_soccp_resource 
= {
        .needs_tzmem = true,
 };
 
+static const struct qcom_pas_data hawi_cdsp_resource = {
+       .crash_reason_smem = 601,
+       .firmware_name = "cdsp.mdt",
+       .dtb_firmware_name = "cdsp_dtb.mdt",
+       .pas_id = 18,
+       .dtb_pas_id = 0x25,
+       .minidump_id = 7,
+       .auto_boot = true,
+       .proxy_pd_names = (char*[]){
+               "cx",
+               "mxc",
+               "nsp",
+               NULL
+       },
+       .proxy_pd_performance_states = (const unsigned int[]){
+               RPMH_REGULATOR_LEVEL_TURBO,
+               RPMH_REGULATOR_LEVEL_TURBO,
+               RPMH_REGULATOR_LEVEL_NOM,
+       },
+       .num_proxy_pd_performance_states = 3,
+       .load_state = "cdsp",
+       .ssr_name = "cdsp",
+       .sysmon_name = "cdsp",
+       .ssctl_id = 0x17,
+       .smem_host_id = 5,
+};
+
 static const struct qcom_pas_data eliza_cdsp_resource = {
        .crash_reason_smem = 601,
        .firmware_name = "cdsp.mbn",
@@ -1831,6 +1876,7 @@ static const struct of_device_id qcom_pas_of_match[] = {
        { .compatible = "qcom,eliza-adsp-pas", .data = &sm8550_adsp_resource },
        { .compatible = "qcom,eliza-cdsp-pas", .data = &eliza_cdsp_resource },
        { .compatible = "qcom,glymur-soccp-pas", .data = &glymur_soccp_resource 
},
+       { .compatible = "qcom,hawi-cdsp-pas", .data = &hawi_cdsp_resource },
        { .compatible = "qcom,kaanapali-soccp-pas", .data = 
&kaanapali_soccp_resource },
        { .compatible = "qcom,milos-adsp-pas", .data = &sm8550_adsp_resource },
        { .compatible = "qcom,milos-cdsp-pas", .data = &milos_cdsp_resource },
-- 
2.55.0


Reply via email to