2017-12-21 23:39:33

by Stephen Boyd

[permalink] [raw]
Subject: Re: [PATCH v6 4/5] clk: aspeed: Register gated clocks

On 11/28, Joel Stanley wrote:
> diff --git a/drivers/clk/clk-aspeed.c b/drivers/clk/clk-aspeed.c
> index 839243691b26..b5dc3e298693 100644
> --- a/drivers/clk/clk-aspeed.c
> +++ b/drivers/clk/clk-aspeed.c
> @@ -202,6 +202,107 @@ static const struct aspeed_clk_soc_data ast2400_data = {
> .calc_pll = aspeed_ast2400_calc_pll,
> };
>
> +static int aspeed_clk_enable(struct clk_hw *hw)
> +{
> + struct aspeed_clk_gate *gate = to_aspeed_clk_gate(hw);
> + unsigned long flags;
> + u32 clk = BIT(gate->clock_idx);
> + u32 rst = BIT(gate->reset_idx);
> +
> + spin_lock_irqsave(gate->lock, flags);
> +
> + if (gate->reset_idx >= 0) {
> + /* Put IP in reset */
> + regmap_update_bits(gate->map, ASPEED_RESET_CTRL, rst, rst);
> +
> + /* Delay 100us */
> + udelay(100);
> + }
> +
> + /* Enable clock */
> + regmap_update_bits(gate->map, ASPEED_CLK_STOP_CTRL, clk, 0);
> +
> + if (gate->reset_idx >= 0) {
> + /* Delay 10ms */
> + /* TODO: can we sleep here? */
> + msleep(10);

No you can't sleep here. It needs to delay because this is inside
spinlock_irqsave.

> +
> + /* Take IP out of reset */
> + regmap_update_bits(gate->map, ASPEED_RESET_CTRL, rst, 0);
> + }
> +
> + spin_unlock_irqrestore(gate->lock, flags);
> +
> + return 0;
> +}

--
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum,
a Linux Foundation Collaborative Project


2017-12-22 04:03:48

by Benjamin Herrenschmidt

[permalink] [raw]
Subject: Re: [PATCH v6 4/5] clk: aspeed: Register gated clocks

On Fri, 2017-12-22 at 13:36 +1100, Benjamin Herrenschmidt wrote:
>
> > No you can't sleep here. It needs to delay because this is inside
> > spinlock_irqsave.
>
> Additionally you really don't want to delay for 10ms with interrupts
> off :-(
>
> Sadly, it looks like the clk framework already calls you with spinlock
> irqsafe, which is a rather major suckage.
>
> Stephen, why is that so ? That pretty much makes it impossible to
> do sleeping things, which prevents things like i2c based clock
> controllers etc...

I noticed we do have a few i2c based clock drivers... how are they ever
supposed to work ? i2c bus controllers are allowed to sleep and the i2c
core takes mutexes...

> I think the clk framework needs to be overhauled to use sleeping
> mutexes instead. Doing clock enable/disable at interrupt time is
> a bad idea anyway.
>
>
> In the meantime, Joel, you have little choice but do an mdelay
> though that really sucks.
>
> > > + /* Take IP out of reset */
> > > + regmap_update_bits(gate->map, ASPEED_RESET_CTRL, rst, 0);
> > > + }
> > > +
> > > + spin_unlock_irqrestore(gate->lock, flags);
> > > +
> > > + return 0;
> > > +}


2017-12-22 06:50:32

by Benjamin Herrenschmidt

[permalink] [raw]
Subject: Re: [PATCH v6 4/5] clk: aspeed: Register gated clocks

