Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

clk: qcom: common: Add support to configure clk regs in qcom_cc_really_probe

Add support to configure PLLS and clk registers in qcom_cc_really_probe().
This ensures all required power domains are enabled and kept ON by runtime
PM code in qcom_cc_really_probe() before configuring the PLLS or clock
registers.

Add support for qcom_cc_driver_data struct to maintain the clock
controllers PLLs and CBCRs data, and a pointer of it can be stored in
clock descriptor structure. If any clock controller driver requires to
program some additional misc register settings, it can register the
clk_regs_configure() callback in the driver data.

Reviewed-by: Bryan O'Donoghue <bryan.odonoghue@linaro.org>
Reviewed-by: Dmitry Baryshkov <dmitry.baryshkov@oss.qualcomm.com>
Signed-off-by: Jagadeesh Kona <quic_jkona@quicinc.com>
Reviewed-by: Konrad Dybcio <konrad.dybcio@oss.qualcomm.com>
Link: https://lore.kernel.org/r/20250530-videocc-pll-multi-pd-voting-v5-6-02303b3a582d@quicinc.com
Signed-off-by: Bjorn Andersson <andersson@kernel.org>

authored by

Jagadeesh Kona and committed by
Bjorn Andersson
452ae649 c0b66273

+53
+44
drivers/clk/qcom/common.c
··· 14 14 #include <linux/of.h> 15 15 16 16 #include "common.h" 17 + #include "clk-alpha-pll.h" 18 + #include "clk-branch.h" 17 19 #include "clk-rcg.h" 18 20 #include "clk-regmap.h" 19 21 #include "reset.h" ··· 287 285 desc->num_icc_hws, icd); 288 286 } 289 287 288 + static int qcom_cc_clk_pll_configure(const struct qcom_cc_driver_data *data, 289 + struct regmap *regmap) 290 + { 291 + const struct clk_init_data *init; 292 + struct clk_alpha_pll *pll; 293 + int i; 294 + 295 + for (i = 0; i < data->num_alpha_plls; i++) { 296 + pll = data->alpha_plls[i]; 297 + init = pll->clkr.hw.init; 298 + 299 + if (!pll->config || !pll->regs) { 300 + pr_err("%s: missing pll config or regs\n", init->name); 301 + return -EINVAL; 302 + } 303 + 304 + qcom_clk_alpha_pll_configure(pll, regmap); 305 + } 306 + 307 + return 0; 308 + } 309 + 310 + static void qcom_cc_clk_regs_configure(struct device *dev, const struct qcom_cc_driver_data *data, 311 + struct regmap *regmap) 312 + { 313 + int i; 314 + 315 + for (i = 0; i < data->num_clk_cbcrs; i++) 316 + qcom_branch_set_clk_en(regmap, data->clk_cbcrs[i]); 317 + 318 + if (data->clk_regs_configure) 319 + data->clk_regs_configure(dev, regmap); 320 + } 321 + 290 322 int qcom_cc_really_probe(struct device *dev, 291 323 const struct qcom_cc_desc *desc, struct regmap *regmap) 292 324 { ··· 349 313 ret = pm_runtime_resume_and_get(dev); 350 314 if (ret) 351 315 return ret; 316 + } 317 + 318 + if (desc->driver_data) { 319 + ret = qcom_cc_clk_pll_configure(desc->driver_data, regmap); 320 + if (ret) 321 + goto put_rpm; 322 + 323 + qcom_cc_clk_regs_configure(dev, desc->driver_data, regmap); 352 324 } 353 325 354 326 reset = &cc->reset;
+9
drivers/clk/qcom/common.h
··· 25 25 int clk_id; 26 26 }; 27 27 28 + struct qcom_cc_driver_data { 29 + struct clk_alpha_pll **alpha_plls; 30 + size_t num_alpha_plls; 31 + u32 *clk_cbcrs; 32 + size_t num_clk_cbcrs; 33 + void (*clk_regs_configure)(struct device *dev, struct regmap *regmap); 34 + }; 35 + 28 36 struct qcom_cc_desc { 29 37 const struct regmap_config *config; 30 38 struct clk_regmap **clks; ··· 47 39 size_t num_icc_hws; 48 40 unsigned int icc_first_node_id; 49 41 bool use_rpm; 42 + struct qcom_cc_driver_data *driver_data; 50 43 }; 51 44 52 45 /**