Merge branch 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/cooloney...
authorLinus Torvalds <torvalds@linux-foundation.org>
Tue, 16 Dec 2014 02:28:25 +0000 (18:28 -0800)
committerLinus Torvalds <torvalds@linux-foundation.org>
Tue, 16 Dec 2014 02:28:25 +0000 (18:28 -0800)
Pull LED subsystem update from Bryan Wu:
 "We got some cleanup and driver for LP8860 as well as some patches for
  LED Flash Class"

* 'for-next' of git://git.kernel.org/pub/scm/linux/kernel/git/cooloney/linux-leds:
  leds: lp8860: Fix module dependency
  leds: lp8860: Introduce TI lp8860 4 channel LED driver
  leds: Add support for setting brightness in a synchronous way
  leds: implement sysfs interface locking mechanism
  leds: syscon: handle multiple syscon instances
  leds: delete copy/paste mistake
  leds: regulator: Convert to devm_regulator_get_exclusive

1  2 
drivers/leds/leds-regulator.c
include/linux/leds.h

@@@ -153,24 -153,21 +153,21 @@@ static int regulator_led_probe(struct p
                return -ENODEV;
        }
  
-       vcc = regulator_get_exclusive(&pdev->dev, "vled");
+       vcc = devm_regulator_get_exclusive(&pdev->dev, "vled");
        if (IS_ERR(vcc)) {
                dev_err(&pdev->dev, "Cannot get vcc for %s\n", pdata->name);
                return PTR_ERR(vcc);
        }
  
        led = devm_kzalloc(&pdev->dev, sizeof(*led), GFP_KERNEL);
-       if (led == NULL) {
-               ret = -ENOMEM;
-               goto err_vcc;
-       }
+       if (led == NULL)
+               return -ENOMEM;
  
        led->cdev.max_brightness = led_regulator_get_max_brightness(vcc);
        if (pdata->brightness > led->cdev.max_brightness) {
                dev_err(&pdev->dev, "Invalid default brightness %d\n",
                                pdata->brightness);
-               ret = -EINVAL;
-               goto err_vcc;
+               return -EINVAL;
        }
        led->value = pdata->brightness;
  
        ret = led_classdev_register(&pdev->dev, &led->cdev);
        if (ret < 0) {
                cancel_work_sync(&led->work);
-               goto err_vcc;
+               return ret;
        }
  
        /* to expose the default value to userspace */
        regulator_led_set_value(led);
  
        return 0;
- err_vcc:
-       regulator_put(vcc);
-       return ret;
  }
  
  static int regulator_led_remove(struct platform_device *pdev)
        led_classdev_unregister(&led->cdev);
        cancel_work_sync(&led->work);
        regulator_led_disable(led);
-       regulator_put(led->vcc);
        return 0;
  }
  
  static struct platform_driver regulator_led_driver = {
        .driver = {
                   .name  = "leds-regulator",
 -                 .owner = THIS_MODULE,
                   },
        .probe  = regulator_led_probe,
        .remove = regulator_led_remove,
diff --combined include/linux/leds.h
@@@ -13,6 -13,7 +13,7 @@@
  #define __LINUX_LEDS_H_INCLUDED
  
  #include <linux/list.h>
+ #include <linux/mutex.h>
  #include <linux/rwsem.h>
  #include <linux/spinlock.h>
  #include <linux/timer.h>
@@@ -42,11 -43,20 +43,20 @@@ struct led_classdev 
  #define LED_BLINK_ONESHOT     (1 << 17)
  #define LED_BLINK_ONESHOT_STOP        (1 << 18)
  #define LED_BLINK_INVERT      (1 << 19)
+ #define LED_SYSFS_DISABLE     (1 << 20)
+ #define SET_BRIGHTNESS_ASYNC  (1 << 21)
+ #define SET_BRIGHTNESS_SYNC   (1 << 22)
  
        /* Set LED brightness level */
        /* Must not sleep, use a workqueue if needed */
        void            (*brightness_set)(struct led_classdev *led_cdev,
                                          enum led_brightness brightness);
+       /*
+        * Set LED brightness level immediately - it can block the caller for
+        * the time required for accessing a LED device register.
+        */
+       int             (*brightness_set_sync)(struct led_classdev *led_cdev,
+                                       enum led_brightness brightness);
        /* Get LED brightness level */
        enum led_brightness (*brightness_get)(struct led_classdev *led_cdev);
  
@@@ -85,6 -95,9 +95,9 @@@
        /* true if activated - deactivate routine uses it to do cleanup */
        bool                    activated;
  #endif
+       /* Ensures consistent access to the LED Flash Class device */
+       struct mutex            led_access;
  };
  
  extern int led_classdev_register(struct device *parent,
@@@ -151,6 -164,33 +164,33 @@@ extern void led_set_brightness(struct l
   */
  extern int led_update_brightness(struct led_classdev *led_cdev);
  
+ /**
+  * led_sysfs_disable - disable LED sysfs interface
+  * @led_cdev: the LED to set
+  *
+  * Disable the led_cdev's sysfs interface.
+  */
+ extern void led_sysfs_disable(struct led_classdev *led_cdev);
+ /**
+  * led_sysfs_enable - enable LED sysfs interface
+  * @led_cdev: the LED to set
+  *
+  * Enable the led_cdev's sysfs interface.
+  */
+ extern void led_sysfs_enable(struct led_classdev *led_cdev);
+ /**
+  * led_sysfs_is_disabled - check if LED sysfs interface is disabled
+  * @led_cdev: the LED to query
+  *
+  * Returns: true if the led_cdev's sysfs interface is disabled.
+  */
+ static inline bool led_sysfs_is_disabled(struct led_classdev *led_cdev)
+ {
+       return led_cdev->flags & LED_SYSFS_DISABLE;
+ }
  /*
   * LED Triggers
   */
@@@ -261,7 -301,6 +301,7 @@@ struct gpio_led 
        unsigned        retain_state_suspended : 1;
        unsigned        default_state : 2;
        /* default_state should be one of LEDS_GPIO_DEFSTATE_(ON|OFF|KEEP) */
 +      struct gpio_desc *gpiod;
  };
  #define LEDS_GPIO_DEFSTATE_OFF                0
  #define LEDS_GPIO_DEFSTATE_ON         1
@@@ -274,7 -313,7 +314,7 @@@ struct gpio_led_platform_data 
  #define GPIO_LED_NO_BLINK_LOW 0       /* No blink GPIO state low */
  #define GPIO_LED_NO_BLINK_HIGH        1       /* No blink GPIO state high */
  #define GPIO_LED_BLINK                2       /* Please, blink */
 -      int             (*gpio_blink_set)(unsigned gpio, int state,
 +      int             (*gpio_blink_set)(struct gpio_desc *desc, int state,
                                        unsigned long *delay_on,
                                        unsigned long *delay_off);
  };