linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
From: tomasz.figa@gmail.com (Tomasz Figa)
To: linux-arm-kernel@lists.infradead.org
Subject: [PATCH v2 3/6] clk: samsung: add plls used in s3c2416 and s3c2443
Date: Thu, 11 Jul 2013 11:25:47 +0200	[thread overview]
Message-ID: <10485562.994mEYPTEH@thinkpad> (raw)
In-Reply-To: <201307111050.39878.heiko@sntech.de>

On Thursday 11 of July 2013 10:50:39 Heiko St?bner wrote:
> Am Donnerstag, 11. Juli 2013, 10:16:41 schrieb Tomasz Figa:
> > Hi Heiko,
> > 
> > On Wednesday 10 of July 2013 00:59:08 Heiko St?bner wrote:
> > > This adds support for pll2126x, pll3000x, pll6552x and pll6553x.
> > > 
> > > Signed-off-by: Heiko Stuebner <heiko@sntech.de>
> > > ---
> > > 
> > >  drivers/clk/samsung/clk-pll.c |  280
> > > 
> > > +++++++++++++++++++++++++++++++++++++++++ drivers/clk/samsung/clk-pll.h
> > > |
> > > 
> > >  8 ++
> > >  2 files changed, 288 insertions(+)
> > 
> > Generally the patch looks good, but I have some comments to the part
> > related to 655xx PLLs.
> > 
> > I had a patch adding support for them too, but we can go with yours, since
> > the way of registration has been changed by Yadwinder's patches and mine
> > would have to be updated anyway.
> > 
> > > diff --git a/drivers/clk/samsung/clk-pll.c
> > > b/drivers/clk/samsung/clk-pll.c index 0afaec6..35c15a1 100644
> > > --- a/drivers/clk/samsung/clk-pll.c
> > > +++ b/drivers/clk/samsung/clk-pll.c
> > > @@ -323,6 +323,73 @@ struct clk * __init
> > > samsung_clk_register_pll46xx(const char *name, }
> > > 
> > >  /*
> > > 
> > > + * PLL2126x Clock Type
> > > + */
> > > +
> > > +#define PLL2126X_MDIV_MASK	(0xFF)
> > > +#define PLL2126X_PDIV_MASK	(0x3)
> > > +#define PLL2126X_SDIV_MASK	(0x3)
> > > +#define PLL2126X_MDIV_SHIFT	(16)
> > > +#define PLL2126X_PDIV_SHIFT	(8)
> > > +#define PLL2126X_SDIV_SHIFT	(0)
> 
> +#define PLL2126X_PDIV_MASK	(0x3F)
> 
> is the correct value.
> 
> > > +
> > > +struct samsung_clk_pll2126x {
> > > +	struct clk_hw		hw;
> > > +	const void __iomem	*con_reg;
> > > +};
> > > +
> > > +#define to_clk_pll2126x(_hw) container_of(_hw, struct
> > > samsung_clk_pll2126x, hw) +
> > > +static unsigned long samsung_pll2126x_recalc_rate(struct clk_hw *hw,
> > > +				unsigned long parent_rate)
> > > +{
> > > +	struct samsung_clk_pll2126x *pll = to_clk_pll2126x(hw);
> > > +	u32 pll_con, mdiv, pdiv, sdiv;
> > > +	u64 fvco = parent_rate;
> > > +
> > > +	pll_con = __raw_readl(pll->con_reg);
> > > +	mdiv = (pll_con >> PLL2126X_MDIV_SHIFT) & PLL2126X_MDIV_MASK;
> > > +	pdiv = (pll_con >> PLL2126X_PDIV_SHIFT) & PLL2126X_PDIV_MASK;
> > > +	sdiv = (pll_con >> PLL2126X_SDIV_SHIFT) & PLL2126X_SDIV_MASK;
> > > +
> > > +	fvco *= (mdiv + 8);
> > > +	do_div(fvco, (pdiv + 2) << sdiv);
> > > +
> > > +	return (unsigned long)fvco;
> > > +}
> > > +
> > > +static const struct clk_ops samsung_pll2126x_clk_ops = {
> > > +	.recalc_rate = samsung_pll2126x_recalc_rate,
> > > +};
> > > +
> > > +struct clk * __init samsung_clk_register_pll2126x(const char *name,
> > > +			const char *pname, const void __iomem *con_reg)
> > > +{
> > > +	struct samsung_clk_pll2126x *pll;
> > > +	struct clk *clk;
> > > +	struct clk_init_data init;
> > > +
> > > +	pll = kzalloc(sizeof(*pll), GFP_KERNEL);
> > > +	if (!pll)
> > > +		return ERR_PTR(-ENOMEM);
> > > +
> > > +	init.name = name;
> > > +	init.ops = &samsung_pll2126x_clk_ops;
> > > +	init.flags = CLK_GET_RATE_NOCACHE;
> > > +	init.parent_names = &pname;
> > > +	init.num_parents = 1;
> > > +
> > > +	pll->hw.init = &init;
> > > +	pll->con_reg = con_reg;
> > > +
> > > +	clk = samsung_register_pll(&pll->hw);
> > > +	if (IS_ERR(clk))
> > > +		kfree(pll);
> > > +
> > > +	return clk;
> > > +}
> > > +
> > > +/*
> > > 
> > >   * PLL2550x Clock Type
> > >   */
> > > 
> > > @@ -396,3 +463,216 @@ struct clk * __init
> > > samsung_clk_register_pll2550x(const char *name,
> > > 
> > >  	return clk;
> > >  
> > >  }
> > > 
> > > +
> > > +/*
> > > + * PLL3000x Clock Type
> > > + */
> > > +
> > > +#define PLL3000X_MDIV_MASK	(0xFF)
> > > +#define PLL3000X_PDIV_MASK	(0x3)
> > > +#define PLL3000X_SDIV_MASK	(0x3)
> > > +#define PLL3000X_MDIV_SHIFT	(16)
> > > +#define PLL3000X_PDIV_SHIFT	(8)
> > > +#define PLL3000X_SDIV_SHIFT	(0)
> 
> these are correct.
> 
> > > +
> > > +struct samsung_clk_pll3000x {
> > > +	struct clk_hw		hw;
> > > +	const void __iomem	*con_reg;
> > > +};
> > > +
> > > +#define to_clk_pll3000x(_hw) container_of(_hw, struct
> > > samsung_clk_pll3000x, hw) +
> > > +static unsigned long samsung_pll3000x_recalc_rate(struct clk_hw *hw,
> > > +				unsigned long parent_rate)
> > > +{
> > > +	struct samsung_clk_pll3000x *pll = to_clk_pll3000x(hw);
> > > +	u32 pll_con, mdiv, pdiv, sdiv;
> > > +	u64 fvco = parent_rate;
> > > +
> > > +	pll_con = __raw_readl(pll->con_reg);
> > > +	mdiv = (pll_con >> PLL3000X_MDIV_SHIFT) & PLL3000X_MDIV_MASK;
> > > +	pdiv = (pll_con >> PLL3000X_PDIV_SHIFT) & PLL3000X_PDIV_MASK;
> > > +	sdiv = (pll_con >> PLL3000X_SDIV_SHIFT) & PLL3000X_SDIV_MASK;
> > > +
> > > +	fvco *= (2 * (mdiv + 8));
> > > +	do_div(fvco, pdiv << sdiv);
> > > +
> > > +	return (unsigned long)fvco;
> > > +}
> > > +
> > > +static const struct clk_ops samsung_pll3000x_clk_ops = {
> > > +	.recalc_rate = samsung_pll3000x_recalc_rate,
> > > +};
> > > +
> > > +struct clk * __init samsung_clk_register_pll3000x(const char *name,
> > > +			const char *pname, const void __iomem *con_reg)
> > > +{
> > > +	struct samsung_clk_pll3000x *pll;
> > > +	struct clk *clk;
> > > +	struct clk_init_data init;
> > > +
> > > +	pll = kzalloc(sizeof(*pll), GFP_KERNEL);
> > > +	if (!pll)
> > > +		return ERR_PTR(-ENOMEM);
> > > +
> > > +	init.name = name;
> > > +	init.ops = &samsung_pll3000x_clk_ops;
> > > +	init.flags = CLK_GET_RATE_NOCACHE;
> > > +	init.parent_names = &pname;
> > > +	init.num_parents = 1;
> > > +
> > > +	pll->hw.init = &init;
> > > +	pll->con_reg = con_reg;
> > > +
> > > +	clk = samsung_register_pll(&pll->hw);
> > > +	if (IS_ERR(clk))
> > > +		kfree(pll);
> > > +
> > > +	return clk;
> > > +}
> > > +
> > > +/*
> > > + * PLL6552x Clock Type
> > > + */
> > > +
> > > +#define PLL6552X_MDIV_MASK	(0x3FF)
> > > +#define PLL6552X_PDIV_MASK	(0x3F)
> > > +#define PLL6552X_SDIV_MASK	(0x7)
> > > +#define PLL6552X_MDIV_SHIFT	(14)
> > > +#define PLL6552X_PDIV_SHIFT	(5)
> > > +#define PLL6552X_SDIV_SHIFT	(0)
> > 
> > Are you sure about those bitfields?
> > 
> > In S3C6410 User's Manual they are different. You can look at my patch for
> > a
> > comparison:
> > 
> > http://thread.gmane.org/gmane.linux.usb.general/87571/focus=88344
> 
> The numbers where taken from the previous pll code, but I now again checked
> them against the datasheet of the s3c2416 and the s3c2450.
> 
> When comparing with your patch, it really seems that the bit offsets in the
> register are different for the pdiv and mdiv - the above values are correct
> according the the datasheet (and also produce the expected results in the
> clock tree).

