mirror of
https://github.com/raspberrypi/linux.git
synced 2025-12-06 01:49:46 +00:00
clk: qcom: common: Add interconnect clocks support
Unlike MSM platforms that manage NoC related clocks and scaling from RPM, IPQ SoCs dont involve RPM in managing NoC related clocks and there is no NoC scaling. However, there is a requirement to enable some NoC interface clocks for accessing the peripheral controllers present on these NoCs. Though exposing these as normal clocks would work, having a minimalistic interconnect driver to handle these clocks would make it consistent with other Qualcomm platforms resulting in common code paths. This is similar to msm8996-cbf's usage of icc-clk framework. Signed-off-by: Varadarajan Narayanan <quic_varada@quicinc.com> Link: https://lore.kernel.org/r/20240430064214.2030013-5-quic_varada@quicinc.com Signed-off-by: Bjorn Andersson <andersson@kernel.org>
This commit is contained in:
committed by
Bjorn Andersson
parent
d315311361
commit
8737ec830e
@@ -8,6 +8,7 @@
|
||||
#include <linux/regmap.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/clk-provider.h>
|
||||
#include <linux/interconnect-clk.h>
|
||||
#include <linux/reset-controller.h>
|
||||
#include <linux/of.h>
|
||||
|
||||
@@ -252,6 +253,38 @@ static struct clk_hw *qcom_cc_clk_hw_get(struct of_phandle_args *clkspec,
|
||||
return cc->rclks[idx] ? &cc->rclks[idx]->hw : NULL;
|
||||
}
|
||||
|
||||
static int qcom_cc_icc_register(struct device *dev,
|
||||
const struct qcom_cc_desc *desc)
|
||||
{
|
||||
struct icc_clk_data *icd;
|
||||
struct clk_hw *hws;
|
||||
int i;
|
||||
|
||||
if (!IS_ENABLED(CONFIG_INTERCONNECT_CLK))
|
||||
return 0;
|
||||
|
||||
if (!desc->icc_hws)
|
||||
return 0;
|
||||
|
||||
icd = devm_kcalloc(dev, desc->num_icc_hws, sizeof(*icd), GFP_KERNEL);
|
||||
if (!icd)
|
||||
return -ENOMEM;
|
||||
|
||||
for (i = 0; i < desc->num_icc_hws; i++) {
|
||||
icd[i].master_id = desc->icc_hws[i].master_id;
|
||||
icd[i].slave_id = desc->icc_hws[i].slave_id;
|
||||
hws = &desc->clks[desc->icc_hws[i].clk_id]->hw;
|
||||
icd[i].clk = devm_clk_hw_get_clk(dev, hws, "icc");
|
||||
if (!icd[i].clk)
|
||||
return dev_err_probe(dev, -ENOENT,
|
||||
"(%d) clock entry is null\n", i);
|
||||
icd[i].name = clk_hw_get_name(hws);
|
||||
}
|
||||
|
||||
return devm_icc_clk_register(dev, desc->icc_first_node_id,
|
||||
desc->num_icc_hws, icd);
|
||||
}
|
||||
|
||||
int qcom_cc_really_probe(struct device *dev,
|
||||
const struct qcom_cc_desc *desc, struct regmap *regmap)
|
||||
{
|
||||
@@ -320,7 +353,7 @@ int qcom_cc_really_probe(struct device *dev,
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
return 0;
|
||||
return qcom_cc_icc_register(dev, desc);
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(qcom_cc_really_probe);
|
||||
|
||||
|
||||
@@ -19,6 +19,12 @@ struct clk_hw;
|
||||
#define PLL_VOTE_FSM_ENA BIT(20)
|
||||
#define PLL_VOTE_FSM_RESET BIT(21)
|
||||
|
||||
struct qcom_icc_hws_data {
|
||||
int master_id;
|
||||
int slave_id;
|
||||
int clk_id;
|
||||
};
|
||||
|
||||
struct qcom_cc_desc {
|
||||
const struct regmap_config *config;
|
||||
struct clk_regmap **clks;
|
||||
@@ -29,6 +35,9 @@ struct qcom_cc_desc {
|
||||
size_t num_gdscs;
|
||||
struct clk_hw **clk_hws;
|
||||
size_t num_clk_hws;
|
||||
struct qcom_icc_hws_data *icc_hws;
|
||||
size_t num_icc_hws;
|
||||
unsigned int icc_first_node_id;
|
||||
};
|
||||
|
||||
/**
|
||||
|
||||
Reference in New Issue
Block a user