lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [day] [month] [year] [list]
Date: Sun, 23 Jun 2024 23:09:08 +0200
From: Martin Blumenstingl <martin.blumenstingl@...glemail.com>
To: Uwe Kleine-König <u.kleine-koenig@...libre.com>
Cc: linux-pwm@...r.kernel.org, linux-kernel@...r.kernel.org, 
	broonie@...nel.org, lgirdwood@...il.com
Subject: Re: [RFC PATCH v2] regulator: pwm-regulator: Make assumptions about
 disabled PWM consistent

Hello Uwe,

On Sun, Jun 23, 2024 at 11:32 AM Uwe Kleine-König
<u.kleine-koenig@...libre.com> wrote:
>
> Hello Martin,
>
> On Sat, Jun 22, 2024 at 09:15:04PM +0200, Martin Blumenstingl wrote:
> > Generally it's not known how a disabled PWM behaves. However if the
> > bootloader hands over a disabled PWM that drives a regulator and it's
> > claimed the regulator is enabled, then the most likely assumption is
> > that the PWM emits the inactive level. This is represented by duty_cycle
> > = 0 even for .polarity == PWM_POLARITY_INVERSED.
>
> I'd write: "This is represented by duty_cycle = 0 independent of the
> polarity."
That makes things easier - I'll apply this, thank you!

> > Change the implementation to always use duty_cycle = 0, regardless of
> > the polarity. Also update the code so it keeps a copy of the pwm_state
> > around. Both of these changes result in the fact that the logic from
> > pwm_regulator_init_boot_on() is much less complex and can be simplified
> > to a point where the whole function is not needed anymore.
>
> In my (German) ear the following sounds a bit nicer:
>
>         Both of these changes reduce the complexity of
>         pwm_regulator_init_boot_on() to a point where the whole function
>         is not needed anymore.
Sounds fine to my (German) ear as well - thanks!

> > Suggested-by: Uwe Kleine-König <u.kleine-koenig@...libre.com>
> > Signed-off-by: Martin Blumenstingl <martin.blumenstingl@...glemail.com>
> > ---
> > Changes from v1 [0] (which was sent by Uwe):
> > - keep the struct pwm_state around to prevent a regression on Meson8b
> >   Odroid-C1 boards where just calling pwm_enable() without adjusting
> >   the duty_cycle to 0 would hang the board
> > - I'm actively looking for input on the commit description and
> >   suggestions whether/why Fixes tags should be applied
>
> Apart of the nitpicking above, I like the commit description.
>
> Regarding a Fixes tag: I'm unsure if without this patch, the
> pwm-regulator driver is broken for your Odroid-C1 board. It's not,
> right?
> I think I wouldn't add a Fixes tag and just consider this patch a
> cleanup then.
My Odroid-C1 works fine with and without this patch.
Only the patch that you found previously which you wanted to improve
is required (and reverting it breaks boot).

[...]
> > -     ret = pwm_apply_might_sleep(drvdata->pwm, &pstate);
> > -     if (ret) {
> > -             dev_err(&rdev->dev, "Failed to configure PWM: %d\n", ret);
> > +     ret = pwm_regulator_apply_state(rdev, &pstate);
> > +     if (ret)
> >               return ret;
> > -     }
>
> If you drop the local variable pstate and just do
>
>         pwm_set_relative_duty_cycle(drvdata->pwm_state,
>                                 drvdata->duty_cycle_table[selector].dutycycle, 100);
>
> you might get a mismatch between actual configuration and
> drvdata->pwm_state if pwm_regulator_apply_state() fails, but I think
> that doesn't matter and simplifies the code a bit. (Drop the assignment
> in pwm_regulator_apply_state() then.)
If you're fine with this potential mismatch (I am - I just was unsure
about potential side-effects) then you're right: this is an
improvement!

> >       drvdata->state = selector;
> >
> > @@ -115,17 +129,26 @@ static int pwm_regulator_list_voltage(struct regulator_dev *rdev,
> >  static int pwm_regulator_enable(struct regulator_dev *dev)
> >  {
> >       struct pwm_regulator_data *drvdata = rdev_get_drvdata(dev);
> > +     struct pwm_state pstate = drvdata->pwm_state;
> >
> >       gpiod_set_value_cansleep(drvdata->enb_gpio, 1);
> >
> > -     return pwm_enable(drvdata->pwm);
> > +     pstate.enabled = true;
> > +
> > +     return pwm_regulator_apply_state(dev, &pstate);
> >  }
> >
> >  static int pwm_regulator_disable(struct regulator_dev *dev)
> >  {
> >       struct pwm_regulator_data *drvdata = rdev_get_drvdata(dev);
> > +     struct pwm_state pstate = drvdata->pwm_state;
> > +     int ret;
> > +
> > +     pstate.enabled = false;
> >
> > -     pwm_disable(drvdata->pwm);
> > +     ret = pwm_regulator_apply_state(dev, &pstate);
> > +     if (ret)
> > +             return ret;
>
> With that part I'm a bit unhappy. You don't know what the pwm does when
> disabled (it might yield a 100% relative duty cycle). So the safe bet is
> to use .enabled=true, .duty_cycle=0 here.
>
> The only code that "knows" if it's safe to disable the PWM is the
> lowlevel pwm driver.
Here I don't know the regulator framework enough. Let's make two assumptions:
1. the optimization you suggest is implemented (I'm not against it,
it's just different from what pwm_disable() does)
2. regulator core does not expect the set voltage to change in a
.disable() callback

In that case disabling the PWM output is fine. Since we're now
updating the cached pwm_state with duty_cycle = 0 the next time the
regulator core calls the .enable() callback (without calling
.set_voltage() between disabling and enabling) we end up enabling the
PWM output with duty_cycle = 0 (and thus likely changing the voltage
output).
I see three options here:
- my assumption about the regulator core is incorrect, then your
optimization works just fine
- we only write enabled = false to the cached pwm_state but not duty_cycle = 0
- we drop the suggested optimization here (and maybe let PWM core handle this)

What do you think?


Best regards,
Martin

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