> > > +struct samsung_clk_pll6552x {
> > > +	struct clk_hw		hw;
> > > +	const void __iomem	*con_reg;
> > > +};
> > > +
> > > +#define to_clk_pll6552x(_hw) container_of(_hw, struct
> > > samsung_clk_pll6552x, hw) +
> > > +static unsigned long samsung_pll6552x_recalc_rate(struct clk_hw *hw,
> > > +				unsigned long parent_rate)
> > > +{
> > > +	struct samsung_clk_pll6552x *pll = to_clk_pll6552x(hw);
> > > +	u32 pll_con, mdiv, pdiv, sdiv;
> > > +	u64 fvco = parent_rate;
> > > +
> > > +	pll_con = __raw_readl(pll->con_reg);
> > > +	mdiv = (pll_con >> PLL6552X_MDIV_SHIFT) & PLL6552X_MDIV_MASK;
> > > +	pdiv = (pll_con >> PLL6552X_PDIV_SHIFT) & PLL6552X_PDIV_MASK;
> > > +	sdiv = (pll_con >> PLL6552X_SDIV_SHIFT) & PLL6552X_SDIV_MASK;
> > > +
> > > +	fvco *= mdiv;
> > > +	do_div(fvco, (pdiv << sdiv));
> > > +
> > > +	return (unsigned long)fvco;
> > > +}
> > > +
> > > +static const struct clk_ops samsung_pll6552x_clk_ops = {
> > > +	.recalc_rate = samsung_pll6552x_recalc_rate,
> > > +};
> > > +
> > > +struct clk * __init samsung_clk_register_pll6552x(const char *name,
> > > +			const char *pname, const void __iomem *con_reg)
> > > +{
> > > +	struct samsung_clk_pll6552x *pll;
> > > +	struct clk *clk;
> > > +	struct clk_init_data init;
> > > +
> > > +	pll = kzalloc(sizeof(*pll), GFP_KERNEL);
> > > +	if (!pll)
> > > +		return ERR_PTR(-ENOMEM);
> > > +
> > > +	init.name = name;
> > > +	init.ops = &samsung_pll6552x_clk_ops;
> > > +	init.flags = CLK_GET_RATE_NOCACHE;
> > > +	init.parent_names = &pname;
> > > +	init.num_parents = 1;
> > > +
> > > +	pll->hw.init = &init;
> > > +	pll->con_reg = con_reg;
> > > +
> > > +	clk = samsung_register_pll(&pll->hw);
> > > +	if (IS_ERR(clk))
> > > +		kfree(pll);
> > > +
> > > +	return clk;
> > > +}
> > > +
> > > +/*
> > > + * PLL6553x Clock Type
> > > + */
> > > +
> > > +#define PLL6553X_MDIV_MASK	(0x7F)
> > > +#define PLL6553X_PDIV_MASK	(0x1F)
> > > +#define PLL6553X_SDIV_MASK	(0x3)
> > > +#define PLL6553X_KDIV_MASK	(0xFFFF)
> > > +#define PLL6553X_MDIV_SHIFT	(16)
> > > +#define PLL6553X_PDIV_SHIFT	(8)
> > > +#define PLL6553X_SDIV_SHIFT	(0)
> > 
> > Same about those bitfields. They seem to be different on S3C64xx.
> 
> Here it seems the values were off in the original code. According to the
> datasheet the values in your patch are correct. Thanks for the catch.
> 
> +#define PLL6553X_MDIV_MASK	(0xFF)
> +#define PLL6553X_PDIV_MASK	(0x3F)
> +#define PLL6553X_SDIV_MASK	(0x7)
> 
> 
> This leaves the problem on what to do with the 6552X and its different bit
> offsets. Is the pll in question really a 6552X? In the s3c2416 manual its
> name is explicitly stated.

