20 #include <linux/module.h>
22 #include <linux/slab.h>
24 #include <linux/i2c.h>
34 static const unsigned short normal_i2c[] = { 0x09,
I2C_CLIENT_END };
51 #define cdev_to_blmled(c) container_of(c, struct blinkm_led, led_cdev)
52 #define work_to_blmwork(c) container_of(c, struct blinkm_work, work)
95 #define BLM_FADE_RGB 1
96 #define BLM_FADE_HSB 2
97 #define BLM_FADE_RAND_RGB 3
98 #define BLM_FADE_RAND_HSB 4
99 #define BLM_PLAY_SCRIPT 5
100 #define BLM_STOP_SCRIPT 6
101 #define BLM_SET_FADE_SPEED 7
102 #define BLM_SET_TIME_ADJ 8
103 #define BLM_GET_CUR_RGB 9
104 #define BLM_WRITE_SCRIPT_LINE 10
105 #define BLM_READ_SCRIPT_LINE 11
106 #define BLM_SET_SCRIPT_LR 12
107 #define BLM_SET_ADDR 13
108 #define BLM_GET_ADDR 14
109 #define BLM_GET_FW_VER 15
110 #define BLM_SET_STARTUP_PARAM 16
122 static const struct {
128 } blinkm_cmds[17] = {
130 {
'n', 0x6e, 3, 0, 1},
131 {
'c', 0x63, 3, 0, 1},
132 {
'h', 0x68, 3, 0, 1},
133 {
'C', 0x43, 3, 0, 1},
134 {
'H', 0x48, 3, 0, 1},
135 {
'p', 0x70, 3, 0, 1},
136 {
'o', 0x6f, 0, 0, 1},
137 {
'f', 0x66, 1, 0, 1},
138 {
't', 0x74, 1, 0, 1},
139 {
'g', 0x67, 0, 3, 0},
140 {
'W', 0x57, 7, 0, 1},
141 {
'R', 0x52, 2, 5, 2},
142 {
'L', 0x4c, 3, 0, 1},
143 {
'A', 0x41, 4, 0, 1},
144 {
'a', 0x61, 0, 1, 0},
145 {
'Z', 0x5a, 0, 1, 0},
146 {
'B', 0x42, 5, 0, 1},
156 data = i2c_get_clientdata(client);
177 static int store_color_common(
struct device *dev,
const char *buf,
int color)
185 data = i2c_get_clientdata(client);
189 dev_err(dev,
"BlinkM: value too large!\n");
207 dev_dbg(dev,
"next_red = %d, next_green = %d, next_blue = %d\n",
213 dev_err(dev,
"BlinkM: can't set RGB\n");
222 return show_color_common(dev, buf,
RED);
226 const char *buf,
size_t count)
230 ret = store_color_common(dev, buf,
RED);
241 return show_color_common(dev, buf,
GREEN);
245 const char *buf,
size_t count)
250 ret = store_color_common(dev, buf,
GREEN);
261 return show_color_common(dev, buf,
BLUE);
265 const char *buf,
size_t count)
269 ret = store_color_common(dev, buf,
BLUE);
281 "#Write into test to start test sequence!#\n");
285 const char *buf,
size_t count)
293 ret = blinkm_test_run(client);
304 static struct attribute *blinkm_attrs[] = {
306 &dev_attr_green.attr,
314 .attrs = blinkm_attrs,
321 int arglen = blinkm_cmds[
cmd].nr_args;
330 for (i = 0; i < arglen; i++) {
339 static int blinkm_read(
struct i2c_client *client,
int cmd,
u8 *arg)
343 int retlen = blinkm_cmds[
cmd].nr_ret;
344 for (i = 0; i < retlen; i++) {
355 static int blinkm_transfer_hw(
struct i2c_client *client,
int cmd)
369 struct blinkm_data *data = i2c_get_clientdata(client);
384 blinkm_write(client, cmd, data->
args);
394 blinkm_write(client, cmd, data->
args);
403 blinkm_write(client, cmd, data->
args);
406 blinkm_write(client, cmd,
NULL);
412 blinkm_write(client, cmd,
NULL);
413 blinkm_read(client, cmd, data->
args);
420 blinkm_write(client, cmd,
NULL);
421 blinkm_read(client, cmd, data->
args);
433 "BlinkM: cmd %d not implemented yet.\n", cmd);
436 dev_err(&client->
dev,
"BlinkM: unknown command %d\n", cmd);
458 "# DONE # next_red = %d, next_green = %d,"
459 " next_blue = %d, active = %d\n",
465 static int blinkm_led_common_set(
struct led_classdev *led_cdev,
513 bl_work = kzalloc(
sizeof(*bl_work),
GFP_ATOMIC);
519 "#TO_SCHED# next_red = %d, next_green = %d,"
520 " next_blue = %d, active = %d\n",
533 static void blinkm_led_red_set(
struct led_classdev *led_cdev,
536 blinkm_led_common_set(led_cdev, value,
RED);
539 static void blinkm_led_green_set(
struct led_classdev *led_cdev,
542 blinkm_led_common_set(led_cdev, value,
GREEN);
545 static void blinkm_led_blue_set(
struct led_classdev *led_cdev,
548 blinkm_led_common_set(led_cdev, value,
BLUE);
551 static void blinkm_init_hw(
struct i2c_client *client)
558 static int blinkm_test_run(
struct i2c_client *client)
561 struct blinkm_data *data = i2c_get_clientdata(client);
612 if (tmpargs[0] == 0x09)
626 if (tmpargs[0] != 0x09) {
627 dev_err(&client->
dev,
"enodev DEV ADDR = 0x%02X\n", tmpargs[0]);
641 char blinkm_led_name[28];
659 i2c_set_clientdata(client, data);
665 dev_err(&client->
dev,
"couldn't register sysfs group\n");
669 for (i = 0; i < 3; i++) {
679 snprintf(blinkm_led_name,
sizeof(blinkm_led_name),
684 led[
i]->
led_cdev.brightness_set = blinkm_led_red_set;
689 "couldn't register LED %s\n",
695 snprintf(blinkm_led_name,
sizeof(blinkm_led_name),
696 "blinkm-%d-%d-green",
700 led[
i]->
led_cdev.brightness_set = blinkm_led_green_set;
705 "couldn't register LED %s\n",
711 snprintf(blinkm_led_name,
sizeof(blinkm_led_name),
716 led[
i]->
led_cdev.brightness_set = blinkm_led_blue_set;
721 "couldn't register LED %s\n",
730 blinkm_init_hw(client);
748 struct blinkm_data *data = i2c_get_clientdata(client);
753 for (i = 0; i < 3; i++) {
764 dev_err(&client->
dev,
"Failure in blinkm_remove ignored. Continuing.\n");
772 dev_err(&client->
dev,
"Failure in blinkm_remove ignored. Continuing.\n");
778 dev_err(&client->
dev,
"Failure in blinkm_remove ignored. Continuing.\n");
784 dev_err(&client->
dev,
"Failure in blinkm_remove ignored. Continuing.\n");
803 .probe = blinkm_probe,
805 .id_table = blinkm_id,
806 .detect = blinkm_detect,
807 .address_list = normal_i2c,