Skip to content

Commit db34c47

Browse files
committed
remoteproc: qcom_q6v5_adsp: Convert to dev_pm_domain_attach|detach_list()
Let's avoid some of the boilerplate code to manage the various PM domain cases, by converting into using dev_pm_domain_attach|detach_list(). As a part of the conversion, we are moving over to use device_links, which simplifies the runtime PM support too. Moreover, while attaching let's trust that an already attached single PM domain is the correct one. Cc: Mathieu Poirier <mathieu.poirier@linaro.org> Cc: Bjorn Andersson <andersson@kernel.org> Cc: Konrad Dybcio <konrad.dybcio@linaro.org> Cc: <linux-remoteproc@vger.kernel.org> Signed-off-by: Ulf Hansson <ulf.hansson@linaro.org> Link: https://lore.kernel.org/r/20240130123951.236243-5-ulf.hansson@linaro.org
1 parent 3f6905f commit db34c47

File tree

1 file changed

+73
-87
lines changed

1 file changed

+73
-87
lines changed

drivers/remoteproc/qcom_q6v5_adsp.c

Lines changed: 73 additions & 87 deletions
Original file line numberDiff line numberDiff line change
@@ -55,8 +55,6 @@
5555
#define QDSP6SS_CORE_CBCR 0x20
5656
#define QDSP6SS_SLEEP_CBCR 0x3c
5757

58-
#define QCOM_Q6V5_RPROC_PROXY_PD_MAX 3
59-
6058
#define LPASS_BOOT_CORE_START BIT(0)
6159
#define LPASS_BOOT_CMD_START BIT(0)
6260
#define LPASS_EFUSE_Q6SS_EVB_SEL 0x0
@@ -74,7 +72,8 @@ struct adsp_pil_data {
7472

7573
const char **clk_ids;
7674
int num_clks;
77-
const char **proxy_pd_names;
75+
const char **pd_names;
76+
unsigned int num_pds;
7877
const char *load_state;
7978
};
8079