So is it in S3C6410 User's Manual.

If you look at the old plat/pll.h header, you can see that none of S3C2416_PLL 
(which I believe corresponds to your 6552X) and S3C6400_PLL (which is the 
PLL6552x that can be found on S3C64xx) is labelled as PLL6552x explicitly.

Best regards,
Tomasz

  reply	other threads:[~2013-07-11  9:25 UTC|newest]

Thread overview: 23+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-07-09 22:57 [PATCH v2 0/6] Convert S3C2416 ad S3C2443 to common clock framework Heiko Stübner
2013-07-09 22:57 ` [PATCH v2 1/6] clk: samsung: move common plls registration into separate function Heiko Stübner
2013-07-10 16:59   ` Yadwinder Singh Brar
2013-07-11  7:46     ` Tomasz Figa
2013-07-11  8:52       ` Heiko Stübner
2013-08-02 21:35         ` Mike Turquette
2013-07-09 22:58 ` [PATCH v2 2/6] clk: samsung: fix error handling in pll register functions Heiko Stübner
2013-07-11  7:50   ` Tomasz Figa
2013-07-09 22:59 ` [PATCH v2 3/6] clk: samsung: add plls used in s3c2416 and s3c2443 Heiko Stübner
2013-07-11  8:16   ` Tomasz Figa
2013-07-11  8:50     ` Heiko Stübner
2013-07-11  9:25       ` Tomasz Figa [this message]
2013-07-09 22:59 ` [PATCH v2 4/6] ARM: S3C24XX: enable legacy clock code only when SAMSUNG_CLOCK selected Heiko Stübner
2013-07-09 23:00 ` [PATCH v2 5/6] clk: samsung: add clock-driver for s3c2416, s3c2443 and s3c2450 Heiko Stübner
2013-07-11  9:13   ` Tomasz Figa
2013-07-09 23:00 ` [PATCH v2 6/6] ARM: S3C24XX: Convert s3c2416 and s3c2443 to common clock framework Heiko Stübner
2013-07-16  7:09   ` Kukjin Kim
2013-07-22 17:07     ` Tomasz Figa
2013-07-24 12:59       ` Kukjin Kim
2013-07-24 14:01         ` Tomasz Figa
2013-08-05 17:03       ` Kukjin Kim
2013-07-10  8:47 ` [PATCH v2 0/6] Convert S3C2416 ad S3C2443 " Thomas Abraham
2013-08-05 17:05 ` Kukjin Kim

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=10485562.994mEYPTEH@thinkpad \
    --to=tomasz.figa@gmail.com \
    --cc=linux-arm-kernel@lists.infradead.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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).