From: Mike Turquette <mturquette@linaro.org>
To: Viresh Kumar <viresh.kumar@linaro.org>, rjw@sisk.pl, swarren@nvidia.com
Cc: linaro-kernel@lists.linaro.org, patches@linaro.org,
cpufreq@vger.kernel.org, linux-pm@vger.kernel.org,
linux-kernel@vger.kernel.org,
linux-arm-kernel@lists.infradead.org,
Viresh Kumar <viresh.kumar@linaro.org>
Subject: Re: [PATCH 1/6] clk: Tegra: Add CPU0 clock driver
Date: Wed, 07 Aug 2013 09:44:23 -0700 [thread overview]
Message-ID: <20130807164423.5348.81610@quantum> (raw)
In-Reply-To: <8d192a13cb7e088943da40689d62bc6353bd8604.1375886595.git.viresh.kumar@linaro.org>
Quoting Viresh Kumar (2013-08-07 07:46:43)
> This patch adds CPU0's clk driver for Tegra. It will be used by the generic
> cpufreq-cpu0 driver to get/set cpu clk.
>
> Most of the platform specific bits are picked from tegra-cpufreq.c.
>
> Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Hi Viresh,
It is nice to see more CPUfreq consolidation.
I'm currently hacking on a patch to introduce clk_coordinate_rates().
That function may be a better fit for this sort of thing compared to
overloading the .set_rate callback. I'll try to get the patches on the
list ASAP and will Cc you.
Regards,
Mike
> ---
> drivers/clk/tegra/Makefile | 1 +
> drivers/clk/tegra/clk-cpu.c | 164 ++++++++++++++++++++++++++++++++++++++++
> drivers/clk/tegra/clk-tegra30.c | 4 +
> include/linux/clk/tegra.h | 1 +
> 4 files changed, 170 insertions(+)
> create mode 100644 drivers/clk/tegra/clk-cpu.c
>
> diff --git a/drivers/clk/tegra/Makefile b/drivers/clk/tegra/Makefile
> index f49fac2..0e818c0 100644
> --- a/drivers/clk/tegra/Makefile
> +++ b/drivers/clk/tegra/Makefile
> @@ -10,3 +10,4 @@ obj-y += clk-super.o
> obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += clk-tegra20.o
> obj-$(CONFIG_ARCH_TEGRA_3x_SOC) += clk-tegra30.o
> obj-$(CONFIG_ARCH_TEGRA_114_SOC) += clk-tegra114.o
> +obj-$(CONFIG_GENERIC_CPUFREQ_CPU0) += clk-cpu.o
> diff --git a/drivers/clk/tegra/clk-cpu.c b/drivers/clk/tegra/clk-cpu.c
> new file mode 100644
> index 0000000..01716d6
> --- /dev/null
> +++ b/drivers/clk/tegra/clk-cpu.c
> @@ -0,0 +1,164 @@
> +/*
> + * Copyright (C) 2013 Linaro
> + *
> + * Author: Viresh Kumar <viresh.kumar@linaro.org>
> + *
> + * This file is licensed under the terms of the GNU General Public
> + * License version 2. This program is licensed "as is" without any
> + * warranty of any kind, whether express or implied.
> + */
> +
> +/*
> + * Responsible for setting cpu0 clk as requested by cpufreq-cpu0 driver
> + *
> + * All platform specific bits are taken from tegra-cpufreq driver.
> + */
> +
> +#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
> +
> +#include <linux/clk-provider.h>
> +#include <linux/err.h>
> +#include <linux/slab.h>
> +
> +#define to_clk_cpu0(_hw) container_of(_hw, struct clk_cpu0, hw)
> +
> +struct clk_cpu0 {
> + struct clk_hw hw;
> + spinlock_t *lock;
> +};
> +
> +static struct clk *cpu_clk;
> +static struct clk *pll_x_clk;
> +static struct clk *pll_p_clk;
> +static struct clk *emc_clk;
> +
> +static unsigned long cpu0_recalc_rate(struct clk_hw *hw,
> + unsigned long parent_rate)
> +{
> + return clk_get_rate(cpu_clk);
> +}
> +
> +static long cpu0_round_rate(struct clk_hw *hw, unsigned long drate,
> + unsigned long *parent_rate)
> +{
> + return clk_round_rate(cpu_clk, drate);
> +}
> +
> +static int cpu0_set_rate(struct clk_hw *hw, unsigned long rate,
> + unsigned long parent_rate)
> +{
> + int ret;
> +
> + /*
> + * Vote on memory bus frequency based on cpu frequency
> + * This sets the minimum frequency, display or avp may request higher
> + */
> + if (rate >= 816000000)
> + clk_set_rate(emc_clk, 600000000); /* cpu 816 MHz, emc max */
> + else if (rate >= 456000000)
> + clk_set_rate(emc_clk, 300000000); /* cpu 456 MHz, emc 150Mhz */
> + else
> + clk_set_rate(emc_clk, 100000000); /* emc 50Mhz */
> +
> + /*
> + * Take an extra reference to the main pll so it doesn't turn
> + * off when we move the cpu off of it
> + */
> + clk_prepare_enable(pll_x_clk);
> +
> + ret = clk_set_parent(cpu_clk, pll_p_clk);
> + if (ret) {
> + pr_err("%s: Failed to switch cpu to clock pll_p\n", __func__);
> + goto out;
> + }
> +
> + if (rate == clk_get_rate(pll_p_clk))
> + goto out;
> +
> + ret = clk_set_rate(pll_x_clk, rate);
> + if (ret) {
> + pr_err("Failed to change pll_x to %lu\n", rate);
> + goto out;
> + }
> +
> + ret = clk_set_parent(cpu_clk, pll_x_clk);
> + if (ret) {
> + pr_err("Failed to switch cpu to clock pll_x\n");
> + goto out;
> + }
> +
> +out:
> + clk_disable_unprepare(pll_x_clk);
> + return ret;
> +}
> +
> +static struct clk_ops clk_cpu0_ops = {
> + .recalc_rate = cpu0_recalc_rate,
> + .round_rate = cpu0_round_rate,
> + .set_rate = cpu0_set_rate,
> +};
> +
> +struct clk *tegra_clk_register_cpu0(void)
> +{
> + struct clk_init_data init;
> + struct clk_cpu0 *cpu0;
> + struct clk *clk;
> +
> + cpu0 = kzalloc(sizeof(*cpu0), GFP_KERNEL);
> + if (!cpu0) {
> + pr_err("%s: could not allocate cpu0 clk\n", __func__);
> + return ERR_PTR(-ENOMEM);
> + }
> +
> + cpu_clk = clk_get_sys(NULL, "cpu");
> + if (IS_ERR(cpu_clk)) {
> + clk = cpu_clk;
> + goto free_mem;
> + }
> +
> + pll_x_clk = clk_get_sys(NULL, "pll_x");
> + if (IS_ERR(pll_x_clk)) {
> + clk = pll_x_clk;
> + goto put_cpu_clk;
> + }
> +
> + pll_p_clk = clk_get_sys(NULL, "pll_p_cclk");
> + if (IS_ERR(pll_p_clk)) {
> + clk = pll_p_clk;
> + goto put_pll_x_clk;
> + }
> +
> + emc_clk = clk_get_sys("cpu", "emc");
> + if (IS_ERR(emc_clk)) {
> + clk = emc_clk;
> + goto put_pll_p_clk;
> + }
> +
> + cpu0->hw.init = &init;
> +
> + init.name = "cpu0";
> + init.ops = &clk_cpu0_ops;
> + init.flags = CLK_IS_ROOT | CLK_GET_RATE_NOCACHE;
> + init.num_parents = 0;
> +
> + clk = clk_register(NULL, &cpu0->hw);
> + if (!IS_ERR(clk))
> + return clk;
> +
> + clk_prepare_enable(emc_clk);
> + clk_prepare_enable(cpu_clk);
> +
> + clk_put(emc_clk);
> +put_pll_p_clk:
> + clk_put(pll_p_clk);
> +put_pll_x_clk:
> + clk_put(pll_x_clk);
> +put_cpu_clk:
> + clk_put(cpu_clk);
> +free_mem:
> + kfree(cpu0);
> +
> + pr_err("%s: clk register failed\n", __func__);
> +
> + return NULL;
> +}
> diff --git a/drivers/clk/tegra/clk-tegra30.c b/drivers/clk/tegra/clk-tegra30.c
> index e2c6ca0..1cabeea 100644
> --- a/drivers/clk/tegra/clk-tegra30.c
> +++ b/drivers/clk/tegra/clk-tegra30.c
> @@ -1396,6 +1396,10 @@ static void __init tegra30_super_clk_init(void)
> CLK_SET_RATE_PARENT, 1, 2);
> clk_register_clkdev(clk, "twd", NULL);
> clks[twd] = clk;
> +
> + /* cpu0 clk for cpufreq driver */
> + clk = tegra_clk_register_cpu0();
> + clk_register_clkdev(clk, NULL, "cpu0");
> }
>
> static const char *mux_pllacp_clkm[] = { "pll_a_out0", "unused", "pll_p",
> diff --git a/include/linux/clk/tegra.h b/include/linux/clk/tegra.h
> index 23a0cee..d416138 100644
> --- a/include/linux/clk/tegra.h
> +++ b/include/linux/clk/tegra.h
> @@ -128,5 +128,6 @@ static inline void tegra_periph_reset_deassert(struct clk *c) {}
> static inline void tegra_periph_reset_assert(struct clk *c) {}
> #endif
> void tegra_clocks_apply_init_table(void);
> +struct clk *tegra_clk_register_cpu0(void);
>
> #endif /* __LINUX_CLK_TEGRA_H_ */
> --
> 1.7.12.rc2.18.g61b472e
WARNING: multiple messages have this Message-ID (diff)
From: Mike Turquette <mturquette@linaro.org>
To: rjw@sisk.pl, swarren@nvidia.com
Cc: linaro-kernel@lists.linaro.org, patches@linaro.org,
cpufreq@vger.kernel.org, linux-pm@vger.kernel.org,
linux-kernel@vger.kernel.org,
linux-arm-kernel@lists.infradead.org,
Viresh Kumar <viresh.kumar@linaro.org>
Subject: Re: [PATCH 1/6] clk: Tegra: Add CPU0 clock driver
Date: Wed, 07 Aug 2013 09:44:23 -0700 [thread overview]
Message-ID: <20130807164423.5348.81610@quantum> (raw)
In-Reply-To: <8d192a13cb7e088943da40689d62bc6353bd8604.1375886595.git.viresh.kumar@linaro.org>
Quoting Viresh Kumar (2013-08-07 07:46:43)
> This patch adds CPU0's clk driver for Tegra. It will be used by the generic
> cpufreq-cpu0 driver to get/set cpu clk.
>
> Most of the platform specific bits are picked from tegra-cpufreq.c.
>
> Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Hi Viresh,
It is nice to see more CPUfreq consolidation.
I'm currently hacking on a patch to introduce clk_coordinate_rates().
That function may be a better fit for this sort of thing compared to
overloading the .set_rate callback. I'll try to get the patches on the
list ASAP and will Cc you.
Regards,
Mike
> ---
> drivers/clk/tegra/Makefile | 1 +
> drivers/clk/tegra/clk-cpu.c | 164 ++++++++++++++++++++++++++++++++++++++++
> drivers/clk/tegra/clk-tegra30.c | 4 +
> include/linux/clk/tegra.h | 1 +
> 4 files changed, 170 insertions(+)
> create mode 100644 drivers/clk/tegra/clk-cpu.c
>
> diff --git a/drivers/clk/tegra/Makefile b/drivers/clk/tegra/Makefile
> index f49fac2..0e818c0 100644
> --- a/drivers/clk/tegra/Makefile
> +++ b/drivers/clk/tegra/Makefile
> @@ -10,3 +10,4 @@ obj-y += clk-super.o
> obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += clk-tegra20.o
> obj-$(CONFIG_ARCH_TEGRA_3x_SOC) += clk-tegra30.o
> obj-$(CONFIG_ARCH_TEGRA_114_SOC) += clk-tegra114.o
> +obj-$(CONFIG_GENERIC_CPUFREQ_CPU0) += clk-cpu.o
> diff --git a/drivers/clk/tegra/clk-cpu.c b/drivers/clk/tegra/clk-cpu.c
> new file mode 100644
> index 0000000..01716d6
> --- /dev/null
> +++ b/drivers/clk/tegra/clk-cpu.c
> @@ -0,0 +1,164 @@
> +/*
> + * Copyright (C) 2013 Linaro
> + *
> + * Author: Viresh Kumar <viresh.kumar@linaro.org>
> + *
> + * This file is licensed under the terms of the GNU General Public
> + * License version 2. This program is licensed "as is" without any
> + * warranty of any kind, whether express or implied.
> + */
> +
> +/*
> + * Responsible for setting cpu0 clk as requested by cpufreq-cpu0 driver
> + *
> + * All platform specific bits are taken from tegra-cpufreq driver.
> + */
> +
> +#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
> +
> +#include <linux/clk-provider.h>
> +#include <linux/err.h>
> +#include <linux/slab.h>
> +
> +#define to_clk_cpu0(_hw) container_of(_hw, struct clk_cpu0, hw)
> +
> +struct clk_cpu0 {
> + struct clk_hw hw;
> + spinlock_t *lock;
> +};
> +
> +static struct clk *cpu_clk;
> +static struct clk *pll_x_clk;
> +static struct clk *pll_p_clk;
> +static struct clk *emc_clk;
> +
> +static unsigned long cpu0_recalc_rate(struct clk_hw *hw,
> + unsigned long parent_rate)
> +{
> + return clk_get_rate(cpu_clk);
> +}
> +
> +static long cpu0_round_rate(struct clk_hw *hw, unsigned long drate,
> + unsigned long *parent_rate)
> +{
> + return clk_round_rate(cpu_clk, drate);
> +}
> +
> +static int cpu0_set_rate(struct clk_hw *hw, unsigned long rate,
> + unsigned long parent_rate)
> +{
> + int ret;
> +
> + /*
> + * Vote on memory bus frequency based on cpu frequency
> + * This sets the minimum frequency, display or avp may request higher
> + */
> + if (rate >= 816000000)
> + clk_set_rate(emc_clk, 600000000); /* cpu 816 MHz, emc max */
> + else if (rate >= 456000000)
> + clk_set_rate(emc_clk, 300000000); /* cpu 456 MHz, emc 150Mhz */
> + else
> + clk_set_rate(emc_clk, 100000000); /* emc 50Mhz */
> +
> + /*
> + * Take an extra reference to the main pll so it doesn't turn
> + * off when we move the cpu off of it
> + */
> + clk_prepare_enable(pll_x_clk);
> +
> + ret = clk_set_parent(cpu_clk, pll_p_clk);
> + if (ret) {
> + pr_err("%s: Failed to switch cpu to clock pll_p\n", __func__);
> + goto out;
> + }
> +
> + if (rate == clk_get_rate(pll_p_clk))
> + goto out;
> +
> + ret = clk_set_rate(pll_x_clk, rate);
> + if (ret) {
> + pr_err("Failed to change pll_x to %lu\n", rate);
> + goto out;
> + }
> +
> + ret = clk_set_parent(cpu_clk, pll_x_clk);
> + if (ret) {
> + pr_err("Failed to switch cpu to clock pll_x\n");
> + goto out;
> + }
> +
> +out:
> + clk_disable_unprepare(pll_x_clk);
> + return ret;
> +}
> +
> +static struct clk_ops clk_cpu0_ops = {
> + .recalc_rate = cpu0_recalc_rate,
> + .round_rate = cpu0_round_rate,
> + .set_rate = cpu0_set_rate,
> +};
> +
> +struct clk *tegra_clk_register_cpu0(void)
> +{
> + struct clk_init_data init;
> + struct clk_cpu0 *cpu0;
> + struct clk *clk;
> +
> + cpu0 = kzalloc(sizeof(*cpu0), GFP_KERNEL);
> + if (!cpu0) {
> + pr_err("%s: could not allocate cpu0 clk\n", __func__);
> + return ERR_PTR(-ENOMEM);
> + }
> +
> + cpu_clk = clk_get_sys(NULL, "cpu");
> + if (IS_ERR(cpu_clk)) {
> + clk = cpu_clk;
> + goto free_mem;
> + }
> +
> + pll_x_clk = clk_get_sys(NULL, "pll_x");
> + if (IS_ERR(pll_x_clk)) {
> + clk = pll_x_clk;
> + goto put_cpu_clk;
> + }
> +
> + pll_p_clk = clk_get_sys(NULL, "pll_p_cclk");
> + if (IS_ERR(pll_p_clk)) {
> + clk = pll_p_clk;
> + goto put_pll_x_clk;
> + }
> +
> + emc_clk = clk_get_sys("cpu", "emc");
> + if (IS_ERR(emc_clk)) {
> + clk = emc_clk;
> + goto put_pll_p_clk;
> + }
> +
> + cpu0->hw.init = &init;
> +
> + init.name = "cpu0";
> + init.ops = &clk_cpu0_ops;
> + init.flags = CLK_IS_ROOT | CLK_GET_RATE_NOCACHE;
> + init.num_parents = 0;
> +
> + clk = clk_register(NULL, &cpu0->hw);
> + if (!IS_ERR(clk))
> + return clk;
> +
> + clk_prepare_enable(emc_clk);
> + clk_prepare_enable(cpu_clk);
> +
> + clk_put(emc_clk);
> +put_pll_p_clk:
> + clk_put(pll_p_clk);
> +put_pll_x_clk:
> + clk_put(pll_x_clk);
> +put_cpu_clk:
> + clk_put(cpu_clk);
> +free_mem:
> + kfree(cpu0);
> +
> + pr_err("%s: clk register failed\n", __func__);
> +
> + return NULL;
> +}
> diff --git a/drivers/clk/tegra/clk-tegra30.c b/drivers/clk/tegra/clk-tegra30.c
> index e2c6ca0..1cabeea 100644
> --- a/drivers/clk/tegra/clk-tegra30.c
> +++ b/drivers/clk/tegra/clk-tegra30.c
> @@ -1396,6 +1396,10 @@ static void __init tegra30_super_clk_init(void)
> CLK_SET_RATE_PARENT, 1, 2);
> clk_register_clkdev(clk, "twd", NULL);
> clks[twd] = clk;
> +
> + /* cpu0 clk for cpufreq driver */
> + clk = tegra_clk_register_cpu0();
> + clk_register_clkdev(clk, NULL, "cpu0");
> }
>
> static const char *mux_pllacp_clkm[] = { "pll_a_out0", "unused", "pll_p",
> diff --git a/include/linux/clk/tegra.h b/include/linux/clk/tegra.h
> index 23a0cee..d416138 100644
> --- a/include/linux/clk/tegra.h
> +++ b/include/linux/clk/tegra.h
> @@ -128,5 +128,6 @@ static inline void tegra_periph_reset_deassert(struct clk *c) {}
> static inline void tegra_periph_reset_assert(struct clk *c) {}
> #endif
> void tegra_clocks_apply_init_table(void);
> +struct clk *tegra_clk_register_cpu0(void);
>
> #endif /* __LINUX_CLK_TEGRA_H_ */
> --
> 1.7.12.rc2.18.g61b472e
WARNING: multiple messages have this Message-ID (diff)
From: mturquette@linaro.org (Mike Turquette)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH 1/6] clk: Tegra: Add CPU0 clock driver
Date: Wed, 07 Aug 2013 09:44:23 -0700 [thread overview]
Message-ID: <20130807164423.5348.81610@quantum> (raw)
In-Reply-To: <8d192a13cb7e088943da40689d62bc6353bd8604.1375886595.git.viresh.kumar@linaro.org>
Quoting Viresh Kumar (2013-08-07 07:46:43)
> This patch adds CPU0's clk driver for Tegra. It will be used by the generic
> cpufreq-cpu0 driver to get/set cpu clk.
>
> Most of the platform specific bits are picked from tegra-cpufreq.c.
>
> Signed-off-by: Viresh Kumar <viresh.kumar@linaro.org>
Hi Viresh,
It is nice to see more CPUfreq consolidation.
I'm currently hacking on a patch to introduce clk_coordinate_rates().
That function may be a better fit for this sort of thing compared to
overloading the .set_rate callback. I'll try to get the patches on the
list ASAP and will Cc you.
Regards,
Mike
> ---
> drivers/clk/tegra/Makefile | 1 +
> drivers/clk/tegra/clk-cpu.c | 164 ++++++++++++++++++++++++++++++++++++++++
> drivers/clk/tegra/clk-tegra30.c | 4 +
> include/linux/clk/tegra.h | 1 +
> 4 files changed, 170 insertions(+)
> create mode 100644 drivers/clk/tegra/clk-cpu.c
>
> diff --git a/drivers/clk/tegra/Makefile b/drivers/clk/tegra/Makefile
> index f49fac2..0e818c0 100644
> --- a/drivers/clk/tegra/Makefile
> +++ b/drivers/clk/tegra/Makefile
> @@ -10,3 +10,4 @@ obj-y += clk-super.o
> obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += clk-tegra20.o
> obj-$(CONFIG_ARCH_TEGRA_3x_SOC) += clk-tegra30.o
> obj-$(CONFIG_ARCH_TEGRA_114_SOC) += clk-tegra114.o
> +obj-$(CONFIG_GENERIC_CPUFREQ_CPU0) += clk-cpu.o
> diff --git a/drivers/clk/tegra/clk-cpu.c b/drivers/clk/tegra/clk-cpu.c
> new file mode 100644
> index 0000000..01716d6
> --- /dev/null
> +++ b/drivers/clk/tegra/clk-cpu.c
> @@ -0,0 +1,164 @@
> +/*
> + * Copyright (C) 2013 Linaro
> + *
> + * Author: Viresh Kumar <viresh.kumar@linaro.org>
> + *
> + * This file is licensed under the terms of the GNU General Public
> + * License version 2. This program is licensed "as is" without any
> + * warranty of any kind, whether express or implied.
> + */
> +
> +/*
> + * Responsible for setting cpu0 clk as requested by cpufreq-cpu0 driver
> + *
> + * All platform specific bits are taken from tegra-cpufreq driver.
> + */
> +
> +#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
> +
> +#include <linux/clk-provider.h>
> +#include <linux/err.h>
> +#include <linux/slab.h>
> +
> +#define to_clk_cpu0(_hw) container_of(_hw, struct clk_cpu0, hw)
> +
> +struct clk_cpu0 {
> + struct clk_hw hw;
> + spinlock_t *lock;
> +};
> +
> +static struct clk *cpu_clk;
> +static struct clk *pll_x_clk;
> +static struct clk *pll_p_clk;
> +static struct clk *emc_clk;
> +
> +static unsigned long cpu0_recalc_rate(struct clk_hw *hw,
> + unsigned long parent_rate)
> +{
> + return clk_get_rate(cpu_clk);
> +}
> +
> +static long cpu0_round_rate(struct clk_hw *hw, unsigned long drate,
> + unsigned long *parent_rate)
> +{
> + return clk_round_rate(cpu_clk, drate);
> +}
> +
> +static int cpu0_set_rate(struct clk_hw *hw, unsigned long rate,
> + unsigned long parent_rate)
> +{
> + int ret;
> +
> + /*
> + * Vote on memory bus frequency based on cpu frequency
> + * This sets the minimum frequency, display or avp may request higher
> + */
> + if (rate >= 816000000)
> + clk_set_rate(emc_clk, 600000000); /* cpu 816 MHz, emc max */
> + else if (rate >= 456000000)
> + clk_set_rate(emc_clk, 300000000); /* cpu 456 MHz, emc 150Mhz */
> + else
> + clk_set_rate(emc_clk, 100000000); /* emc 50Mhz */
> +
> + /*
> + * Take an extra reference to the main pll so it doesn't turn
> + * off when we move the cpu off of it
> + */
> + clk_prepare_enable(pll_x_clk);
> +
> + ret = clk_set_parent(cpu_clk, pll_p_clk);
> + if (ret) {
> + pr_err("%s: Failed to switch cpu to clock pll_p\n", __func__);
> + goto out;
> + }
> +
> + if (rate == clk_get_rate(pll_p_clk))
> + goto out;
> +
> + ret = clk_set_rate(pll_x_clk, rate);
> + if (ret) {
> + pr_err("Failed to change pll_x to %lu\n", rate);
> + goto out;
> + }
> +
> + ret = clk_set_parent(cpu_clk, pll_x_clk);
> + if (ret) {
> + pr_err("Failed to switch cpu to clock pll_x\n");
> + goto out;
> + }
> +
> +out:
> + clk_disable_unprepare(pll_x_clk);
> + return ret;
> +}
> +
> +static struct clk_ops clk_cpu0_ops = {
> + .recalc_rate = cpu0_recalc_rate,
> + .round_rate = cpu0_round_rate,
> + .set_rate = cpu0_set_rate,
> +};
> +
> +struct clk *tegra_clk_register_cpu0(void)
> +{
> + struct clk_init_data init;
> + struct clk_cpu0 *cpu0;
> + struct clk *clk;
> +
> + cpu0 = kzalloc(sizeof(*cpu0), GFP_KERNEL);
> + if (!cpu0) {
> + pr_err("%s: could not allocate cpu0 clk\n", __func__);
> + return ERR_PTR(-ENOMEM);
> + }
> +
> + cpu_clk = clk_get_sys(NULL, "cpu");
> + if (IS_ERR(cpu_clk)) {
> + clk = cpu_clk;
> + goto free_mem;
> + }
> +
> + pll_x_clk = clk_get_sys(NULL, "pll_x");
> + if (IS_ERR(pll_x_clk)) {
> + clk = pll_x_clk;
> + goto put_cpu_clk;
> + }
> +
> + pll_p_clk = clk_get_sys(NULL, "pll_p_cclk");
> + if (IS_ERR(pll_p_clk)) {
> + clk = pll_p_clk;
> + goto put_pll_x_clk;
> + }
> +
> + emc_clk = clk_get_sys("cpu", "emc");
> + if (IS_ERR(emc_clk)) {
> + clk = emc_clk;
> + goto put_pll_p_clk;
> + }
> +
> + cpu0->hw.init = &init;
> +
> + init.name = "cpu0";
> + init.ops = &clk_cpu0_ops;
> + init.flags = CLK_IS_ROOT | CLK_GET_RATE_NOCACHE;
> + init.num_parents = 0;
> +
> + clk = clk_register(NULL, &cpu0->hw);
> + if (!IS_ERR(clk))
> + return clk;
> +
> + clk_prepare_enable(emc_clk);
> + clk_prepare_enable(cpu_clk);
> +
> + clk_put(emc_clk);
> +put_pll_p_clk:
> + clk_put(pll_p_clk);
> +put_pll_x_clk:
> + clk_put(pll_x_clk);
> +put_cpu_clk:
> + clk_put(cpu_clk);
> +free_mem:
> + kfree(cpu0);
> +
> + pr_err("%s: clk register failed\n", __func__);
> +
> + return NULL;
> +}
> diff --git a/drivers/clk/tegra/clk-tegra30.c b/drivers/clk/tegra/clk-tegra30.c
> index e2c6ca0..1cabeea 100644
> --- a/drivers/clk/tegra/clk-tegra30.c
> +++ b/drivers/clk/tegra/clk-tegra30.c
> @@ -1396,6 +1396,10 @@ static void __init tegra30_super_clk_init(void)
> CLK_SET_RATE_PARENT, 1, 2);
> clk_register_clkdev(clk, "twd", NULL);
> clks[twd] = clk;
> +
> + /* cpu0 clk for cpufreq driver */
> + clk = tegra_clk_register_cpu0();
> + clk_register_clkdev(clk, NULL, "cpu0");
> }
>
> static const char *mux_pllacp_clkm[] = { "pll_a_out0", "unused", "pll_p",
> diff --git a/include/linux/clk/tegra.h b/include/linux/clk/tegra.h
> index 23a0cee..d416138 100644
> --- a/include/linux/clk/tegra.h
> +++ b/include/linux/clk/tegra.h
> @@ -128,5 +128,6 @@ static inline void tegra_periph_reset_deassert(struct clk *c) {}
> static inline void tegra_periph_reset_assert(struct clk *c) {}
> #endif
> void tegra_clocks_apply_init_table(void);
> +struct clk *tegra_clk_register_cpu0(void);
>
> #endif /* __LINUX_CLK_TEGRA_H_ */
> --
> 1.7.12.rc2.18.g61b472e
next prev parent reply other threads:[~2013-08-07 16:44 UTC|newest]
Thread overview: 75+ messages / expand[flat|nested] mbox.gz Atom feed top
2013-08-07 14:46 [PATCH 0/6] Tegra: Use cpufreq-cpu0 driver Viresh Kumar
2013-08-07 14:46 ` Viresh Kumar
2013-08-07 14:46 ` [PATCH 1/6] clk: Tegra: Add CPU0 clock driver Viresh Kumar
2013-08-07 14:46 ` Viresh Kumar
2013-08-07 16:44 ` Mike Turquette [this message]
2013-08-07 16:44 ` Mike Turquette
2013-08-07 16:44 ` Mike Turquette
2013-08-07 17:38 ` Stephen Warren
2013-08-07 17:38 ` Stephen Warren
2013-08-07 17:45 ` Viresh Kumar
2013-08-07 17:45 ` Viresh Kumar
2013-08-07 17:48 ` Stephen Warren
2013-08-07 17:48 ` Stephen Warren
2013-08-07 17:54 ` Viresh Kumar
2013-08-07 17:54 ` Viresh Kumar
2013-08-07 18:50 ` Stephen Warren
2013-08-07 18:50 ` Stephen Warren
2013-08-08 2:42 ` Viresh Kumar
2013-08-08 2:42 ` Viresh Kumar
2013-08-08 18:50 ` Stephen Warren
2013-08-08 18:50 ` Stephen Warren
2013-08-09 3:19 ` Viresh Kumar
2013-08-09 3:19 ` Viresh Kumar
2013-08-07 14:46 ` [PATCH 2/6] ARM: Tegra: Add CPU's OPPs for using cpufreq-cpu0 driver Viresh Kumar
2013-08-07 14:46 ` Viresh Kumar
2013-08-07 17:42 ` Stephen Warren
2013-08-07 17:42 ` Stephen Warren
2013-08-07 18:06 ` Viresh Kumar
2013-08-07 18:06 ` Viresh Kumar
2013-08-07 18:55 ` Stephen Warren
2013-08-07 18:55 ` Stephen Warren
2013-08-08 2:57 ` Viresh Kumar
2013-08-08 2:57 ` Viresh Kumar
2013-08-08 18:55 ` Stephen Warren
2013-08-08 18:55 ` Stephen Warren
2013-08-08 13:58 ` Lucas Stach
2013-08-08 13:58 ` Lucas Stach
2013-08-08 13:58 ` Lucas Stach
2013-08-08 14:11 ` Viresh Kumar
2013-08-08 14:11 ` Viresh Kumar
2013-08-08 14:22 ` Lucas Stach
2013-08-08 14:22 ` Lucas Stach
2013-08-08 14:37 ` Viresh Kumar
2013-08-08 14:37 ` Viresh Kumar
2013-08-08 15:52 ` Nishanth Menon
2013-08-08 15:52 ` Nishanth Menon
2013-08-08 15:52 ` Nishanth Menon
2013-08-07 14:46 ` [PATCH 3/6] ARM: Tegra: Enable OPP library Viresh Kumar
2013-08-07 14:46 ` Viresh Kumar
2013-08-07 17:43 ` Stephen Warren
2013-08-07 17:43 ` Stephen Warren
2013-08-07 18:08 ` Viresh Kumar
2013-08-07 18:08 ` Viresh Kumar
2013-08-07 14:46 ` [PATCH 4/6] ARM: Tegra: defconfig: select cpufreq-cpu0 driver Viresh Kumar
2013-08-07 14:46 ` Viresh Kumar
2013-08-07 14:46 ` [PATCH 5/6] ARM: Tegra: start using " Viresh Kumar
2013-08-07 14:46 ` Viresh Kumar
2013-08-07 17:46 ` Stephen Warren
2013-08-07 17:46 ` Stephen Warren
2013-08-07 17:49 ` Viresh Kumar
2013-08-07 17:49 ` Viresh Kumar
2013-08-07 17:53 ` Stephen Warren
2013-08-07 17:53 ` Stephen Warren
2013-08-07 17:59 ` Viresh Kumar
2013-08-07 17:59 ` Viresh Kumar
2013-08-07 18:51 ` Stephen Warren
2013-08-07 18:51 ` Stephen Warren
2013-08-08 2:48 ` Viresh Kumar
2013-08-08 2:48 ` Viresh Kumar
2013-08-07 14:46 ` [PATCH 6/6] cpufreq: Tegra: Remove tegra-cpufreq driver Viresh Kumar
2013-08-07 14:46 ` Viresh Kumar
2013-08-08 8:31 ` [PATCH 0/6] Tegra: Use cpufreq-cpu0 driver Richard Zhao
2013-08-08 8:31 ` Richard Zhao
2013-08-08 8:33 ` Viresh Kumar
2013-08-08 8:33 ` Viresh Kumar
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20130807164423.5348.81610@quantum \
--to=mturquette@linaro.org \
--cc=cpufreq@vger.kernel.org \
--cc=linaro-kernel@lists.linaro.org \
--cc=linux-arm-kernel@lists.infradead.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-pm@vger.kernel.org \
--cc=patches@linaro.org \
--cc=rjw@sisk.pl \
--cc=swarren@nvidia.com \
--cc=viresh.kumar@linaro.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.