On Mon, 9 Sep 2019 11:57:29 +0100 Daniel Thompson <daniel.thompson@xxxxxxxxxx> wrote: > On Sun, Sep 08, 2019 at 10:37:03PM +0200, Andreas Kemnade wrote: > > For now just enable it in the probe function to allow i2c > > access and disable it on remove. Disabling also means resetting > > the register values to default. > > > > Tested on Kobo Clara HD. > > > > Signed-off-by: Andreas Kemnade <andreas@xxxxxxxxxxxx> > > --- > > drivers/video/backlight/lm3630a_bl.c | 18 ++++++++++++++++++ > > 1 file changed, 18 insertions(+) > > > > diff --git a/drivers/video/backlight/lm3630a_bl.c b/drivers/video/backlight/lm3630a_bl.c > > index b04b35d007a2..3b45a1733198 100644 > > --- a/drivers/video/backlight/lm3630a_bl.c > > +++ b/drivers/video/backlight/lm3630a_bl.c > > @@ -12,6 +12,8 @@ > > #include <linux/uaccess.h> > > #include <linux/interrupt.h> > > #include <linux/regmap.h> > > +#include <linux/gpio/consumer.h> > > +#include <linux/gpio.h> > > #include <linux/pwm.h> > > #include <linux/platform_data/lm3630a_bl.h> > > > > @@ -48,6 +50,7 @@ struct lm3630a_chip { > > struct lm3630a_platform_data *pdata; > > struct backlight_device *bleda; > > struct backlight_device *bledb; > > + struct gpio_desc *enable_gpio; > > struct regmap *regmap; > > struct pwm_device *pwmd; > > }; > > @@ -506,6 +509,14 @@ static int lm3630a_probe(struct i2c_client *client, > > return -ENOMEM; > > pchip->dev = &client->dev; > > > > + pchip->enable_gpio = devm_gpiod_get_optional(&client->dev, "enable", > > + GPIOD_ASIS); > > Initializing GPIOD_ASIS doesn't look right to me. > > If you initialize ASIS then the driver must configure the pin as an > output... far easier just to set GPIOD_OUT_HIGH during the get. > > Note also that the call to this function should also be moved *below* > the calls parse the DT. > oops, must have forgotten that, and had good luck here. > > > + if (IS_ERR(pchip->enable_gpio)) { > > + rval = PTR_ERR(pchip->enable_gpio); > > + return rval; > > + } > > + > > + > > pchip->regmap = devm_regmap_init_i2c(client, &lm3630a_regmap); > > if (IS_ERR(pchip->regmap)) { > > rval = PTR_ERR(pchip->regmap); > > @@ -535,6 +546,10 @@ static int lm3630a_probe(struct i2c_client *client, > > } > > pchip->pdata = pdata; > > > > + if (pchip->enable_gpio) { > > + gpiod_set_value_cansleep(pchip->enable_gpio, 1); > > Not needed, use GPIOD_OUT_HIGH instead. > > > > + usleep_range(1000, 2000); > > Not needed, this sleep is already part of lm3630a_chip_init(). > you are right. > > > + } > > /* chip initialize */ > > rval = lm3630a_chip_init(pchip); > > if (rval < 0) { > > @@ -586,6 +601,9 @@ static int lm3630a_remove(struct i2c_client *client) > > if (rval < 0) > > dev_err(pchip->dev, "i2c failed to access register\n"); > > > > + if (pchip->enable_gpio) > > + gpiod_set_value_cansleep(pchip->enable_gpio, 0); > > + > > Is this needed? > > This is a remove path, not a power management path, and we have no idea > what the original status of the pin was anyway? > Looking at Ishdn on page 5 of the datasheet, switching it off everytime possible seems not needed. We would need to call chip_init() everytime we enable the gpio or live with default values. Therefore I did decide to not put it into any power management path. But switching it on and not switching it off feels so unbalanced. Regards, Andreas