Lines Matching +full:led +full:- +full:red

1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * leds-blinkm.c
4 * (c) Jan-Simon Möller (dl9pf@gmx.de)
19 /* Addresses to scan - BlinkM is on 0x09 by default*/
36 /* used for led class interface */
39 u8 red; /* color red */ member
43 u8 next_red; /* color red */
58 u8 fade_speed; /* fade speed 1 - 255 */
59 s8 time_adjust; /* time adjust -128 - 127 */
68 #define RED 0 macro
72 /* mapping command names to cmd chars - see datasheet */
141 case RED: in show_color_common()
142 return sysfs_emit(buf, "%02X\n", data->red); in show_color_common()
144 return sysfs_emit(buf, "%02X\n", data->green); in show_color_common()
146 return sysfs_emit(buf, "%02X\n", data->blue); in show_color_common()
148 return -EINVAL; in show_color_common()
150 return -EINVAL; in show_color_common()
170 case RED: in store_color_common()
171 data->next_red = value; in store_color_common()
174 data->next_green = value; in store_color_common()
177 data->next_blue = value; in store_color_common()
180 return -EINVAL; in store_color_common()
184 data->next_red, data->next_green, data->next_blue); in store_color_common()
198 return show_color_common(dev, buf, RED); in red_show()
206 ret = store_color_common(dev, buf, RED); in red_store()
212 static DEVICE_ATTR_RW(red);
298 /* write out cmd to blinkm - always / default step */ in blinkm_write()
333 /* the protocol is simple but non-standard: in blinkm_transfer_hw()
335 * - which defaults to 0x09 - would be the sequence: in blinkm_transfer_hw()
349 if (mutex_lock_interruptible(&data->update_lock) < 0) in blinkm_transfer_hw()
350 return -EAGAIN; in blinkm_transfer_hw()
352 /* switch cmd - usually write before reads */ in blinkm_transfer_hw()
357 data->args[0] = data->next_red; in blinkm_transfer_hw()
358 data->args[1] = data->next_green; in blinkm_transfer_hw()
359 data->args[2] = data->next_blue; in blinkm_transfer_hw()
360 blinkm_write(client, cmd, data->args); in blinkm_transfer_hw()
361 data->red = data->args[0]; in blinkm_transfer_hw()
362 data->green = data->args[1]; in blinkm_transfer_hw()
363 data->blue = data->args[2]; in blinkm_transfer_hw()
367 data->args[0] = data->next_hue; in blinkm_transfer_hw()
368 data->args[1] = data->next_saturation; in blinkm_transfer_hw()
369 data->args[2] = data->next_brightness; in blinkm_transfer_hw()
370 blinkm_write(client, cmd, data->args); in blinkm_transfer_hw()
371 data->hue = data->next_hue; in blinkm_transfer_hw()
372 data->saturation = data->next_saturation; in blinkm_transfer_hw()
373 data->brightness = data->next_brightness; in blinkm_transfer_hw()
376 data->args[0] = data->script_id; in blinkm_transfer_hw()
377 data->args[1] = data->script_repeats; in blinkm_transfer_hw()
378 data->args[2] = data->script_startline; in blinkm_transfer_hw()
379 blinkm_write(client, cmd, data->args); in blinkm_transfer_hw()
385 data->args[0] = data->red; in blinkm_transfer_hw()
386 data->args[1] = data->green; in blinkm_transfer_hw()
387 data->args[2] = data->blue; in blinkm_transfer_hw()
389 blinkm_read(client, cmd, data->args); in blinkm_transfer_hw()
390 data->red = data->args[0]; in blinkm_transfer_hw()
391 data->green = data->args[1]; in blinkm_transfer_hw()
392 data->blue = data->args[2]; in blinkm_transfer_hw()
395 data->args[0] = data->i2c_addr; in blinkm_transfer_hw()
397 blinkm_read(client, cmd, data->args); in blinkm_transfer_hw()
398 data->i2c_addr = data->args[0]; in blinkm_transfer_hw()
408 dev_err(&client->dev, in blinkm_transfer_hw()
412 dev_err(&client->dev, "BlinkM: unknown command %d\n", cmd); in blinkm_transfer_hw()
413 mutex_unlock(&data->update_lock); in blinkm_transfer_hw()
414 return -EINVAL; in blinkm_transfer_hw()
418 mutex_unlock(&data->update_lock); in blinkm_transfer_hw()
425 /* led_brightness is 0, 127 or 255 - we just use it here as-is */ in blinkm_led_common_set()
426 struct blinkm_led *led = cdev_to_blmled(led_cdev); in blinkm_led_common_set() local
427 struct blinkm_data *data = i2c_get_clientdata(led->i2c_client); in blinkm_led_common_set()
430 case RED: in blinkm_led_common_set()
432 if (data->next_red == (u8) value) in blinkm_led_common_set()
434 data->next_red = (u8) value; in blinkm_led_common_set()
438 if (data->next_green == (u8) value) in blinkm_led_common_set()
440 data->next_green = (u8) value; in blinkm_led_common_set()
444 if (data->next_blue == (u8) value) in blinkm_led_common_set()
446 data->next_blue = (u8) value; in blinkm_led_common_set()
450 dev_err(&led->i2c_client->dev, "BlinkM: unknown color.\n"); in blinkm_led_common_set()
451 return -EINVAL; in blinkm_led_common_set()
454 blinkm_transfer_hw(led->i2c_client, BLM_GO_RGB); in blinkm_led_common_set()
455 dev_dbg(&led->i2c_client->dev, in blinkm_led_common_set()
458 data->next_red, data->next_green, in blinkm_led_common_set()
459 data->next_blue); in blinkm_led_common_set()
466 return blinkm_led_common_set(led_cdev, value, RED); in blinkm_led_red_set()
492 data->next_red = 0x01; in blinkm_test_run()
493 data->next_green = 0x05; in blinkm_test_run()
494 data->next_blue = 0x10; in blinkm_test_run()
500 data->next_red = 0x25; in blinkm_test_run()
501 data->next_green = 0x10; in blinkm_test_run()
502 data->next_blue = 0x31; in blinkm_test_run()
508 data->next_hue = 0x50; in blinkm_test_run()
509 data->next_saturation = 0x10; in blinkm_test_run()
510 data->next_brightness = 0x20; in blinkm_test_run()
519 /* Return 0 if detection is successful, -ENODEV otherwise */
522 struct i2c_adapter *adapter = client->adapter; in blinkm_detect()
530 return -ENODEV; in blinkm_detect()
547 count--; in blinkm_detect()
550 /* Step 1: Read BlinkM address back - cmd_char 'a' */ in blinkm_detect()
560 dev_err(&client->dev, "enodev DEV ADDR = 0x%02X\n", tmpargs[0]); in blinkm_detect()
561 return -ENODEV; in blinkm_detect()
564 strscpy(info->type, "blinkm", I2C_NAME_SIZE); in blinkm_detect()
571 struct blinkm_led *led[3]; in blinkm_probe() local
575 data = devm_kzalloc(&client->dev, in blinkm_probe()
578 err = -ENOMEM; in blinkm_probe()
582 data->i2c_addr = 0x08; in blinkm_probe()
583 /* i2c addr - use fake addr of 0x08 initially (real is 0x09) */ in blinkm_probe()
584 data->fw_ver = 0xfe; in blinkm_probe()
585 /* firmware version - use fake until we read real value in blinkm_probe()
586 * (currently broken - BlinkM confused!) */ in blinkm_probe()
587 data->script_id = 0x01; in blinkm_probe()
588 data->i2c_client = client; in blinkm_probe()
591 mutex_init(&data->update_lock); in blinkm_probe()
594 err = sysfs_create_group(&client->dev.kobj, &blinkm_group); in blinkm_probe()
596 dev_err(&client->dev, "couldn't register sysfs group\n"); in blinkm_probe()
601 /* RED = 0, GREEN = 1, BLUE = 2 */ in blinkm_probe()
602 led[i] = &data->blinkm_leds[i]; in blinkm_probe()
603 led[i]->i2c_client = client; in blinkm_probe()
604 led[i]->id = i; in blinkm_probe()
605 led[i]->led_cdev.max_brightness = 255; in blinkm_probe()
606 led[i]->led_cdev.flags = LED_CORE_SUSPENDRESUME; in blinkm_probe()
608 case RED: in blinkm_probe()
610 "blinkm-%d-%d-red", in blinkm_probe()
611 client->adapter->nr, in blinkm_probe()
612 client->addr); in blinkm_probe()
613 led[i]->led_cdev.name = blinkm_led_name; in blinkm_probe()
614 led[i]->led_cdev.brightness_set_blocking = in blinkm_probe()
616 err = led_classdev_register(&client->dev, in blinkm_probe()
617 &led[i]->led_cdev); in blinkm_probe()
619 dev_err(&client->dev, in blinkm_probe()
620 "couldn't register LED %s\n", in blinkm_probe()
621 led[i]->led_cdev.name); in blinkm_probe()
627 "blinkm-%d-%d-green", in blinkm_probe()
628 client->adapter->nr, in blinkm_probe()
629 client->addr); in blinkm_probe()
630 led[i]->led_cdev.name = blinkm_led_name; in blinkm_probe()
631 led[i]->led_cdev.brightness_set_blocking = in blinkm_probe()
633 err = led_classdev_register(&client->dev, in blinkm_probe()
634 &led[i]->led_cdev); in blinkm_probe()
636 dev_err(&client->dev, in blinkm_probe()
637 "couldn't register LED %s\n", in blinkm_probe()
638 led[i]->led_cdev.name); in blinkm_probe()
644 "blinkm-%d-%d-blue", in blinkm_probe()
645 client->adapter->nr, in blinkm_probe()
646 client->addr); in blinkm_probe()
647 led[i]->led_cdev.name = blinkm_led_name; in blinkm_probe()
648 led[i]->led_cdev.brightness_set_blocking = in blinkm_probe()
650 err = led_classdev_register(&client->dev, in blinkm_probe()
651 &led[i]->led_cdev); in blinkm_probe()
653 dev_err(&client->dev, in blinkm_probe()
654 "couldn't register LED %s\n", in blinkm_probe()
655 led[i]->led_cdev.name); in blinkm_probe()
668 led_classdev_unregister(&led[GREEN]->led_cdev); in blinkm_probe()
671 led_classdev_unregister(&led[RED]->led_cdev); in blinkm_probe()
674 sysfs_remove_group(&client->dev.kobj, &blinkm_group); in blinkm_probe()
687 led_classdev_unregister(&data->blinkm_leds[i].led_cdev); in blinkm_remove()
690 data->next_red = 0x00; in blinkm_remove()
691 data->next_green = 0x00; in blinkm_remove()
692 data->next_blue = 0x00; in blinkm_remove()
695 dev_err(&client->dev, "Failure in blinkm_remove ignored. Continuing.\n"); in blinkm_remove()
698 data->next_hue = 0x00; in blinkm_remove()
699 data->next_saturation = 0x00; in blinkm_remove()
700 data->next_brightness = 0x00; in blinkm_remove()
703 dev_err(&client->dev, "Failure in blinkm_remove ignored. Continuing.\n"); in blinkm_remove()
705 /* red fade to off */ in blinkm_remove()
706 data->next_red = 0xff; in blinkm_remove()
709 dev_err(&client->dev, "Failure in blinkm_remove ignored. Continuing.\n"); in blinkm_remove()
712 data->next_red = 0x00; in blinkm_remove()
715 dev_err(&client->dev, "Failure in blinkm_remove ignored. Continuing.\n"); in blinkm_remove()
717 sysfs_remove_group(&client->dev.kobj, &blinkm_group); in blinkm_remove()
742 MODULE_AUTHOR("Jan-Simon Moeller <dl9pf@gmx.de>");
743 MODULE_DESCRIPTION("BlinkM RGB LED driver");