aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Documentation/devicetree/bindings/leds/leds-lp55xx.txt11
-rw-r--r--arch/arm/mach-omap2/board-rx51-peripherals.c20
-rw-r--r--drivers/leds/Kconfig10
-rw-r--r--drivers/leds/Makefile1
-rw-r--r--drivers/leds/leds-blinkm.c3
-rw-r--r--drivers/leds/leds-dac124s085.c3
-rw-r--r--drivers/leds/leds-gpio.c7
-rw-r--r--drivers/leds/leds-lp5523.c1
-rw-r--r--drivers/leds/leds-lp5562.c1
-rw-r--r--drivers/leds/leds-lp55xx-common.c28
-rw-r--r--drivers/leds/leds-lp8501.c1
-rw-r--r--drivers/leds/leds-ns2.c1
-rw-r--r--drivers/leds/leds-pca9685.c213
-rw-r--r--drivers/leds/leds-pwm.c2
-rw-r--r--include/linux/of.h16
-rw-r--r--include/linux/platform_data/leds-lp55xx.h7
-rw-r--r--include/linux/platform_data/leds-pca9685.h35
17 files changed, 312 insertions, 48 deletions
diff --git a/Documentation/devicetree/bindings/leds/leds-lp55xx.txt b/Documentation/devicetree/bindings/leds/leds-lp55xx.txt
index a61727f9a6d1..c55b8c016a9e 100644
--- a/Documentation/devicetree/bindings/leds/leds-lp55xx.txt
+++ b/Documentation/devicetree/bindings/leds/leds-lp55xx.txt
@@ -10,6 +10,7 @@ Each child has own specific current settings
10- max-cur: Maximun current at each led channel. 10- max-cur: Maximun current at each led channel.
11 11
12Optional properties: 12Optional properties:
13- enable-gpio: GPIO attached to the chip's enable pin
13- label: Used for naming LEDs 14- label: Used for naming LEDs
14- pwr-sel: LP8501 specific property. Power selection for output channels. 15- pwr-sel: LP8501 specific property. Power selection for output channels.
15 0: D1~9 are connected to VDD 16 0: D1~9 are connected to VDD
@@ -17,12 +18,15 @@ Optional properties:
17 2: D1~6 with VOUT, D7~9 with VDD 18 2: D1~6 with VOUT, D7~9 with VDD
18 3: D1~9 are connected to VOUT 19 3: D1~9 are connected to VOUT
19 20
20Alternatively, each child can have specific channel name 21Alternatively, each child can have a specific channel name and trigger:
21- chan-name: Name of each channel name 22- chan-name (optional): name of channel
23- linux,default-trigger (optional): see
24 Documentation/devicetree/bindings/leds/common.txt
22 25
23example 1) LP5521 26example 1) LP5521
243 LED channels, external clock used. Channel names are 'lp5521_pri:channel0', 273 LED channels, external clock used. Channel names are 'lp5521_pri:channel0',
25'lp5521_pri:channel1' and 'lp5521_pri:channel2' 28'lp5521_pri:channel1' and 'lp5521_pri:channel2', with a heartbeat trigger
29on channel 0.
26 30
27lp5521@32 { 31lp5521@32 {
28 compatible = "national,lp5521"; 32 compatible = "national,lp5521";
@@ -33,6 +37,7 @@ lp5521@32 {
33 chan0 { 37 chan0 {
34 led-cur = /bits/ 8 <0x2f>; 38 led-cur = /bits/ 8 <0x2f>;
35 max-cur = /bits/ 8 <0x5f>; 39 max-cur = /bits/ 8 <0x5f>;
40 linux,default-trigger = "heartbeat";
36 }; 41 };
37 42
38 chan1 { 43 chan1 {
diff --git a/arch/arm/mach-omap2/board-rx51-peripherals.c b/arch/arm/mach-omap2/board-rx51-peripherals.c
index 5c0d0e120420..f093af17f5e6 100644
--- a/arch/arm/mach-omap2/board-rx51-peripherals.c
+++ b/arch/arm/mach-omap2/board-rx51-peripherals.c
@@ -213,29 +213,11 @@ static struct lp55xx_led_config rx51_lp5523_led_config[] = {
213 } 213 }
214}; 214};
215 215
216static int rx51_lp5523_setup(void)
217{
218 return gpio_request_one(RX51_LP5523_CHIP_EN_GPIO, GPIOF_DIR_OUT,
219 "lp5523_enable");
220}
221
222static void rx51_lp5523_release(void)
223{
224 gpio_free(RX51_LP5523_CHIP_EN_GPIO);
225}
226
227static void rx51_lp5523_enable(bool state)
228{
229 gpio_set_value(RX51_LP5523_CHIP_EN_GPIO, !!state);
230}
231
232static struct lp55xx_platform_data rx51_lp5523_platform_data = { 216static struct lp55xx_platform_data rx51_lp5523_platform_data = {
233 .led_config = rx51_lp5523_led_config, 217 .led_config = rx51_lp5523_led_config,
234 .num_channels = ARRAY_SIZE(rx51_lp5523_led_config), 218 .num_channels = ARRAY_SIZE(rx51_lp5523_led_config),
235 .clock_mode = LP55XX_CLOCK_AUTO, 219 .clock_mode = LP55XX_CLOCK_AUTO,
236 .setup_resources = rx51_lp5523_setup, 220 .enable_gpio = RX51_LP5523_CHIP_EN_GPIO,
237 .release_resources = rx51_lp5523_release,
238 .enable = rx51_lp5523_enable,
239}; 221};
240#endif 222#endif
241 223
diff --git a/drivers/leds/Kconfig b/drivers/leds/Kconfig
index 875bbe4c962e..72156c123033 100644
--- a/drivers/leds/Kconfig
+++ b/drivers/leds/Kconfig
@@ -300,6 +300,16 @@ config LEDS_PCA963X
300 LED driver chip accessed via the I2C bus. Supported 300 LED driver chip accessed via the I2C bus. Supported
301 devices include PCA9633 and PCA9634 301 devices include PCA9633 and PCA9634
302 302
303config LEDS_PCA9685
304 tristate "LED support for PCA9685 I2C chip"
305 depends on LEDS_CLASS
306 depends on I2C
307 help
308 This option enables support for LEDs connected to the PCA9685
309 LED driver chip accessed via the I2C bus.
310 The PCA9685 offers 12-bit PWM (4095 levels of brightness) on
311 16 individual channels.
312
303config LEDS_WM831X_STATUS 313config LEDS_WM831X_STATUS
304 tristate "LED support for status LEDs on WM831x PMICs" 314 tristate "LED support for status LEDs on WM831x PMICs"
305 depends on LEDS_CLASS 315 depends on LEDS_CLASS
diff --git a/drivers/leds/Makefile b/drivers/leds/Makefile
index 8979b0b2c85e..3cd76dbd9be2 100644
--- a/drivers/leds/Makefile
+++ b/drivers/leds/Makefile
@@ -36,6 +36,7 @@ obj-$(CONFIG_LEDS_OT200) += leds-ot200.o
36obj-$(CONFIG_LEDS_FSG) += leds-fsg.o 36obj-$(CONFIG_LEDS_FSG) += leds-fsg.o
37obj-$(CONFIG_LEDS_PCA955X) += leds-pca955x.o 37obj-$(CONFIG_LEDS_PCA955X) += leds-pca955x.o
38obj-$(CONFIG_LEDS_PCA963X) += leds-pca963x.o 38obj-$(CONFIG_LEDS_PCA963X) += leds-pca963x.o
39obj-$(CONFIG_LEDS_PCA9685) += leds-pca9685.o
39obj-$(CONFIG_LEDS_DA903X) += leds-da903x.o 40obj-$(CONFIG_LEDS_DA903X) += leds-da903x.o
40obj-$(CONFIG_LEDS_DA9052) += leds-da9052.o 41obj-$(CONFIG_LEDS_DA9052) += leds-da9052.o
41obj-$(CONFIG_LEDS_WM831X_STATUS) += leds-wm831x-status.o 42obj-$(CONFIG_LEDS_WM831X_STATUS) += leds-wm831x-status.o
diff --git a/drivers/leds/leds-blinkm.c b/drivers/leds/leds-blinkm.c
index a502678cc7f5..66d0a57db221 100644
--- a/drivers/leds/leds-blinkm.c
+++ b/drivers/leds/leds-blinkm.c
@@ -161,13 +161,10 @@ static ssize_t show_color_common(struct device *dev, char *buf, int color)
161 switch (color) { 161 switch (color) {
162 case RED: 162 case RED:
163 return scnprintf(buf, PAGE_SIZE, "%02X\n", data->red); 163 return scnprintf(buf, PAGE_SIZE, "%02X\n", data->red);
164 break;
165 case GREEN: 164 case GREEN:
166 return scnprintf(buf, PAGE_SIZE, "%02X\n", data->green); 165 return scnprintf(buf, PAGE_SIZE, "%02X\n", data->green);
167 break;
168 case BLUE: 166 case BLUE:
169 return scnprintf(buf, PAGE_SIZE, "%02X\n", data->blue); 167 return scnprintf(buf, PAGE_SIZE, "%02X\n", data->blue);
170 break;
171 default: 168 default:
172 return -EINVAL; 169 return -EINVAL;
173 } 170 }
diff --git a/drivers/leds/leds-dac124s085.c b/drivers/leds/leds-dac124s085.c
index 1f9d8e62d37e..db3ba8b42517 100644
--- a/drivers/leds/leds-dac124s085.c
+++ b/drivers/leds/leds-dac124s085.c
@@ -101,7 +101,6 @@ eledcr:
101 while (i--) 101 while (i--)
102 led_classdev_unregister(&dac->leds[i].ldev); 102 led_classdev_unregister(&dac->leds[i].ldev);
103 103
104 spi_set_drvdata(spi, NULL);
105 return ret; 104 return ret;
106} 105}
107 106
@@ -115,8 +114,6 @@ static int dac124s085_remove(struct spi_device *spi)
115 cancel_work_sync(&dac->leds[i].work); 114 cancel_work_sync(&dac->leds[i].work);
116 } 115 }
117 116
118 spi_set_drvdata(spi, NULL);
119
120 return 0; 117 return 0;
121} 118}
122 119
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index e8b01e57348d..78b0e273a903 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -15,6 +15,7 @@
15#include <linux/platform_device.h> 15#include <linux/platform_device.h>
16#include <linux/gpio.h> 16#include <linux/gpio.h>
17#include <linux/leds.h> 17#include <linux/leds.h>
18#include <linux/of.h>
18#include <linux/of_platform.h> 19#include <linux/of_platform.h>
19#include <linux/of_gpio.h> 20#include <linux/of_gpio.h>
20#include <linux/slab.h> 21#include <linux/slab.h>
@@ -170,11 +171,11 @@ static struct gpio_leds_priv *gpio_leds_create_of(struct platform_device *pdev)
170 int count, ret; 171 int count, ret;
171 172
172 /* count LEDs in this device, so we know how much to allocate */ 173 /* count LEDs in this device, so we know how much to allocate */
173 count = of_get_child_count(np); 174 count = of_get_available_child_count(np);
174 if (!count) 175 if (!count)
175 return ERR_PTR(-ENODEV); 176 return ERR_PTR(-ENODEV);
176 177
177 for_each_child_of_node(np, child) 178 for_each_available_child_of_node(np, child)
178 if (of_get_gpio(child, 0) == -EPROBE_DEFER) 179 if (of_get_gpio(child, 0) == -EPROBE_DEFER)
179 return ERR_PTR(-EPROBE_DEFER); 180 return ERR_PTR(-EPROBE_DEFER);
180 181
@@ -183,7 +184,7 @@ static struct gpio_leds_priv *gpio_leds_create_of(struct platform_device *pdev)
183 if (!priv) 184 if (!priv)
184 return ERR_PTR(-ENOMEM); 185 return ERR_PTR(-ENOMEM);
185 186
186 for_each_child_of_node(np, child) { 187 for_each_available_child_of_node(np, child) {
187 struct gpio_led led = {}; 188 struct gpio_led led = {};
188 enum of_gpio_flags flags; 189 enum of_gpio_flags flags;
189 const char *state; 190 const char *state;
diff --git a/drivers/leds/leds-lp5523.c b/drivers/leds/leds-lp5523.c
index fe3bcbb5747f..6b553d9f4266 100644
--- a/drivers/leds/leds-lp5523.c
+++ b/drivers/leds/leds-lp5523.c
@@ -29,6 +29,7 @@
29#include <linux/leds.h> 29#include <linux/leds.h>
30#include <linux/module.h> 30#include <linux/module.h>
31#include <linux/mutex.h> 31#include <linux/mutex.h>
32#include <linux/of.h>
32#include <linux/platform_data/leds-lp55xx.h> 33#include <linux/platform_data/leds-lp55xx.h>
33#include <linux/slab.h> 34#include <linux/slab.h>
34 35
diff --git a/drivers/leds/leds-lp5562.c b/drivers/leds/leds-lp5562.c
index 2585cfd57711..bf006f4e44a0 100644
--- a/drivers/leds/leds-lp5562.c
+++ b/drivers/leds/leds-lp5562.c
@@ -17,6 +17,7 @@
17#include <linux/leds.h> 17#include <linux/leds.h>
18#include <linux/module.h> 18#include <linux/module.h>
19#include <linux/mutex.h> 19#include <linux/mutex.h>
20#include <linux/of.h>
20#include <linux/platform_data/leds-lp55xx.h> 21#include <linux/platform_data/leds-lp55xx.h>
21#include <linux/slab.h> 22#include <linux/slab.h>
22 23
diff --git a/drivers/leds/leds-lp55xx-common.c b/drivers/leds/leds-lp55xx-common.c
index 351825b96f16..9acc6bb7deef 100644
--- a/drivers/leds/leds-lp55xx-common.c
+++ b/drivers/leds/leds-lp55xx-common.c
@@ -20,6 +20,8 @@
20#include <linux/module.h> 20#include <linux/module.h>
21#include <linux/platform_data/leds-lp55xx.h> 21#include <linux/platform_data/leds-lp55xx.h>
22#include <linux/slab.h> 22#include <linux/slab.h>
23#include <linux/gpio.h>
24#include <linux/of_gpio.h>
23 25
24#include "leds-lp55xx-common.h" 26#include "leds-lp55xx-common.h"
25 27
@@ -165,6 +167,7 @@ static int lp55xx_init_led(struct lp55xx_led *led,
165 led->led_current = pdata->led_config[chan].led_current; 167 led->led_current = pdata->led_config[chan].led_current;
166 led->max_current = pdata->led_config[chan].max_current; 168 led->max_current = pdata->led_config[chan].max_current;
167 led->chan_nr = pdata->led_config[chan].chan_nr; 169 led->chan_nr = pdata->led_config[chan].chan_nr;
170 led->cdev.default_trigger = pdata->led_config[chan].default_trigger;
168 171
169 if (led->chan_nr >= max_channel) { 172 if (led->chan_nr >= max_channel) {
170 dev_err(dev, "Use channel numbers between 0 and %d\n", 173 dev_err(dev, "Use channel numbers between 0 and %d\n",
@@ -406,18 +409,18 @@ int lp55xx_init_device(struct lp55xx_chip *chip)
406 if (!pdata || !cfg) 409 if (!pdata || !cfg)
407 return -EINVAL; 410 return -EINVAL;
408 411
409 if (pdata->setup_resources) { 412 if (gpio_is_valid(pdata->enable_gpio)) {
410 ret = pdata->setup_resources(); 413 ret = devm_gpio_request_one(dev, pdata->enable_gpio,
414 GPIOF_DIR_OUT, "lp5523_enable");
411 if (ret < 0) { 415 if (ret < 0) {
412 dev_err(dev, "setup resoure err: %d\n", ret); 416 dev_err(dev, "could not acquire enable gpio (err=%d)\n",
417 ret);
413 goto err; 418 goto err;
414 } 419 }
415 }
416 420
417 if (pdata->enable) { 421 gpio_set_value(pdata->enable_gpio, 0);
418 pdata->enable(0);
419 usleep_range(1000, 2000); /* Keep enable down at least 1ms */ 422 usleep_range(1000, 2000); /* Keep enable down at least 1ms */
420 pdata->enable(1); 423 gpio_set_value(pdata->enable_gpio, 1);
421 usleep_range(1000, 2000); /* 500us abs min. */ 424 usleep_range(1000, 2000); /* 500us abs min. */
422 } 425 }
423 426
@@ -458,11 +461,8 @@ void lp55xx_deinit_device(struct lp55xx_chip *chip)
458 if (chip->clk) 461 if (chip->clk)
459 clk_disable_unprepare(chip->clk); 462 clk_disable_unprepare(chip->clk);
460 463
461 if (pdata->enable) 464 if (gpio_is_valid(pdata->enable_gpio))
462 pdata->enable(0); 465 gpio_set_value(pdata->enable_gpio, 0);
463
464 if (pdata->release_resources)
465 pdata->release_resources();
466} 466}
467EXPORT_SYMBOL_GPL(lp55xx_deinit_device); 467EXPORT_SYMBOL_GPL(lp55xx_deinit_device);
468 468
@@ -586,6 +586,8 @@ int lp55xx_of_populate_pdata(struct device *dev, struct device_node *np)
586 of_property_read_string(child, "chan-name", &cfg[i].name); 586 of_property_read_string(child, "chan-name", &cfg[i].name);
587 of_property_read_u8(child, "led-cur", &cfg[i].led_current); 587 of_property_read_u8(child, "led-cur", &cfg[i].led_current);
588 of_property_read_u8(child, "max-cur", &cfg[i].max_current); 588 of_property_read_u8(child, "max-cur", &cfg[i].max_current);
589 cfg[i].default_trigger =
590 of_get_property(child, "linux,default-trigger", NULL);
589 591
590 i++; 592 i++;
591 } 593 }
@@ -593,6 +595,8 @@ int lp55xx_of_populate_pdata(struct device *dev, struct device_node *np)
593 of_property_read_string(np, "label", &pdata->label); 595 of_property_read_string(np, "label", &pdata->label);
594 of_property_read_u8(np, "clock-mode", &pdata->clock_mode); 596 of_property_read_u8(np, "clock-mode", &pdata->clock_mode);
595 597
598 pdata->enable_gpio = of_get_named_gpio(np, "enable-gpio", 0);
599
596 /* LP8501 specific */ 600 /* LP8501 specific */
597 of_property_read_u8(np, "pwr-sel", (u8 *)&pdata->pwr_sel); 601 of_property_read_u8(np, "pwr-sel", (u8 *)&pdata->pwr_sel);
598 602
diff --git a/drivers/leds/leds-lp8501.c b/drivers/leds/leds-lp8501.c
index 8d55a780ca46..f1c704f2243a 100644
--- a/drivers/leds/leds-lp8501.c
+++ b/drivers/leds/leds-lp8501.c
@@ -18,6 +18,7 @@
18#include <linux/leds.h> 18#include <linux/leds.h>
19#include <linux/module.h> 19#include <linux/module.h>
20#include <linux/mutex.h> 20#include <linux/mutex.h>
21#include <linux/of.h>
21#include <linux/platform_data/leds-lp55xx.h> 22#include <linux/platform_data/leds-lp55xx.h>
22#include <linux/slab.h> 23#include <linux/slab.h>
23 24
diff --git a/drivers/leds/leds-ns2.c b/drivers/leds/leds-ns2.c
index 141f13438e80..c7a4230233ea 100644
--- a/drivers/leds/leds-ns2.c
+++ b/drivers/leds/leds-ns2.c
@@ -30,6 +30,7 @@
30#include <linux/leds.h> 30#include <linux/leds.h>
31#include <linux/module.h> 31#include <linux/module.h>
32#include <linux/platform_data/leds-kirkwood-ns2.h> 32#include <linux/platform_data/leds-kirkwood-ns2.h>
33#include <linux/of.h>
33#include <linux/of_gpio.h> 34#include <linux/of_gpio.h>
34 35
35/* 36/*
diff --git a/drivers/leds/leds-pca9685.c b/drivers/leds/leds-pca9685.c
new file mode 100644
index 000000000000..6e1ef3a9d6ef
--- /dev/null
+++ b/drivers/leds/leds-pca9685.c
@@ -0,0 +1,213 @@
1/*
2 * Copyright 2013 Maximilian Güntner <maximilian.guentner@gmail.com>
3 *
4 * This file is subject to the terms and conditions of version 2 of
5 * the GNU General Public License. See the file COPYING in the main
6 * directory of this archive for more details.
7 *
8 * Based on leds-pca963x.c driver by
9 * Peter Meerwald <p.meerwald@bct-electronic.com>
10 *
11 * Driver for the NXP PCA9685 12-Bit PWM LED driver chip.
12 *
13 */
14
15#include <linux/ctype.h>
16#include <linux/delay.h>
17#include <linux/err.h>
18#include <linux/i2c.h>
19#include <linux/leds.h>
20#include <linux/module.h>
21#include <linux/slab.h>
22#include <linux/string.h>
23#include <linux/workqueue.h>
24
25#include <linux/platform_data/leds-pca9685.h>
26
27/* Register Addresses */
28#define PCA9685_MODE1 0x00
29#define PCA9685_MODE2 0x01
30#define PCA9685_LED0_ON_L 0x06
31#define PCA9685_ALL_LED_ON_L 0xFA
32
33/* MODE1 Register */
34#define PCA9685_ALLCALL 0x00
35#define PCA9685_SLEEP 0x04
36#define PCA9685_AI 0x05
37
38/* MODE2 Register */
39#define PCA9685_INVRT 0x04
40#define PCA9685_OUTDRV 0x02
41
42static const struct i2c_device_id pca9685_id[] = {
43 { "pca9685", 0 },
44 { }
45};
46MODULE_DEVICE_TABLE(i2c, pca9685_id);
47
48struct pca9685_led {
49 struct i2c_client *client;
50 struct work_struct work;
51 u16 brightness;
52 struct led_classdev led_cdev;
53 int led_num; /* 0-15 */
54 char name[32];
55};
56
57static void pca9685_write_msg(struct i2c_client *client, u8 *buf, u8 len)
58{
59 struct i2c_msg msg = {
60 .addr = client->addr,
61 .flags = 0x00,
62 .len = len,
63 .buf = buf
64 };
65 i2c_transfer(client->adapter, &msg, 1);
66}
67
68static void pca9685_all_off(struct i2c_client *client)
69{
70 u8 i2c_buffer[5] = {PCA9685_ALL_LED_ON_L, 0x00, 0x00, 0x00, 0x10};
71 pca9685_write_msg(client, i2c_buffer, 5);
72}
73
74static void pca9685_led_work(struct work_struct *work)
75{
76 struct pca9685_led *pca9685;
77 u8 i2c_buffer[5];
78
79 pca9685 = container_of(work, struct pca9685_led, work);
80 i2c_buffer[0] = PCA9685_LED0_ON_L + 4 * pca9685->led_num;
81 /*
82 * 4095 is the maximum brightness, so we set the ON time to 0x1000
83 * which disables the PWM generator for that LED
84 */
85 if (pca9685->brightness == 4095)
86 *((__le16 *)(i2c_buffer+1)) = cpu_to_le16(0x1000);
87 else
88 *((__le16 *)(i2c_buffer+1)) = 0x0000;
89
90 if (pca9685->brightness == 0)
91 *((__le16 *)(i2c_buffer+3)) = cpu_to_le16(0x1000);
92 else if (pca9685->brightness == 4095)
93 *((__le16 *)(i2c_buffer+3)) = 0x0000;
94 else
95 *((__le16 *)(i2c_buffer+3)) = cpu_to_le16(pca9685->brightness);
96
97 pca9685_write_msg(pca9685->client, i2c_buffer, 5);
98}
99
100static void pca9685_led_set(struct led_classdev *led_cdev,
101 enum led_brightness value)
102{
103 struct pca9685_led *pca9685;
104 pca9685 = container_of(led_cdev, struct pca9685_led, led_cdev);
105 pca9685->brightness = value;
106
107 schedule_work(&pca9685->work);
108}
109
110static int pca9685_probe(struct i2c_client *client,
111 const struct i2c_device_id *id)
112{
113 struct pca9685_led *pca9685;
114 struct pca9685_platform_data *pdata;
115 int err;
116 u8 i;
117
118 pdata = dev_get_platdata(&client->dev);
119 if (pdata) {
120 if (pdata->leds.num_leds < 1 || pdata->leds.num_leds > 15) {
121 dev_err(&client->dev, "board info must claim 1-16 LEDs");
122 return -EINVAL;
123 }
124 }
125
126 pca9685 = devm_kzalloc(&client->dev, 16 * sizeof(*pca9685), GFP_KERNEL);
127 if (!pca9685)
128 return -ENOMEM;
129
130 i2c_set_clientdata(client, pca9685);
131 pca9685_all_off(client);
132
133 for (i = 0; i < 16; i++) {
134 pca9685[i].client = client;
135 pca9685[i].led_num = i;
136 pca9685[i].name[0] = '\0';
137 if (pdata && i < pdata->leds.num_leds) {
138 if (pdata->leds.leds[i].name)
139 strncpy(pca9685[i].name,
140 pdata->leds.leds[i].name,
141 sizeof(pca9685[i].name)-1);
142 if (pdata->leds.leds[i].default_trigger)
143 pca9685[i].led_cdev.default_trigger =
144 pdata->leds.leds[i].default_trigger;
145 }
146 if (strlen(pca9685[i].name) == 0) {
147 /*
148 * Write adapter and address to the name as well.
149 * Otherwise multiple chips attached to one host would
150 * not work.
151 */
152 snprintf(pca9685[i].name, sizeof(pca9685[i].name),
153 "pca9685:%d:x%.2x:%d",
154 client->adapter->nr, client->addr, i);
155 }
156 pca9685[i].led_cdev.name = pca9685[i].name;
157 pca9685[i].led_cdev.max_brightness = 0xfff;
158 pca9685[i].led_cdev.brightness_set = pca9685_led_set;
159
160 INIT_WORK(&pca9685[i].work, pca9685_led_work);
161 err = led_classdev_register(&client->dev, &pca9685[i].led_cdev);
162 if (err < 0)
163 goto exit;
164 }
165
166 if (pdata)
167 i2c_smbus_write_byte_data(client, PCA9685_MODE2,
168 pdata->outdrv << PCA9685_OUTDRV |
169 pdata->inverted << PCA9685_INVRT);
170 else
171 i2c_smbus_write_byte_data(client, PCA9685_MODE2,
172 PCA9685_TOTEM_POLE << PCA9685_OUTDRV);
173 /* Enable Auto-Increment, enable oscillator, ALLCALL/SUBADDR disabled */
174 i2c_smbus_write_byte_data(client, PCA9685_MODE1, BIT(PCA9685_AI));
175
176 return 0;
177
178exit:
179 while (i--) {
180 led_classdev_unregister(&pca9685[i].led_cdev);
181 cancel_work_sync(&pca9685[i].work);
182 }
183 return err;
184}
185
186static int pca9685_remove(struct i2c_client *client)
187{
188 struct pca9685_led *pca9685 = i2c_get_clientdata(client);
189 u8 i;
190
191 for (i = 0; i < 16; i++) {
192 led_classdev_unregister(&pca9685[i].led_cdev);
193 cancel_work_sync(&pca9685[i].work);
194 }
195 pca9685_all_off(client);
196 return 0;
197}
198
199static struct i2c_driver pca9685_driver = {
200 .driver = {
201 .name = "leds-pca9685",
202 .owner = THIS_MODULE,
203 },
204 .probe = pca9685_probe,
205 .remove = pca9685_remove,
206 .id_table = pca9685_id,
207};
208
209module_i2c_driver(pca9685_driver);
210
211MODULE_AUTHOR("Maximilian Güntner <maximilian.guentner@gmail.com>");
212MODULE_DESCRIPTION("PCA9685 LED Driver");
213MODULE_LICENSE("GPL v2");
diff --git a/drivers/leds/leds-pwm.c b/drivers/leds/leds-pwm.c
index bb6f94898541..2848171b8576 100644
--- a/drivers/leds/leds-pwm.c
+++ b/drivers/leds/leds-pwm.c
@@ -232,7 +232,7 @@ static struct platform_driver led_pwm_driver = {
232 .driver = { 232 .driver = {
233 .name = "leds_pwm", 233 .name = "leds_pwm",
234 .owner = THIS_MODULE, 234 .owner = THIS_MODULE,
235 .of_match_table = of_match_ptr(of_pwm_leds_match), 235 .of_match_table = of_pwm_leds_match,
236 }, 236 },
237}; 237};
238 238
diff --git a/include/linux/of.h b/include/linux/of.h
index c08c07e249b3..ebf75f760bd3 100644
--- a/include/linux/of.h
+++ b/include/linux/of.h
@@ -226,6 +226,17 @@ static inline int of_get_child_count(const struct device_node *np)
226 return num; 226 return num;
227} 227}
228 228
229static inline int of_get_available_child_count(const struct device_node *np)
230{
231 struct device_node *child;
232 int num = 0;
233
234 for_each_available_child_of_node(np, child)
235 num++;
236
237 return num;
238}
239
229/* cache lookup */ 240/* cache lookup */
230extern struct device_node *of_find_next_cache_node(const struct device_node *); 241extern struct device_node *of_find_next_cache_node(const struct device_node *);
231extern struct device_node *of_find_node_with_property( 242extern struct device_node *of_find_node_with_property(
@@ -378,6 +389,11 @@ static inline int of_get_child_count(const struct device_node *np)
378 return 0; 389 return 0;
379} 390}
380 391
392static inline int of_get_available_child_count(const struct device_node *np)
393{
394 return 0;
395}
396
381static inline int of_device_is_compatible(const struct device_node *device, 397static inline int of_device_is_compatible(const struct device_node *device,
382 const char *name) 398 const char *name)
383{ 399{
diff --git a/include/linux/platform_data/leds-lp55xx.h b/include/linux/platform_data/leds-lp55xx.h
index 51a2ff579d60..624ff9edad6f 100644
--- a/include/linux/platform_data/leds-lp55xx.h
+++ b/include/linux/platform_data/leds-lp55xx.h
@@ -22,6 +22,7 @@
22 22
23struct lp55xx_led_config { 23struct lp55xx_led_config {
24 const char *name; 24 const char *name;
25 const char *default_trigger;
25 u8 chan_nr; 26 u8 chan_nr;
26 u8 led_current; /* mA x10, 0 if led is not connected */ 27 u8 led_current; /* mA x10, 0 if led is not connected */
27 u8 max_current; 28 u8 max_current;
@@ -66,10 +67,8 @@ struct lp55xx_platform_data {
66 /* Clock configuration */ 67 /* Clock configuration */
67 u8 clock_mode; 68 u8 clock_mode;
68 69
69 /* Platform specific functions */ 70 /* optional enable GPIO */
70 int (*setup_resources)(void); 71 int enable_gpio;
71 void (*release_resources)(void);
72 void (*enable)(bool state);
73 72
74 /* Predefined pattern data */ 73 /* Predefined pattern data */
75 struct lp55xx_predef_pattern *patterns; 74 struct lp55xx_predef_pattern *patterns;
diff --git a/include/linux/platform_data/leds-pca9685.h b/include/linux/platform_data/leds-pca9685.h
new file mode 100644
index 000000000000..778e9e4249cc
--- /dev/null
+++ b/include/linux/platform_data/leds-pca9685.h
@@ -0,0 +1,35 @@
1/*
2 * Copyright 2013 Maximilian Güntner <maximilian.guentner@gmail.com>
3 *
4 * This file is subject to the terms and conditions of version 2 of
5 * the GNU General Public License. See the file COPYING in the main
6 * directory of this archive for more details.
7 *
8 * Based on leds-pca963x.h by Peter Meerwald <p.meerwald@bct-electronic.com>
9 *
10 * LED driver for the NXP PCA9685 PWM chip
11 *
12 */
13
14#ifndef __LINUX_PCA9685_H
15#define __LINUX_PCA9685_H
16
17#include <linux/leds.h>
18
19enum pca9685_outdrv {
20 PCA9685_OPEN_DRAIN,
21 PCA9685_TOTEM_POLE,
22};
23
24enum pca9685_inverted {
25 PCA9685_NOT_INVERTED,
26 PCA9685_INVERTED,
27};
28
29struct pca9685_platform_data {
30 struct led_platform_data leds;
31 enum pca9685_outdrv outdrv;
32 enum pca9685_inverted inverted;
33};
34
35#endif /* __LINUX_PCA9685_H */