@@ -110,8 +109,7 @@ struct qcom_adsp {
110109
size_t mem_size;
111110
bool has_iommu;
112111

113-
struct device *proxy_pds[QCOM_Q6V5_RPROC_PROXY_PD_MAX];
114-
size_t proxy_pd_count;
112+
struct dev_pm_domain_list *pd_list;
115113

116114
struct qcom_rproc_glink glink_subdev;
117115
struct qcom_rproc_ssr ssr_subdev;
@@ -120,98 +118,92 @@ struct qcom_adsp {
120118
int (*shutdown)(struct qcom_adsp *adsp);
121119
};
122120

123-
static int qcom_rproc_pds_attach(struct device *dev, struct qcom_adsp *adsp,
124-
const char **pd_names)
121+
static int qcom_rproc_pds_attach(struct qcom_adsp *adsp, const char **pd_names,
122+
unsigned int num_pds)
125123
{
126-
struct device **devs = adsp->proxy_pds;
127-
size_t num_pds = 0;
124+
struct device *dev = adsp->dev;
125+
struct dev_pm_domain_attach_data pd_data = {
126+
.pd_names = pd_names,
127+
.num_pd_names = num_pds,
128+
};
128129
int ret;
129-
int i;
130-
131-
if (!pd_names)
132-
return 0;
133130

134131
/* Handle single power domain */
135-
if (dev->pm_domain) {
136-
devs[0] = dev;
137-
pm_runtime_enable(dev);
138-
return 1;
139-
}
132+
if (dev->pm_domain)
133+
goto out;
140134

141-
while (pd_names[num_pds])
142-
num_pds++;
135+
if (!pd_names)
136+
return 0;
143137

144-
if (num_pds > ARRAY_SIZE(adsp->proxy_pds))
145-
return -E2BIG;
138+
ret = dev_pm_domain_attach_list(dev, &pd_data, &adsp->pd_list);
139+
if (ret < 0)
140+
return ret;
146141

147-
for (i = 0; i < num_pds; i++) {
148-
devs[i] = dev_pm_domain_attach_by_name(dev, pd_names[i]);
149-
if (IS_ERR_OR_NULL(devs[i])) {
150-
ret = PTR_ERR(devs[i]) ? : -ENODATA;
151-
goto unroll_attach;
152-
}
153-
}
142+
out:
143+
pm_runtime_enable(dev);
144+
return 0;
145+
}
154146

155-
return num_pds;
147+
static void qcom_rproc_pds_detach(struct qcom_adsp *adsp)
148+
{
149+
struct device *dev = adsp->dev;
150+
struct dev_pm_domain_list *pds = adsp->pd_list;
156151

157-
unroll_attach:
158-
for (i--; i >= 0; i--)
159-
dev_pm_domain_detach(devs[i], false);
152+
dev_pm_domain_detach_list(pds);
160153

161-
return ret;
154+
if (dev->pm_domain || pds)
155+
pm_runtime_disable(adsp->dev);
162156
}
163157

164-
static void qcom_rproc_pds_detach(struct qcom_adsp *adsp, struct device **pds,
165-
size_t pd_count)
158+
static int qcom_rproc_pds_enable(struct qcom_adsp *adsp)
166159
{
167160
struct device *dev = adsp->dev;
168-
int i;
161+
struct dev_pm_domain_list *pds = adsp->pd_list;
162+
int ret, i = 0;
169163

170-
/* Handle single power domain */
171-
if (dev->pm_domain && pd_count) {
172-
pm_runtime_disable(dev);
173-
return;
174-
}
164+
if (!dev->pm_domain && !pds)
165+
return 0;
175166

176-
for (i = 0; i < pd_count; i++)
177-
dev_pm_domain_detach(pds[i], false);
178-
}
167+
if (dev->pm_domain)
168+
dev_pm_genpd_set_performance_state(dev, INT_MAX);
179169

180-
static int qcom_rproc_pds_enable(struct qcom_adsp *adsp, struct device **pds,
181-
size_t pd_count)
182-
{
183-
int ret;
184-
int i;
185-
186-
for (i = 0; i < pd_count; i++) {
187-
dev_pm_genpd_set_performance_state(pds[i], INT_MAX);
188-
ret = pm_runtime_resume_and_get(pds[i]);
189-
if (ret < 0) {
190-
dev_pm_genpd_set_performance_state(pds[i], 0);
191-
goto unroll_pd_votes;
192-
}
170+
while (pds && i < pds->num_pds) {
171+
dev_pm_genpd_set_performance_state(pds->pd_devs[i], INT_MAX);
172+
i++;
193173
}
194174

195-
return 0;
175+
ret = pm_runtime_resume_and_get(dev);
176+
if (ret < 0) {
177+
while (pds && i > 0) {
178+
i--;
179+
dev_pm_genpd_set_performance_state(pds->pd_devs[i], 0);
180+
}
196181

197-
unroll_pd_votes:
198-
for (i--; i >= 0; i--) {
199-
dev_pm_genpd_set_performance_state(pds[i], 0);
200-
pm_runtime_put(pds[i]);
182+
if (dev->pm_domain)
183+
dev_pm_genpd_set_performance_state(dev, 0);
201184
}
202185

203186
return ret;
204187
}
205188

206-
static void qcom_rproc_pds_disable(struct qcom_adsp *adsp, struct device **pds,
207-
size_t pd_count)
189+
static void qcom_rproc_pds_disable(struct qcom_adsp *adsp)
208190
{
209-
int i;
191+
struct device *dev = adsp->dev;
192+
struct dev_pm_domain_list *pds = adsp->pd_list;
193+
int i = 0;
194+
195+
if (!dev->pm_domain && !pds)
196+
return;
197+
198+
if (dev->pm_domain)
199+
dev_pm_genpd_set_performance_state(dev, 0);
210200

211-
for (i = 0; i < pd_count; i++) {
212-
dev_pm_genpd_set_performance_state(pds[i], 0);
213-
pm_runtime_put(pds[i]);
201+
while (pds && i < pds->num_pds) {
202+
dev_pm_genpd_set_performance_state(pds->pd_devs[i], 0);
203+
i++;
214204
}
205+
206+
pm_runtime_put(dev);
215207
}
216208

217209
static int qcom_wpss_shutdown(struct qcom_adsp *adsp)
@@ -397,8 +389,7 @@ static int adsp_start(struct rproc *rproc)
397389
if (ret)
398390
goto adsp_smmu_unmap;
399391

400-
ret = qcom_rproc_pds_enable(adsp, adsp->proxy_pds,
401-
adsp->proxy_pd_count);
392+
ret = qcom_rproc_pds_enable(adsp);
402393
if (ret < 0)
403394
goto disable_xo_clk;
404395

@@ -448,7 +439,7 @@ static int adsp_start(struct rproc *rproc)
448439
disable_adsp_clks:
449440
clk_bulk_disable_unprepare(adsp->num_clks, adsp->clks);
450441
disable_power_domain:
451-
qcom_rproc_pds_disable(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
442+
qcom_rproc_pds_disable(adsp);
452443
disable_xo_clk:
453444
clk_disable_unprepare(adsp->xo);
454445
adsp_smmu_unmap:
@@ -464,7 +455,7 @@ static void qcom_adsp_pil_handover(struct qcom_q6v5 *q6v5)
464455
struct qcom_adsp *adsp = container_of(q6v5, struct qcom_adsp, q6v5);
465456

466457
clk_disable_unprepare(adsp->xo);
467-
qcom_rproc_pds_disable(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
458+
qcom_rproc_pds_disable(adsp);
468459
}
469460

470461
static int adsp_stop(struct rproc *rproc)
@@ -715,13 +706,11 @@ static int adsp_probe(struct platform_device *pdev)
715706
if (ret)
716707
goto free_rproc;
717708

718-
ret = qcom_rproc_pds_attach(adsp->dev, adsp,
719-
desc->proxy_pd_names);
709+
ret = qcom_rproc_pds_attach(adsp, desc->pd_names, desc->num_pds);
720710
if (ret < 0) {
721711
dev_err(&pdev->dev, "Failed to attach proxy power domains\n");
722712
goto free_rproc;
723713
}
724-
adsp->proxy_pd_count = ret;
725714

726715
ret = adsp_init_reset(adsp);
727716
if (ret)
@@ -753,7 +742,7 @@ static int adsp_probe(struct platform_device *pdev)
753742
return 0;
754743

755744
disable_pm:
756-
qcom_rproc_pds_detach(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
745+
qcom_rproc_pds_detach(adsp);
757746

758747
free_rproc:
759748
rproc_free(rproc);
@@ -771,7 +760,7 @@ static void adsp_remove(struct platform_device *pdev)
771760
qcom_remove_glink_subdev(adsp->rproc, &adsp->glink_subdev);
772761
qcom_remove_sysmon_subdev(adsp->sysmon);
773762
qcom_remove_ssr_subdev(adsp->rproc, &adsp->ssr_subdev);
774-
qcom_rproc_pds_detach(adsp, adsp->proxy_pds, adsp->proxy_pd_count);
763+
qcom_rproc_pds_detach(adsp);
775764
rproc_free(adsp->rproc);
776765
}
777766

@@ -788,9 +777,8 @@ static const struct adsp_pil_data adsp_resource_init = {
788777
"qdsp6ss_xo", "qdsp6ss_sleep", "qdsp6ss_core", NULL
789778
},
790779
.num_clks = 7,
791-
.proxy_pd_names = (const char*[]) {
792-
"cx", NULL
793-
},
780+
.pd_names = (const char*[]) { "cx" },
781+
.num_pds = 1,
794782
};
795783

796784
static const struct adsp_pil_data adsp_sc7280_resource_init = {
@@ -821,9 +809,8 @@ static const struct adsp_pil_data cdsp_resource_init = {
821809
"q6_axim", NULL
822810
},
823811
.num_clks = 7,
824-
.proxy_pd_names = (const char*[]) {
825-
"cx", NULL
826-
},
812+
.pd_names = (const char*[]) { "cx" },
813+
.num_pds = 1,
827814
};
828815

829816
static const struct adsp_pil_data wpss_resource_init = {
@@ -839,9 +826,8 @@ static const struct adsp_pil_data wpss_resource_init = {
839826
"ahb_bdg", "ahb", "rscp", NULL
840827
},
841828
.num_clks = 3,
842-
.proxy_pd_names = (const char*[]) {
843-
"cx", "mx", NULL
844-
},
829+
.pd_names = (const char*[]) { "cx", "mx" },
830+
.num_pds = 2,
845831
};
846832

847833
static const struct of_device_id adsp_of_match[] = {

0 commit comments

Comments
 (0)