From patchwork Sat May 2 15:58:31 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dario Binacchi X-Patchwork-Id: 244806 List-Id: U-Boot discussion From: dariobin at libero.it (Dario Binacchi) Date: Sat, 2 May 2020 17:58:31 +0200 Subject: [PATCH 1/4] clk: ccf: mux: change include order In-Reply-To: <20200502155834.27481-1-dariobin@libero.it> References: <20200502155834.27481-1-dariobin@libero.it> Message-ID: <20200502155834.27481-2-dariobin@libero.it> Apply u-boot coding style on include files order. Signed-off-by: Dario Binacchi --- drivers/clk/clk-mux.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/drivers/clk/clk-mux.c b/drivers/clk/clk-mux.c index b9d2ae6778..9511a80fe3 100644 --- a/drivers/clk/clk-mux.c +++ b/drivers/clk/clk-mux.c @@ -22,15 +22,15 @@ */ #include -#include -#include +#include #include #include #include +#include +#include #include -#include -#include "clk.h" #include +#include "clk.h" #define UBOOT_DM_CLK_CCF_MUX "ccf_clk_mux" From patchwork Sat May 2 15:58:32 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dario Binacchi X-Patchwork-Id: 244807 List-Id: U-Boot discussion From: dariobin at libero.it (Dario Binacchi) Date: Sat, 2 May 2020 17:58:32 +0200 Subject: [PATCH 2/4] clk: ccf: mux: fix typo In-Reply-To: <20200502155834.27481-1-dariobin@libero.it> References: <20200502155834.27481-1-dariobin@libero.it> Message-ID: <20200502155834.27481-3-dariobin@libero.it> Close the opening bracket. Signed-off-by: Dario Binacchi --- drivers/clk/clk-mux.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/clk/clk-mux.c b/drivers/clk/clk-mux.c index 9511a80fe3..6264b63900 100644 --- a/drivers/clk/clk-mux.c +++ b/drivers/clk/clk-mux.c @@ -193,7 +193,7 @@ struct clk *clk_hw_register_mux_table(struct device *dev, const char *name, * Read the current mux setup - so we assign correct parent. * * Changing parent would require changing internals of udevice struct - * for the corresponding clock (to do that define .set_parent() method. + * for the corresponding clock (to do that define .set_parent() method). */ ret = clk_register(clk, UBOOT_DM_CLK_CCF_MUX, name, parent_names[clk_mux_get_parent(clk)]); From patchwork Sat May 2 15:58:33 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dario Binacchi X-Patchwork-Id: 244808 List-Id: U-Boot discussion From: dariobin at libero.it (Dario Binacchi) Date: Sat, 2 May 2020 17:58:33 +0200 Subject: [PATCH 3/4] clk: ccf: mux: fix access to the sandbox register In-Reply-To: <20200502155834.27481-1-dariobin@libero.it> References: <20200502155834.27481-1-dariobin@libero.it> Message-ID: <20200502155834.27481-4-dariobin@libero.it> The tests developed for the mux clock are run on the sandbox. They don't call the clk_mux_set_parent routine and therefore they do not detect this error. Signed-off-by: Dario Binacchi --- drivers/clk/clk-mux.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/clk/clk-mux.c b/drivers/clk/clk-mux.c index 6264b63900..8f85e84ae9 100644 --- a/drivers/clk/clk-mux.c +++ b/drivers/clk/clk-mux.c @@ -134,12 +134,20 @@ static int clk_mux_set_parent(struct clk *clk, struct clk *parent) if (mux->flags & CLK_MUX_HIWORD_MASK) { reg = mux->mask << (mux->shift + 16); } else { +#if CONFIG_IS_ENABLED(SANDBOX_CLK_CCF) + reg = mux->io_mux_val; +#else reg = readl(mux->reg); +#endif reg &= ~(mux->mask << mux->shift); } val = val << mux->shift; reg |= val; +#if CONFIG_IS_ENABLED(SANDBOX_CLK_CCF) + mux->io_mux_val = reg; +#else writel(reg, mux->reg); +#endif return 0; } From patchwork Sat May 2 15:58:34 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dario Binacchi X-Patchwork-Id: 244809 List-Id: U-Boot discussion From: dariobin at libero.it (Dario Binacchi) Date: Sat, 2 May 2020 17:58:34 +0200 Subject: [PATCH 4/4] clk: ccf: mux: change the get_rate helper In-Reply-To: <20200502155834.27481-1-dariobin@libero.it> References: <20200502155834.27481-1-dariobin@libero.it> Message-ID: <20200502155834.27481-5-dariobin@libero.it> The previous version of the get_rate helper does not work if the mux clock parent is changed after the probe. This error has not been detected because this condition has not been tested. The error occurs because the set_parent helper does not change the parent of the clock device but only the clock selection register. Since changing the parent of a probed device can be tricky, the new version of the get_rate helper provides the rate of the selected clock and not that of the parent. Signed-off-by: Dario Binacchi Reviewed-by: Simon Glass --- drivers/clk/clk-mux.c | 26 +++++++++++++++++++++++++- test/dm/clk_ccf.c | 24 ++++++++++++++++++++++++ 2 files changed, 49 insertions(+), 1 deletion(-) diff --git a/drivers/clk/clk-mux.c b/drivers/clk/clk-mux.c index 8f85e84ae9..1f2dab647f 100644 --- a/drivers/clk/clk-mux.c +++ b/drivers/clk/clk-mux.c @@ -152,8 +152,32 @@ static int clk_mux_set_parent(struct clk *clk, struct clk *parent) return 0; } +static ulong clk_mux_get_rate(struct clk *clk) +{ + struct clk_mux *mux = to_clk_mux(clk_dev_binded(clk) ? + dev_get_clk_ptr(clk->dev) : clk); + struct udevice *parent; + struct clk *pclk; + int err, index; + + index = clk_mux_get_parent(clk); + if (index >= mux->num_parents) + return -EFAULT; + + err = uclass_get_device_by_name(UCLASS_CLK, mux->parent_names[index], + &parent); + if (err) + return err; + + pclk = dev_get_clk_ptr(parent); + if (!pclk) + return -ENODEV; + + return clk_get_rate(pclk); +} + const struct clk_ops clk_mux_ops = { - .get_rate = clk_generic_get_rate, + .get_rate = clk_mux_get_rate, .set_parent = clk_mux_set_parent, }; diff --git a/test/dm/clk_ccf.c b/test/dm/clk_ccf.c index ae3a4d8a76..bf99776ac1 100644 --- a/test/dm/clk_ccf.c +++ b/test/dm/clk_ccf.c @@ -46,6 +46,18 @@ static int dm_test_clk_ccf(struct unit_test_state *uts) rate = clk_get_parent_rate(clk); ut_asserteq(rate, 60000000); + rate = clk_get_rate(clk); + ut_asserteq(rate, 60000000); + + ret = clk_get_by_id(SANDBOX_CLK_PLL3_80M, &pclk); + ut_assertok(ret); + + ret = clk_set_parent(clk, pclk); + ut_assertok(ret); + + rate = clk_get_rate(clk); + ut_asserteq(rate, 80000000); + ret = clk_get_by_id(SANDBOX_CLK_USDHC2_SEL, &clk); ut_assertok(ret); ut_asserteq_str("usdhc2_sel", clk->dev->name); @@ -56,6 +68,18 @@ static int dm_test_clk_ccf(struct unit_test_state *uts) pclk = clk_get_parent(clk); ut_asserteq_str("pll3_80m", pclk->dev->name); + rate = clk_get_rate(clk); + ut_asserteq(rate, 80000000); + + ret = clk_get_by_id(SANDBOX_CLK_PLL3_60M, &pclk); + ut_assertok(ret); + + ret = clk_set_parent(clk, pclk); + ut_assertok(ret); + + rate = clk_get_rate(clk); + ut_asserteq(rate, 60000000); + /* Test the composite of CCF */ ret = clk_get_by_id(SANDBOX_CLK_I2C, &clk); ut_assertok(ret);