Hi Linus, On mar., sept. 04 2018, Linus Walleij <linus.walleij@xxxxxxxxxx> wrote: > Before things go out of hand, make it possible to pass > flags when requesting "own" descriptors from a gpio_chip. > This is necessary if the chip wants to reques a GPIO with > active low semantics, for example. For mvebu: Reviewed-by: Gregory CLEMENT <gregory.clement@xxxxxxxxxxx> Thanks, Gregory > > Cc: Janusz Krzysztofik <jmkrzyszt@xxxxxxxxx> > Cc: Gregory CLEMENT <gregory.clement@xxxxxxxxxxxxxxxxxx> > Cc: Thomas Petazzoni <thomas.petazzoni@xxxxxxxxxxxxxxxxxx> > Cc: Jason Cooper <jason@xxxxxxxxxxxxxx> > Cc: Jiri Kosina <jkosina@xxxxxxx> > Cc: Roger Quadros <rogerq@xxxxxx> > Signed-off-by: Linus Walleij <linus.walleij@xxxxxxxxxx> > --- > Documentation/driver-api/gpio/driver.rst | 4 +++- > arch/arm/mach-omap1/ams-delta-fiq.c | 2 +- > arch/arm/mach-omap1/board-ams-delta.c | 2 +- > drivers/gpio/gpio-mvebu.c | 2 +- > drivers/gpio/gpiolib-acpi.c | 13 +++---------- > drivers/gpio/gpiolib.c | 21 +++++++++++++++++++-- > drivers/hid/hid-cp2112.c | 2 +- > drivers/memory/omap-gpmc.c | 3 ++- > include/linux/gpio/driver.h | 4 +++- > 9 files changed, 34 insertions(+), 19 deletions(-) > > diff --git a/Documentation/driver-api/gpio/driver.rst b/Documentation/driver-api/gpio/driver.rst > index cbe0242842d1..e9a5aae8c84c 100644 > --- a/Documentation/driver-api/gpio/driver.rst > +++ b/Documentation/driver-api/gpio/driver.rst > @@ -413,7 +413,9 @@ try_module_get()). A GPIO driver can use the following functions instead > to request and free descriptors without being pinned to the kernel forever:: > > struct gpio_desc *gpiochip_request_own_desc(struct gpio_desc *desc, > - const char *label) > + u16 hwnum, > + const char *label, > + enum gpiod_flags flags) > > void gpiochip_free_own_desc(struct gpio_desc *desc) > > diff --git a/arch/arm/mach-omap1/ams-delta-fiq.c b/arch/arm/mach-omap1/ams-delta-fiq.c > index b0dc7ddf5877..0324d0f209ea 100644 > --- a/arch/arm/mach-omap1/ams-delta-fiq.c > +++ b/arch/arm/mach-omap1/ams-delta-fiq.c > @@ -103,7 +103,7 @@ void __init ams_delta_init_fiq(struct gpio_chip *chip, > } > > for (i = 0; i < ARRAY_SIZE(irq_data); i++) { > - gpiod = gpiochip_request_own_desc(chip, i, pin_name[i]); > + gpiod = gpiochip_request_own_desc(chip, i, pin_name[i], 0); > if (IS_ERR(gpiod)) { > pr_err("%s: failed to get GPIO pin %d (%ld)\n", > __func__, i, PTR_ERR(gpiod)); > diff --git a/arch/arm/mach-omap1/board-ams-delta.c b/arch/arm/mach-omap1/board-ams-delta.c > index dd28d2614d7f..085438d17662 100644 > --- a/arch/arm/mach-omap1/board-ams-delta.c > +++ b/arch/arm/mach-omap1/board-ams-delta.c > @@ -784,7 +784,7 @@ static void __init ams_delta_led_init(struct gpio_chip *chip) > int i; > > for (i = LATCH1_PIN_LED_CAMERA; i < LATCH1_PIN_DOCKIT1; i++) { > - gpiod = gpiochip_request_own_desc(chip, i, NULL); > + gpiod = gpiochip_request_own_desc(chip, i, "camera-led", 0); > if (IS_ERR(gpiod)) { > pr_warn("%s: %s GPIO %d request failed (%ld)\n", > __func__, LATCH1_LABEL, i, PTR_ERR(gpiod)); > diff --git a/drivers/gpio/gpio-mvebu.c b/drivers/gpio/gpio-mvebu.c > index 6e02148c208b..6c675c5accba 100644 > --- a/drivers/gpio/gpio-mvebu.c > +++ b/drivers/gpio/gpio-mvebu.c > @@ -608,7 +608,7 @@ static int mvebu_pwm_request(struct pwm_chip *chip, struct pwm_device *pwm) > ret = -EBUSY; > } else { > desc = gpiochip_request_own_desc(&mvchip->chip, > - pwm->hwpwm, "mvebu-pwm"); > + pwm->hwpwm, "mvebu-pwm", 0); > if (IS_ERR(desc)) { > ret = PTR_ERR(desc); > goto out; > diff --git a/drivers/gpio/gpiolib-acpi.c b/drivers/gpio/gpiolib-acpi.c > index c48ed9d89ff5..2b76ccaf0350 100644 > --- a/drivers/gpio/gpiolib-acpi.c > +++ b/drivers/gpio/gpiolib-acpi.c > @@ -178,7 +178,7 @@ static acpi_status acpi_gpiochip_request_interrupt(struct acpi_resource *ares, > if (!handler) > return AE_OK; > > - desc = gpiochip_request_own_desc(chip, pin, "ACPI:Event"); > + desc = gpiochip_request_own_desc(chip, pin, "ACPI:Event", 0); > if (IS_ERR(desc)) { > dev_err(chip->parent, "Failed to request GPIO\n"); > return AE_ERROR; > @@ -883,21 +883,14 @@ acpi_gpio_adr_space_handler(u32 function, acpi_physical_address address, > const char *label = "ACPI:OpRegion"; > int err; > > - desc = gpiochip_request_own_desc(chip, pin, label); > + desc = gpiochip_request_own_desc(chip, pin, label, > + 0, flags); > if (IS_ERR(desc)) { > status = AE_ERROR; > mutex_unlock(&achip->conn_lock); > goto out; > } > > - err = gpiod_configure_flags(desc, label, 0, flags); > - if (err < 0) { > - status = AE_NOT_CONFIGURED; > - gpiochip_free_own_desc(desc); > - mutex_unlock(&achip->conn_lock); > - goto out; > - } > - > conn = kzalloc(sizeof(*conn), GFP_KERNEL); > if (!conn) { > status = AE_NO_MEMORY; > diff --git a/drivers/gpio/gpiolib.c b/drivers/gpio/gpiolib.c > index e8f8a1999393..26e2ec06eb43 100644 > --- a/drivers/gpio/gpiolib.c > +++ b/drivers/gpio/gpiolib.c > @@ -2446,6 +2446,7 @@ EXPORT_SYMBOL_GPL(gpiochip_is_requested); > * @chip: GPIO chip > * @hwnum: hardware number of the GPIO for which to request the descriptor > * @label: label for the GPIO > + * @flags: flags for this GPIO or 0 if default > * > * Function allows GPIO chip drivers to request and use their own GPIO > * descriptors via gpiolib API. Difference to gpiod_request() is that this > @@ -2458,7 +2459,8 @@ EXPORT_SYMBOL_GPL(gpiochip_is_requested); > * code on failure. > */ > struct gpio_desc *gpiochip_request_own_desc(struct gpio_chip *chip, u16 hwnum, > - const char *label) > + const char *label, > + enum gpiod_flags flags) > { > struct gpio_desc *desc = gpiochip_get_desc(chip, hwnum); > int err; > @@ -2472,6 +2474,13 @@ struct gpio_desc *gpiochip_request_own_desc(struct gpio_chip *chip, u16 hwnum, > if (err < 0) > return ERR_PTR(err); > > + err = gpiod_configure_flags(desc, label, 0, flags); > + if (err) { > + chip_err(chip, "setup of own GPIO %s failed\n", label); > + gpiod_free_commit(desc); > + return ERR_PTR(err); > + } > + > return desc; > } > EXPORT_SYMBOL_GPL(gpiochip_request_own_desc); > @@ -4108,7 +4117,15 @@ int gpiod_hog(struct gpio_desc *desc, const char *name, > chip = gpiod_to_chip(desc); > hwnum = gpio_chip_hwgpio(desc); > > - local_desc = gpiochip_request_own_desc(chip, hwnum, name); > + /* > + * FIXME: not very elegant that we call gpiod_configure_flags() > + * twice here (once inside gpiochip_request_own_desc() and > + * again here), but the gpiochip_request_own_desc() is external > + * and cannot really pass the lflags so this is the lesser evil > + * at the moment. Pass zero as dflags on this first call so we > + * don't screw anything up. > + */ > + local_desc = gpiochip_request_own_desc(chip, hwnum, name, 0); > if (IS_ERR(local_desc)) { > status = PTR_ERR(local_desc); > pr_err("requesting hog GPIO %s (chip %s, offset %d) failed, %d\n", > diff --git a/drivers/hid/hid-cp2112.c b/drivers/hid/hid-cp2112.c > index 271f31461da4..47f65857408d 100644 > --- a/drivers/hid/hid-cp2112.c > +++ b/drivers/hid/hid-cp2112.c > @@ -1203,7 +1203,7 @@ static int __maybe_unused cp2112_allocate_irq(struct cp2112_device *dev, > return -EINVAL; > > dev->desc[pin] = gpiochip_request_own_desc(&dev->gc, pin, > - "HID/I2C:Event"); > + "HID/I2C:Event", 0); > if (IS_ERR(dev->desc[pin])) { > dev_err(dev->gc.parent, "Failed to request GPIO\n"); > return PTR_ERR(dev->desc[pin]); > diff --git a/drivers/memory/omap-gpmc.c b/drivers/memory/omap-gpmc.c > index c215287e80cf..b9b4f7058b05 100644 > --- a/drivers/memory/omap-gpmc.c > +++ b/drivers/memory/omap-gpmc.c > @@ -2170,7 +2170,8 @@ static int gpmc_probe_generic_child(struct platform_device *pdev, > unsigned int wait_pin = gpmc_s.wait_pin; > > waitpin_desc = gpiochip_request_own_desc(&gpmc->gpio_chip, > - wait_pin, "WAITPIN"); > + wait_pin, "WAITPIN", > + 0); > if (IS_ERR(waitpin_desc)) { > dev_err(&pdev->dev, "invalid wait-pin: %d\n", wait_pin); > ret = PTR_ERR(waitpin_desc); > diff --git a/include/linux/gpio/driver.h b/include/linux/gpio/driver.h > index 0ea328e71ec9..86d9db466444 100644 > --- a/include/linux/gpio/driver.h > +++ b/include/linux/gpio/driver.h > @@ -17,6 +17,7 @@ struct device_node; > struct seq_file; > struct gpio_device; > struct module; > +enum gpiod_flags; > > #ifdef CONFIG_GPIOLIB > > @@ -570,7 +571,8 @@ gpiochip_remove_pin_ranges(struct gpio_chip *chip) > #endif /* CONFIG_PINCTRL */ > > struct gpio_desc *gpiochip_request_own_desc(struct gpio_chip *chip, u16 hwnum, > - const char *label); > + const char *label, > + enum gpiod_flags flags); > void gpiochip_free_own_desc(struct gpio_desc *desc); > > #else /* CONFIG_GPIOLIB */ > -- > 2.17.1 > -- Gregory Clement, Bootlin Embedded Linux and Kernel engineering http://bootlin.com