On Thu, 2017-12-21 at 15:39 -0800, Stephen Boyd wrote:
> On 11/28, Joel Stanley wrote:
> > diff --git a/drivers/clk/clk-aspeed.c b/drivers/clk/clk-aspeed.c
> > index 839243691b26..b5dc3e298693 100644
> > --- a/drivers/clk/clk-aspeed.c
> > +++ b/drivers/clk/clk-aspeed.c
> > @@ -202,6 +202,107 @@ static const struct aspeed_clk_soc_data ast2400_data = {
> > .calc_pll = aspeed_ast2400_calc_pll,
> > };
> >
> > +static int aspeed_clk_enable(struct clk_hw *hw)
> > +{
> > + struct aspeed_clk_gate *gate = to_aspeed_clk_gate(hw);
> > + unsigned long flags;
> > + u32 clk = BIT(gate->clock_idx);
> > + u32 rst = BIT(gate->reset_idx);
> > +
> > + spin_lock_irqsave(gate->lock, flags);
> > +
> > + if (gate->reset_idx >= 0) {
> > + /* Put IP in reset */
> > + regmap_update_bits(gate->map, ASPEED_RESET_CTRL, rst, rst);
> > +
> > + /* Delay 100us */
> > + udelay(100);
> > + }
> > +
> > + /* Enable clock */
> > + regmap_update_bits(gate->map, ASPEED_CLK_STOP_CTRL, clk, 0);
> > +
> > + if (gate->reset_idx >= 0) {
> > + /* Delay 10ms */
> > + /* TODO: can we sleep here? */
> > + msleep(10);
>
> No you can't sleep here. It needs to delay because this is inside
> spinlock_irqsave.

Additionally you really don't want to delay for 10ms with interrupts
off :-(

Sadly, it looks like the clk framework already calls you with spinlock
irqsafe, which is a rather major suckage.

Stephen, why is that so ? That pretty much makes it impossible to
do sleeping things, which prevents things like i2c based clock
controllers etc...

I think the clk framework needs to be overhauled to use sleeping
mutexes instead. Doing clock enable/disable at interrupt time is
a bad idea anyway.


In the meantime, Joel, you have little choice but do an mdelay
though that really sucks.

> > + /* Take IP out of reset */
> > + regmap_update_bits(gate->map, ASPEED_RESET_CTRL, rst, 0);
> > + }
> > +
> > + spin_unlock_irqrestore(gate->lock, flags);
> > +
> > + return 0;
> > +}

2017-12-27 01:32:30

by Stephen Boyd

[permalink] [raw]
Subject: Re: [PATCH v6 4/5] clk: aspeed: Register gated clocks

On 12/22, Benjamin Herrenschmidt wrote:
> On Fri, 2017-12-22 at 13:36 +1100, Benjamin Herrenschmidt wrote:
> >
> > > No you can't sleep here. It needs to delay because this is inside
> > > spinlock_irqsave.
> >
> > Additionally you really don't want to delay for 10ms with interrupts
> > off :-(
> >
> > Sadly, it looks like the clk framework already calls you with spinlock
> > irqsafe, which is a rather major suckage.
> >
> > Stephen, why is that so ? That pretty much makes it impossible to
> > do sleeping things, which prevents things like i2c based clock
> > controllers etc...
>
> I noticed we do have a few i2c based clock drivers... how are they ever
> supposed to work ? i2c bus controllers are allowed to sleep and the i2c
> core takes mutexes...

We have clk_prepare()/clk_unprepare() for sleeping suckage. You
can use that, and i2c based clk drivers do that today.

--
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum,
a Linux Foundation Collaborative Project

2017-12-29 23:20:55

by Benjamin Herrenschmidt

[permalink] [raw]
Subject: Re: [PATCH v6 4/5] clk: aspeed: Register gated clocks

On Tue, 2017-12-26 at 17:32 -0800, Stephen Boyd wrote:
> > I noticed we do have a few i2c based clock drivers... how are they ever
> > supposed to work ? i2c bus controllers are allowed to sleep and the i2c
> > core takes mutexes...
>
> We have clk_prepare()/clk_unprepare() for sleeping suckage. You
> can use that, and i2c based clk drivers do that today.

"suckage" ? Hehe ... the suckage should rather be stuff that cannot
sleep. Arbitrary latencies and jitter caused by too much code wanting
to be "atomic" when unnecessary are a bad thing.

In the case of clocks like the aspeed where we have to wait for a
rather long stabilization delay, way too long to legitimately do a non-
sleepable delay with a lock held, do we need to do everything in
prepare() then ?

Ben.

2018-01-02 05:47:57

by Benjamin Herrenschmidt

[permalink] [raw]
Subject: Re: [PATCH v6 4/5] clk: aspeed: Register gated clocks

On Sat, 2017-12-30 at 09:03 +1100, Benjamin Herrenschmidt wrote:
> On Tue, 2017-12-26 at 17:32 -0800, Stephen Boyd wrote:
> > > I noticed we do have a few i2c based clock drivers... how are they ever
> > > supposed to work ? i2c bus controllers are allowed to sleep and the i2c
> > > core takes mutexes...
> >
> > We have clk_prepare()/clk_unprepare() for sleeping suckage. You
> > can use that, and i2c based clk drivers do that today.
>
> "suckage" ? Hehe ... the suckage should rather be stuff that cannot
> sleep. Arbitrary latencies and jitter caused by too much code wanting
> to be "atomic" when unnecessary are a bad thing.
>
> In the case of clocks like the aspeed where we have to wait for a
> rather long stabilization delay, way too long to legitimately do a non-
> sleepable delay with a lock held, do we need to do everything in
> prepare() then ?

BTW. Pls don't hold Joel's patches for this. Without that clk framework
a lot of the aspeed stuff already upstream doesn't actually work
without additional out-of-tree hacks or uboot black magic.

We can sort out the sleeping issues (and possibly move to using prepare
for the clocks that have that delay requirement) via subsequent
improvements.

Cheers,
Ben.


2018-01-02 18:16:11

by Stephen Boyd

[permalink] [raw]
Subject: Re: [PATCH v6 4/5] clk: aspeed: Register gated clocks

On 12/30, Benjamin Herrenschmidt wrote:
> On Tue, 2017-12-26 at 17:32 -0800, Stephen Boyd wrote:
> > > I noticed we do have a few i2c based clock drivers... how are they ever
> > > supposed to work ? i2c bus controllers are allowed to sleep and the i2c
> > > core takes mutexes...
> >
> > We have clk_prepare()/clk_unprepare() for sleeping suckage. You
> > can use that, and i2c based clk drivers do that today.
>
> "suckage" ? Hehe ... the suckage should rather be stuff that cannot
> sleep. Arbitrary latencies and jitter caused by too much code wanting
> to be "atomic" when unnecessary are a bad thing.

Heh. Of course.

>
> In the case of clocks like the aspeed where we have to wait for a
> rather long stabilization delay, way too long to legitimately do a non-
> sleepable delay with a lock held, do we need to do everything in
> prepare() then ?
>

Yes. If we have to wait a long time in the enable path it makes
sense to move it to the prepare path instead, if possible. That
way we avoid holding a spinlock for a long time.

--
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum,
a Linux Foundation Collaborative Project