Lines Matching +full:led +full:- +full:2

1 // SPDX-License-Identifier: GPL-2.0-only
3 * pca9532.c - 16-bit Led dimmer
18 #include <linux/leds-pca9532.h>
26 #define PCA9532_REG_PSC(m, i) (PCA9532_REG_OFFSET(m) + 0x1 + (i) * 2)
27 #define PCA9532_REG_PWM(m, i) (PCA9532_REG_OFFSET(m) + 0x2 + (i) * 2)
28 #define LED_REG(m, led) (PCA9532_REG_OFFSET(m) + 0x5 + (led >> 2)) argument
29 #define LED_NUM(led) (led & 0x3) argument
30 #define LED_SHIFT(led) (LED_NUM(led) * 2) argument
31 #define LED_MASK(led) (0x3 << LED_SHIFT(led)) argument
49 u8 pwm[2];
50 u8 psc[2];
76 .num_leds = 2,
103 .name = "leds-pca953x",
121 for (i = 0; i < data->chip_info->num_leds; i++) { in pca9532_calcpwm()
122 if (data->leds[i].type == PCA9532_TYPE_LED && in pca9532_calcpwm()
123 data->leds[i].state == PCA9532_PWM0+pwm) { in pca9532_calcpwm()
125 b += data->leds[i].ldev.brightness; in pca9532_calcpwm()
129 dev_err(&client->dev, in pca9532_calcpwm()
132 return -EINVAL; in pca9532_calcpwm()
136 return -EINVAL; in pca9532_calcpwm()
137 data->pwm[pwm] = b; in pca9532_calcpwm()
138 data->psc[pwm] = blink; in pca9532_calcpwm()
145 u8 maxleds = data->chip_info->num_leds; in pca9532_setpwm()
147 mutex_lock(&data->update_lock); in pca9532_setpwm()
149 data->pwm[pwm]); in pca9532_setpwm()
151 data->psc[pwm]); in pca9532_setpwm()
152 mutex_unlock(&data->update_lock); in pca9532_setpwm()
156 /* Set LED routing */
157 static void pca9532_setled(struct pca9532_led *led) in pca9532_setled() argument
159 struct i2c_client *client = led->client; in pca9532_setled()
161 u8 maxleds = data->chip_info->num_leds; in pca9532_setled()
164 mutex_lock(&data->update_lock); in pca9532_setled()
165 reg = i2c_smbus_read_byte_data(client, LED_REG(maxleds, led->id)); in pca9532_setled()
166 /* zero led bits */ in pca9532_setled()
167 reg = reg & ~LED_MASK(led->id); in pca9532_setled()
169 reg = reg | (led->state << LED_SHIFT(led->id)); in pca9532_setled()
170 i2c_smbus_write_byte_data(client, LED_REG(maxleds, led->id), reg); in pca9532_setled()
171 mutex_unlock(&data->update_lock); in pca9532_setled()
178 struct pca9532_led *led = ldev_to_led(led_cdev); in pca9532_set_brightness() local
181 led->state = PCA9532_OFF; in pca9532_set_brightness()
183 led->state = PCA9532_ON; in pca9532_set_brightness()
185 led->state = PCA9532_PWM0; /* Thecus: hardcode one pwm */ in pca9532_set_brightness()
186 err = pca9532_calcpwm(led->client, 0, 0, value); in pca9532_set_brightness()
190 if (led->state == PCA9532_PWM0) in pca9532_set_brightness()
191 pca9532_setpwm(led->client, 0); in pca9532_set_brightness()
192 pca9532_setled(led); in pca9532_set_brightness()
199 struct pca9532_led *led = ldev_to_led(led_cdev); in pca9532_set_blink() local
200 struct i2c_client *client = led->client; in pca9532_set_blink()
205 /* led subsystem ask us for a blink rate */ in pca9532_set_blink()
210 return -EINVAL; in pca9532_set_blink()
213 psc = (*delay_on * 152-1)/1000; in pca9532_set_blink()
214 err = pca9532_calcpwm(client, 0, psc, led_cdev->brightness); in pca9532_set_blink()
217 if (led->state == PCA9532_PWM0) in pca9532_set_blink()
218 pca9532_setpwm(led->client, 0); in pca9532_set_blink()
219 pca9532_setled(led); in pca9532_set_blink()
230 return -1; in pca9532_event()
234 data->pwm[1] = 127; in pca9532_event()
236 data->pwm[1] = 0; in pca9532_event()
238 schedule_work(&data->work); in pca9532_event()
247 u8 maxleds = data->chip_info->num_leds; in pca9532_input_work()
249 mutex_lock(&data->update_lock); in pca9532_input_work()
250 i2c_smbus_write_byte_data(data->client, PCA9532_REG_PWM(maxleds, 1), in pca9532_input_work()
251 data->pwm[1]); in pca9532_input_work()
252 mutex_unlock(&data->update_lock); in pca9532_input_work()
255 static enum pca9532_state pca9532_getled(struct pca9532_led *led) in pca9532_getled() argument
257 struct i2c_client *client = led->client; in pca9532_getled()
259 u8 maxleds = data->chip_info->num_leds; in pca9532_getled()
263 mutex_lock(&data->update_lock); in pca9532_getled()
264 reg = i2c_smbus_read_byte_data(client, LED_REG(maxleds, led->id)); in pca9532_getled()
265 ret = (reg & LED_MASK(led->id)) >> LED_SHIFT(led->id); in pca9532_getled()
266 mutex_unlock(&data->update_lock); in pca9532_getled()
274 struct pca9532_led *led = &data->leds[offset]; in pca9532_gpio_request_pin() local
276 if (led->type == PCA9532_TYPE_GPIO) in pca9532_gpio_request_pin()
279 return -EBUSY; in pca9532_gpio_request_pin()
285 struct pca9532_led *led = &data->leds[offset]; in pca9532_gpio_set_value() local
288 led->state = PCA9532_ON; in pca9532_gpio_set_value()
290 led->state = PCA9532_OFF; in pca9532_gpio_set_value()
292 pca9532_setled(led); in pca9532_gpio_set_value()
300 reg = i2c_smbus_read_byte_data(data->client, PCA9532_REG_INPUT(offset)); in pca9532_gpio_get_value()
326 return -EINVAL; in pca9532_destroy_devices()
328 while (--i >= 0) { in pca9532_destroy_devices()
329 switch (data->leds[i].type) { in pca9532_destroy_devices()
334 led_classdev_unregister(&data->leds[i].ldev); in pca9532_destroy_devices()
337 if (data->idev != NULL) { in pca9532_destroy_devices()
338 cancel_work_sync(&data->work); in pca9532_destroy_devices()
339 data->idev = NULL; in pca9532_destroy_devices()
346 if (data->gpio.parent) in pca9532_destroy_devices()
347 gpiochip_remove(&data->gpio); in pca9532_destroy_devices()
358 u8 maxleds = data->chip_info->num_leds; in pca9532_configure()
360 for (i = 0; i < 2; i++) { in pca9532_configure()
361 data->pwm[i] = pdata->pwm[i]; in pca9532_configure()
362 data->psc[i] = pdata->psc[i]; in pca9532_configure()
364 data->pwm[i]); in pca9532_configure()
366 data->psc[i]); in pca9532_configure()
369 for (i = 0; i < data->chip_info->num_leds; i++) { in pca9532_configure()
370 struct pca9532_led *led = &data->leds[i]; in pca9532_configure() local
371 struct pca9532_led *pled = &pdata->leds[i]; in pca9532_configure()
372 led->client = client; in pca9532_configure()
373 led->id = i; in pca9532_configure()
374 led->type = pled->type; in pca9532_configure()
375 switch (led->type) { in pca9532_configure()
382 if (pled->state == PCA9532_KEEP) in pca9532_configure()
383 led->state = pca9532_getled(led); in pca9532_configure()
385 led->state = pled->state; in pca9532_configure()
386 led->name = pled->name; in pca9532_configure()
387 led->ldev.name = led->name; in pca9532_configure()
388 led->ldev.default_trigger = pled->default_trigger; in pca9532_configure()
389 led->ldev.brightness = LED_OFF; in pca9532_configure()
390 led->ldev.brightness_set_blocking = in pca9532_configure()
392 led->ldev.blink_set = pca9532_set_blink; in pca9532_configure()
393 err = led_classdev_register(&client->dev, &led->ldev); in pca9532_configure()
395 dev_err(&client->dev, in pca9532_configure()
396 "couldn't register LED %s\n", in pca9532_configure()
397 led->name); in pca9532_configure()
400 pca9532_setled(led); in pca9532_configure()
403 BUG_ON(data->idev); in pca9532_configure()
404 led->state = PCA9532_PWM1; in pca9532_configure()
405 pca9532_setled(led); in pca9532_configure()
406 data->idev = devm_input_allocate_device(&client->dev); in pca9532_configure()
407 if (data->idev == NULL) { in pca9532_configure()
408 err = -ENOMEM; in pca9532_configure()
411 data->idev->name = pled->name; in pca9532_configure()
412 data->idev->phys = "i2c/pca9532"; in pca9532_configure()
413 data->idev->id.bustype = BUS_HOST; in pca9532_configure()
414 data->idev->id.vendor = 0x001f; in pca9532_configure()
415 data->idev->id.product = 0x0001; in pca9532_configure()
416 data->idev->id.version = 0x0100; in pca9532_configure()
417 data->idev->evbit[0] = BIT_MASK(EV_SND); in pca9532_configure()
418 data->idev->sndbit[0] = BIT_MASK(SND_BELL) | in pca9532_configure()
420 data->idev->event = pca9532_event; in pca9532_configure()
421 input_set_drvdata(data->idev, data); in pca9532_configure()
422 INIT_WORK(&data->work, pca9532_input_work); in pca9532_configure()
423 err = input_register_device(data->idev); in pca9532_configure()
425 cancel_work_sync(&data->work); in pca9532_configure()
426 data->idev = NULL; in pca9532_configure()
435 data->gpio.label = "gpio-pca9532"; in pca9532_configure()
436 data->gpio.direction_input = pca9532_gpio_direction_input; in pca9532_configure()
437 data->gpio.direction_output = pca9532_gpio_direction_output; in pca9532_configure()
438 data->gpio.set = pca9532_gpio_set_value; in pca9532_configure()
439 data->gpio.get = pca9532_gpio_get_value; in pca9532_configure()
440 data->gpio.request = pca9532_gpio_request_pin; in pca9532_configure()
441 data->gpio.can_sleep = 1; in pca9532_configure()
442 data->gpio.base = pdata->gpio_base; in pca9532_configure()
443 data->gpio.ngpio = data->chip_info->num_leds; in pca9532_configure()
444 data->gpio.parent = &client->dev; in pca9532_configure()
445 data->gpio.owner = THIS_MODULE; in pca9532_configure()
447 err = gpiochip_add_data(&data->gpio, data); in pca9532_configure()
449 /* Use data->gpio.dev as a flag for freeing gpiochip */ in pca9532_configure()
450 data->gpio.parent = NULL; in pca9532_configure()
451 dev_warn(&client->dev, "could not add gpiochip\n"); in pca9532_configure()
453 dev_info(&client->dev, "gpios %i...%i\n", in pca9532_configure()
454 data->gpio.base, data->gpio.base + in pca9532_configure()
455 data->gpio.ngpio - 1); in pca9532_configure()
481 return ERR_PTR(-ENOMEM); in pca9532_of_populate_pdata()
483 of_property_read_u8_array(np, "nxp,pwm", &pdata->pwm[0], in pca9532_of_populate_pdata()
484 ARRAY_SIZE(pdata->pwm)); in pca9532_of_populate_pdata()
485 of_property_read_u8_array(np, "nxp,psc", &pdata->psc[0], in pca9532_of_populate_pdata()
486 ARRAY_SIZE(pdata->psc)); in pca9532_of_populate_pdata()
490 &pdata->leds[i].name)) in pca9532_of_populate_pdata()
491 pdata->leds[i].name = child->name; in pca9532_of_populate_pdata()
492 of_property_read_u32(child, "type", &pdata->leds[i].type); in pca9532_of_populate_pdata()
493 of_property_read_string(child, "linux,default-trigger", in pca9532_of_populate_pdata()
494 &pdata->leds[i].default_trigger); in pca9532_of_populate_pdata()
495 if (!of_property_read_string(child, "default-state", &state)) { in pca9532_of_populate_pdata()
497 pdata->leds[i].state = PCA9532_ON; in pca9532_of_populate_pdata()
499 pdata->leds[i].state = PCA9532_KEEP; in pca9532_of_populate_pdata()
516 dev_get_platdata(&client->dev); in pca9532_probe()
517 struct device_node *np = dev_of_node(&client->dev); in pca9532_probe()
522 pca9532_of_populate_pdata(&client->dev, np); in pca9532_probe()
526 dev_err(&client->dev, "no platform data\n"); in pca9532_probe()
527 return -EINVAL; in pca9532_probe()
529 devid = (int)(uintptr_t)of_device_get_match_data(&client->dev); in pca9532_probe()
531 devid = id->driver_data; in pca9532_probe()
534 if (!i2c_check_functionality(client->adapter, in pca9532_probe()
536 return -EIO; in pca9532_probe()
538 data = devm_kzalloc(&client->dev, sizeof(*data), GFP_KERNEL); in pca9532_probe()
540 return -ENOMEM; in pca9532_probe()
542 data->chip_info = &pca9532_chip_info_tbl[devid]; in pca9532_probe()
544 dev_info(&client->dev, "setting platform data\n"); in pca9532_probe()
546 data->client = client; in pca9532_probe()
547 mutex_init(&data->update_lock); in pca9532_probe()
556 return pca9532_destroy_devices(data, data->chip_info->num_leds); in pca9532_remove()
563 MODULE_DESCRIPTION("PCA 9532 LED dimmer");