aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/hid
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/hid')
-rw-r--r--drivers/hid/hid-roccat-koneplus.c371
-rw-r--r--drivers/hid/hid-roccat-koneplus.h99
2 files changed, 102 insertions, 368 deletions
diff --git a/drivers/hid/hid-roccat-koneplus.c b/drivers/hid/hid-roccat-koneplus.c
index 69592f427579..9fe445082308 100644
--- a/drivers/hid/hid-roccat-koneplus.c
+++ b/drivers/hid/hid-roccat-koneplus.c
@@ -56,56 +56,6 @@ static int koneplus_send_control(struct usb_device *usb_dev, uint value,
56 &control, sizeof(struct roccat_common2_control)); 56 &control, sizeof(struct roccat_common2_control));
57} 57}
58 58
59static int koneplus_get_info(struct usb_device *usb_dev,
60 struct koneplus_info *buf)
61{
62 return roccat_common2_receive(usb_dev, KONEPLUS_COMMAND_INFO,
63 buf, sizeof(struct koneplus_info));
64}
65
66static int koneplus_get_profile_settings(struct usb_device *usb_dev,
67 struct koneplus_profile_settings *buf, uint number)
68{
69 int retval;
70
71 retval = koneplus_send_control(usb_dev, number,
72 KONEPLUS_CONTROL_REQUEST_PROFILE_SETTINGS);
73 if (retval)
74 return retval;
75
76 return roccat_common2_receive(usb_dev, KONEPLUS_COMMAND_PROFILE_SETTINGS,
77 buf, sizeof(struct koneplus_profile_settings));
78}
79
80static int koneplus_set_profile_settings(struct usb_device *usb_dev,
81 struct koneplus_profile_settings const *settings)
82{
83 return roccat_common2_send_with_status(usb_dev,
84 KONEPLUS_COMMAND_PROFILE_SETTINGS,
85 settings, sizeof(struct koneplus_profile_settings));
86}
87
88static int koneplus_get_profile_buttons(struct usb_device *usb_dev,
89 struct koneplus_profile_buttons *buf, int number)
90{
91 int retval;
92
93 retval = koneplus_send_control(usb_dev, number,
94 KONEPLUS_CONTROL_REQUEST_PROFILE_BUTTONS);
95 if (retval)
96 return retval;
97
98 return roccat_common2_receive(usb_dev, KONEPLUS_COMMAND_PROFILE_BUTTONS,
99 buf, sizeof(struct koneplus_profile_buttons));
100}
101
102static int koneplus_set_profile_buttons(struct usb_device *usb_dev,
103 struct koneplus_profile_buttons const *buttons)
104{
105 return roccat_common2_send_with_status(usb_dev,
106 KONEPLUS_COMMAND_PROFILE_BUTTONS,
107 buttons, sizeof(struct koneplus_profile_buttons));
108}
109 59
110/* retval is 0-4 on success, < 0 on error */ 60/* retval is 0-4 on success, < 0 on error */
111static int koneplus_get_actual_profile(struct usb_device *usb_dev) 61static int koneplus_get_actual_profile(struct usb_device *usb_dev)
@@ -114,7 +64,7 @@ static int koneplus_get_actual_profile(struct usb_device *usb_dev)
114 int retval; 64 int retval;
115 65
116 retval = roccat_common2_receive(usb_dev, KONEPLUS_COMMAND_ACTUAL_PROFILE, 66 retval = roccat_common2_receive(usb_dev, KONEPLUS_COMMAND_ACTUAL_PROFILE,
117 &buf, sizeof(struct koneplus_actual_profile)); 67 &buf, KONEPLUS_SIZE_ACTUAL_PROFILE);
118 68
119 return retval ? retval : buf.actual_profile; 69 return retval ? retval : buf.actual_profile;
120} 70}
@@ -125,12 +75,12 @@ static int koneplus_set_actual_profile(struct usb_device *usb_dev,
125 struct koneplus_actual_profile buf; 75 struct koneplus_actual_profile buf;
126 76
127 buf.command = KONEPLUS_COMMAND_ACTUAL_PROFILE; 77 buf.command = KONEPLUS_COMMAND_ACTUAL_PROFILE;
128 buf.size = sizeof(struct koneplus_actual_profile); 78 buf.size = KONEPLUS_SIZE_ACTUAL_PROFILE;
129 buf.actual_profile = new_profile; 79 buf.actual_profile = new_profile;
130 80
131 return roccat_common2_send_with_status(usb_dev, 81 return roccat_common2_send_with_status(usb_dev,
132 KONEPLUS_COMMAND_ACTUAL_PROFILE, 82 KONEPLUS_COMMAND_ACTUAL_PROFILE,
133 &buf, sizeof(struct koneplus_actual_profile)); 83 &buf, KONEPLUS_SIZE_ACTUAL_PROFILE);
134} 84}
135 85
136static ssize_t koneplus_sysfs_read(struct file *fp, struct kobject *kobj, 86static ssize_t koneplus_sysfs_read(struct file *fp, struct kobject *kobj,
@@ -183,77 +133,58 @@ static ssize_t koneplus_sysfs_write(struct file *fp, struct kobject *kobj,
183 return real_size; 133 return real_size;
184} 134}
185 135
186static ssize_t koneplus_sysfs_read_info(struct file *fp, 136#define KONEPLUS_SYSFS_W(thingy, THINGY) \
187 struct kobject *kobj, struct bin_attribute *attr, char *buf, 137static ssize_t koneplus_sysfs_write_ ## thingy(struct file *fp, \
188 loff_t off, size_t count) 138 struct kobject *kobj, struct bin_attribute *attr, char *buf, \
189{ 139 loff_t off, size_t count) \
190 return koneplus_sysfs_read(fp, kobj, buf, off, count, 140{ \
191 sizeof(struct koneplus_info), KONEPLUS_COMMAND_INFO); 141 return koneplus_sysfs_write(fp, kobj, buf, off, count, \
142 KONEPLUS_SIZE_ ## THINGY, KONEPLUS_COMMAND_ ## THINGY); \
192} 143}
193 144
194static ssize_t koneplus_sysfs_write_info(struct file *fp, 145#define KONEPLUS_SYSFS_R(thingy, THINGY) \
195 struct kobject *kobj, struct bin_attribute *attr, char *buf, 146static ssize_t koneplus_sysfs_read_ ## thingy(struct file *fp, \
196 loff_t off, size_t count) 147 struct kobject *kobj, struct bin_attribute *attr, char *buf, \
197{ 148 loff_t off, size_t count) \
198 return koneplus_sysfs_write(fp, kobj, buf, off, count, 149{ \
199 sizeof(struct koneplus_info), KONEPLUS_COMMAND_INFO); 150 return koneplus_sysfs_read(fp, kobj, buf, off, count, \
151 KONEPLUS_SIZE_ ## THINGY, KONEPLUS_COMMAND_ ## THINGY); \
200} 152}
201 153
202static ssize_t koneplus_sysfs_write_talk(struct file *fp, 154#define KONEPLUS_SYSFS_RW(thingy, THINGY) \
203 struct kobject *kobj, struct bin_attribute *attr, char *buf, 155KONEPLUS_SYSFS_W(thingy, THINGY) \
204 loff_t off, size_t count) 156KONEPLUS_SYSFS_R(thingy, THINGY)
205{
206 return koneplus_sysfs_write(fp, kobj, buf, off, count,
207 sizeof(struct koneplus_talk), KONEPLUS_COMMAND_TALK);
208}
209 157
210static ssize_t koneplus_sysfs_write_macro(struct file *fp, 158#define KONEPLUS_BIN_ATTRIBUTE_RW(thingy, THINGY) \
211 struct kobject *kobj, struct bin_attribute *attr, char *buf, 159{ \
212 loff_t off, size_t count) 160 .attr = { .name = #thingy, .mode = 0660 }, \
213{ 161 .size = KONEPLUS_SIZE_ ## THINGY, \
214 return koneplus_sysfs_write(fp, kobj, buf, off, count, 162 .read = koneplus_sysfs_read_ ## thingy, \
215 sizeof(struct koneplus_macro), KONEPLUS_COMMAND_MACRO); 163 .write = koneplus_sysfs_write_ ## thingy \
216} 164}
217 165
218static ssize_t koneplus_sysfs_read_sensor(struct file *fp, 166#define KONEPLUS_BIN_ATTRIBUTE_R(thingy, THINGY) \
219 struct kobject *kobj, struct bin_attribute *attr, char *buf, 167{ \
220 loff_t off, size_t count) 168 .attr = { .name = #thingy, .mode = 0440 }, \
221{ 169 .size = KONEPLUS_SIZE_ ## THINGY, \
222 return koneplus_sysfs_read(fp, kobj, buf, off, count, 170 .read = koneplus_sysfs_read_ ## thingy, \
223 sizeof(struct koneplus_sensor), KONEPLUS_COMMAND_SENSOR);
224} 171}
225 172
226static ssize_t koneplus_sysfs_write_sensor(struct file *fp, 173#define KONEPLUS_BIN_ATTRIBUTE_W(thingy, THINGY) \
227 struct kobject *kobj, struct bin_attribute *attr, char *buf, 174{ \
228 loff_t off, size_t count) 175 .attr = { .name = #thingy, .mode = 0220 }, \
229{ 176 .size = KONEPLUS_SIZE_ ## THINGY, \
230 return koneplus_sysfs_write(fp, kobj, buf, off, count, 177 .write = koneplus_sysfs_write_ ## thingy \
231 sizeof(struct koneplus_sensor), KONEPLUS_COMMAND_SENSOR);
232} 178}
233 179
234static ssize_t koneplus_sysfs_write_tcu(struct file *fp, 180KONEPLUS_SYSFS_RW(info, INFO)
235 struct kobject *kobj, struct bin_attribute *attr, char *buf, 181KONEPLUS_SYSFS_W(talk, TALK)
236 loff_t off, size_t count) 182KONEPLUS_SYSFS_W(macro, MACRO)
237{ 183KONEPLUS_SYSFS_RW(sensor, SENSOR)
238 return koneplus_sysfs_write(fp, kobj, buf, off, count, 184KONEPLUS_SYSFS_RW(tcu, TCU)
239 sizeof(struct koneplus_tcu), KONEPLUS_COMMAND_TCU); 185KONEPLUS_SYSFS_R(tcu_image, TCU_IMAGE)
240} 186KONEPLUS_SYSFS_W(profile_settings, PROFILE_SETTINGS)
241 187KONEPLUS_SYSFS_W(profile_buttons, PROFILE_BUTTONS)
242static ssize_t koneplus_sysfs_read_tcu(struct file *fp,
243 struct kobject *kobj, struct bin_attribute *attr, char *buf,
244 loff_t off, size_t count)
245{
246 return koneplus_sysfs_read(fp, kobj, buf, off, count,
247 sizeof(struct koneplus_tcu), KONEPLUS_COMMAND_TCU);
248}
249
250static ssize_t koneplus_sysfs_read_tcu_image(struct file *fp,
251 struct kobject *kobj, struct bin_attribute *attr, char *buf,
252 loff_t off, size_t count)
253{
254 return koneplus_sysfs_read(fp, kobj, buf, off, count,
255 sizeof(struct koneplus_tcu_image), KONEPLUS_COMMAND_TCU);
256}
257 188
258static ssize_t koneplus_sysfs_read_profilex_settings(struct file *fp, 189static ssize_t koneplus_sysfs_read_profilex_settings(struct file *fp,
259 struct kobject *kobj, struct bin_attribute *attr, char *buf, 190 struct kobject *kobj, struct bin_attribute *attr, char *buf,
@@ -261,57 +192,17 @@ static ssize_t koneplus_sysfs_read_profilex_settings(struct file *fp,
261{ 192{
262 struct device *dev = 193 struct device *dev =
263 container_of(kobj, struct device, kobj)->parent->parent; 194 container_of(kobj, struct device, kobj)->parent->parent;
264 struct koneplus_device *koneplus = hid_get_drvdata(dev_get_drvdata(dev));
265
266 if (off >= sizeof(struct koneplus_profile_settings))
267 return 0;
268
269 if (off + count > sizeof(struct koneplus_profile_settings))
270 count = sizeof(struct koneplus_profile_settings) - off;
271
272 mutex_lock(&koneplus->koneplus_lock);
273 memcpy(buf, ((char const *)&koneplus->profile_settings[*(uint *)(attr->private)]) + off,
274 count);
275 mutex_unlock(&koneplus->koneplus_lock);
276
277 return count;
278}
279
280static ssize_t koneplus_sysfs_write_profile_settings(struct file *fp,
281 struct kobject *kobj, struct bin_attribute *attr, char *buf,
282 loff_t off, size_t count)
283{
284 struct device *dev =
285 container_of(kobj, struct device, kobj)->parent->parent;
286 struct koneplus_device *koneplus = hid_get_drvdata(dev_get_drvdata(dev));
287 struct usb_device *usb_dev = interface_to_usbdev(to_usb_interface(dev)); 195 struct usb_device *usb_dev = interface_to_usbdev(to_usb_interface(dev));
288 int retval = 0; 196 ssize_t retval;
289 int difference;
290 int profile_number;
291 struct koneplus_profile_settings *profile_settings;
292
293 if (off != 0 || count != sizeof(struct koneplus_profile_settings))
294 return -EINVAL;
295
296 profile_number = ((struct koneplus_profile_settings const *)buf)->number;
297 profile_settings = &koneplus->profile_settings[profile_number];
298
299 mutex_lock(&koneplus->koneplus_lock);
300 difference = memcmp(buf, profile_settings,
301 sizeof(struct koneplus_profile_settings));
302 if (difference) {
303 retval = koneplus_set_profile_settings(usb_dev,
304 (struct koneplus_profile_settings const *)buf);
305 if (!retval)
306 memcpy(profile_settings, buf,
307 sizeof(struct koneplus_profile_settings));
308 }
309 mutex_unlock(&koneplus->koneplus_lock);
310 197
198 retval = koneplus_send_control(usb_dev, *(uint *)(attr->private),
199 KONEPLUS_CONTROL_REQUEST_PROFILE_SETTINGS);
311 if (retval) 200 if (retval)
312 return retval; 201 return retval;
313 202
314 return sizeof(struct koneplus_profile_settings); 203 return koneplus_sysfs_read(fp, kobj, buf, off, count,
204 KONEPLUS_SIZE_PROFILE_SETTINGS,
205 KONEPLUS_COMMAND_PROFILE_SETTINGS);
315} 206}
316 207
317static ssize_t koneplus_sysfs_read_profilex_buttons(struct file *fp, 208static ssize_t koneplus_sysfs_read_profilex_buttons(struct file *fp,
@@ -320,57 +211,17 @@ static ssize_t koneplus_sysfs_read_profilex_buttons(struct file *fp,
320{ 211{
321 struct device *dev = 212 struct device *dev =
322 container_of(kobj, struct device, kobj)->parent->parent; 213 container_of(kobj, struct device, kobj)->parent->parent;
323 struct koneplus_device *koneplus = hid_get_drvdata(dev_get_drvdata(dev));
324
325 if (off >= sizeof(struct koneplus_profile_buttons))
326 return 0;
327
328 if (off + count > sizeof(struct koneplus_profile_buttons))
329 count = sizeof(struct koneplus_profile_buttons) - off;
330
331 mutex_lock(&koneplus->koneplus_lock);
332 memcpy(buf, ((char const *)&koneplus->profile_buttons[*(uint *)(attr->private)]) + off,
333 count);
334 mutex_unlock(&koneplus->koneplus_lock);
335
336 return count;
337}
338
339static ssize_t koneplus_sysfs_write_profile_buttons(struct file *fp,
340 struct kobject *kobj, struct bin_attribute *attr, char *buf,
341 loff_t off, size_t count)
342{
343 struct device *dev =
344 container_of(kobj, struct device, kobj)->parent->parent;
345 struct koneplus_device *koneplus = hid_get_drvdata(dev_get_drvdata(dev));
346 struct usb_device *usb_dev = interface_to_usbdev(to_usb_interface(dev)); 214 struct usb_device *usb_dev = interface_to_usbdev(to_usb_interface(dev));
347 int retval = 0; 215 ssize_t retval;
348 int difference;
349 uint profile_number;
350 struct koneplus_profile_buttons *profile_buttons;
351
352 if (off != 0 || count != sizeof(struct koneplus_profile_buttons))
353 return -EINVAL;
354
355 profile_number = ((struct koneplus_profile_buttons const *)buf)->number;
356 profile_buttons = &koneplus->profile_buttons[profile_number];
357
358 mutex_lock(&koneplus->koneplus_lock);
359 difference = memcmp(buf, profile_buttons,
360 sizeof(struct koneplus_profile_buttons));
361 if (difference) {
362 retval = koneplus_set_profile_buttons(usb_dev,
363 (struct koneplus_profile_buttons const *)buf);
364 if (!retval)
365 memcpy(profile_buttons, buf,
366 sizeof(struct koneplus_profile_buttons));
367 }
368 mutex_unlock(&koneplus->koneplus_lock);
369 216
217 retval = koneplus_send_control(usb_dev, *(uint *)(attr->private),
218 KONEPLUS_CONTROL_REQUEST_PROFILE_BUTTONS);
370 if (retval) 219 if (retval)
371 return retval; 220 return retval;
372 221
373 return sizeof(struct koneplus_profile_buttons); 222 return koneplus_sysfs_read(fp, kobj, buf, off, count,
223 KONEPLUS_SIZE_PROFILE_BUTTONS,
224 KONEPLUS_COMMAND_PROFILE_BUTTONS);
374} 225}
375 226
376static ssize_t koneplus_sysfs_show_actual_profile(struct device *dev, 227static ssize_t koneplus_sysfs_show_actual_profile(struct device *dev,
@@ -426,9 +277,20 @@ static ssize_t koneplus_sysfs_set_actual_profile(struct device *dev,
426static ssize_t koneplus_sysfs_show_firmware_version(struct device *dev, 277static ssize_t koneplus_sysfs_show_firmware_version(struct device *dev,
427 struct device_attribute *attr, char *buf) 278 struct device_attribute *attr, char *buf)
428{ 279{
429 struct koneplus_device *koneplus = 280 struct koneplus_device *koneplus;
430 hid_get_drvdata(dev_get_drvdata(dev->parent->parent)); 281 struct usb_device *usb_dev;
431 return snprintf(buf, PAGE_SIZE, "%d\n", koneplus->info.firmware_version); 282 struct koneplus_info info;
283
284 dev = dev->parent->parent;
285 koneplus = hid_get_drvdata(dev_get_drvdata(dev));
286 usb_dev = interface_to_usbdev(to_usb_interface(dev));
287
288 mutex_lock(&koneplus->koneplus_lock);
289 roccat_common2_receive(usb_dev, KONEPLUS_COMMAND_INFO,
290 &info, KONEPLUS_SIZE_INFO);
291 mutex_unlock(&koneplus->koneplus_lock);
292
293 return snprintf(buf, PAGE_SIZE, "%d\n", info.firmware_version);
432} 294}
433 295
434static struct device_attribute koneplus_attributes[] = { 296static struct device_attribute koneplus_attributes[] = {
@@ -444,139 +306,84 @@ static struct device_attribute koneplus_attributes[] = {
444}; 306};
445 307
446static struct bin_attribute koneplus_bin_attributes[] = { 308static struct bin_attribute koneplus_bin_attributes[] = {
447 { 309 KONEPLUS_BIN_ATTRIBUTE_RW(info, INFO),
448 .attr = { .name = "info", .mode = 0660 }, 310 KONEPLUS_BIN_ATTRIBUTE_W(talk, TALK),
449 .size = sizeof(struct koneplus_info), 311 KONEPLUS_BIN_ATTRIBUTE_W(macro, MACRO),
450 .read = koneplus_sysfs_read_info, 312 KONEPLUS_BIN_ATTRIBUTE_RW(sensor, SENSOR),
451 .write = koneplus_sysfs_write_info 313 KONEPLUS_BIN_ATTRIBUTE_RW(tcu, TCU),
452 }, 314 KONEPLUS_BIN_ATTRIBUTE_R(tcu_image, TCU_IMAGE),
453 { 315 KONEPLUS_BIN_ATTRIBUTE_W(profile_settings, PROFILE_SETTINGS),
454 .attr = { .name = "sensor", .mode = 0660 }, 316 KONEPLUS_BIN_ATTRIBUTE_W(profile_buttons, PROFILE_BUTTONS),
455 .size = sizeof(struct koneplus_sensor),
456 .read = koneplus_sysfs_read_sensor,
457 .write = koneplus_sysfs_write_sensor
458 },
459 {
460 .attr = { .name = "tcu", .mode = 0660 },
461 .size = sizeof(struct koneplus_tcu),
462 .read = koneplus_sysfs_read_tcu,
463 .write = koneplus_sysfs_write_tcu
464 },
465 {
466 .attr = { .name = "tcu_image", .mode = 0440 },
467 .size = sizeof(struct koneplus_tcu_image),
468 .read = koneplus_sysfs_read_tcu_image
469 },
470 {
471 .attr = { .name = "profile_settings", .mode = 0220 },
472 .size = sizeof(struct koneplus_profile_settings),
473 .write = koneplus_sysfs_write_profile_settings
474 },
475 { 317 {
476 .attr = { .name = "profile1_settings", .mode = 0440 }, 318 .attr = { .name = "profile1_settings", .mode = 0440 },
477 .size = sizeof(struct koneplus_profile_settings), 319 .size = KONEPLUS_SIZE_PROFILE_SETTINGS,
478 .read = koneplus_sysfs_read_profilex_settings, 320 .read = koneplus_sysfs_read_profilex_settings,
479 .private = &profile_numbers[0] 321 .private = &profile_numbers[0]
480 }, 322 },
481 { 323 {
482 .attr = { .name = "profile2_settings", .mode = 0440 }, 324 .attr = { .name = "profile2_settings", .mode = 0440 },
483 .size = sizeof(struct koneplus_profile_settings), 325 .size = KONEPLUS_SIZE_PROFILE_SETTINGS,
484 .read = koneplus_sysfs_read_profilex_settings, 326 .read = koneplus_sysfs_read_profilex_settings,
485 .private = &profile_numbers[1] 327 .private = &profile_numbers[1]
486 }, 328 },
487 { 329 {
488 .attr = { .name = "profile3_settings", .mode = 0440 }, 330 .attr = { .name = "profile3_settings", .mode = 0440 },
489 .size = sizeof(struct koneplus_profile_settings), 331 .size = KONEPLUS_SIZE_PROFILE_SETTINGS,
490 .read = koneplus_sysfs_read_profilex_settings, 332 .read = koneplus_sysfs_read_profilex_settings,
491 .private = &profile_numbers[2] 333 .private = &profile_numbers[2]
492 }, 334 },
493 { 335 {
494 .attr = { .name = "profile4_settings", .mode = 0440 }, 336 .attr = { .name = "profile4_settings", .mode = 0440 },
495 .size = sizeof(struct koneplus_profile_settings), 337 .size = KONEPLUS_SIZE_PROFILE_SETTINGS,
496 .read = koneplus_sysfs_read_profilex_settings, 338 .read = koneplus_sysfs_read_profilex_settings,
497 .private = &profile_numbers[3] 339 .private = &profile_numbers[3]
498 }, 340 },
499 { 341 {
500 .attr = { .name = "profile5_settings", .mode = 0440 }, 342 .attr = { .name = "profile5_settings", .mode = 0440 },
501 .size = sizeof(struct koneplus_profile_settings), 343 .size = KONEPLUS_SIZE_PROFILE_SETTINGS,
502 .read = koneplus_sysfs_read_profilex_settings, 344 .read = koneplus_sysfs_read_profilex_settings,
503 .private = &profile_numbers[4] 345 .private = &profile_numbers[4]
504 }, 346 },
505 { 347 {
506 .attr = { .name = "profile_buttons", .mode = 0220 },
507 .size = sizeof(struct koneplus_profile_buttons),
508 .write = koneplus_sysfs_write_profile_buttons
509 },
510 {
511 .attr = { .name = "profile1_buttons", .mode = 0440 }, 348 .attr = { .name = "profile1_buttons", .mode = 0440 },
512 .size = sizeof(struct koneplus_profile_buttons), 349 .size = KONEPLUS_SIZE_PROFILE_BUTTONS,
513 .read = koneplus_sysfs_read_profilex_buttons, 350 .read = koneplus_sysfs_read_profilex_buttons,
514 .private = &profile_numbers[0] 351 .private = &profile_numbers[0]
515 }, 352 },
516 { 353 {
517 .attr = { .name = "profile2_buttons", .mode = 0440 }, 354 .attr = { .name = "profile2_buttons", .mode = 0440 },
518 .size = sizeof(struct koneplus_profile_buttons), 355 .size = KONEPLUS_SIZE_PROFILE_BUTTONS,
519 .read = koneplus_sysfs_read_profilex_buttons, 356 .read = koneplus_sysfs_read_profilex_buttons,
520 .private = &profile_numbers[1] 357 .private = &profile_numbers[1]
521 }, 358 },
522 { 359 {
523 .attr = { .name = "profile3_buttons", .mode = 0440 }, 360 .attr = { .name = "profile3_buttons", .mode = 0440 },
524 .size = sizeof(struct koneplus_profile_buttons), 361 .size = KONEPLUS_SIZE_PROFILE_BUTTONS,
525 .read = koneplus_sysfs_read_profilex_buttons, 362 .read = koneplus_sysfs_read_profilex_buttons,
526 .private = &profile_numbers[2] 363 .private = &profile_numbers[2]
527 }, 364 },
528 { 365 {
529 .attr = { .name = "profile4_buttons", .mode = 0440 }, 366 .attr = { .name = "profile4_buttons", .mode = 0440 },
530 .size = sizeof(struct koneplus_profile_buttons), 367 .size = KONEPLUS_SIZE_PROFILE_BUTTONS,
531 .read = koneplus_sysfs_read_profilex_buttons, 368 .read = koneplus_sysfs_read_profilex_buttons,
532 .private = &profile_numbers[3] 369 .private = &profile_numbers[3]
533 }, 370 },
534 { 371 {
535 .attr = { .name = "profile5_buttons", .mode = 0440 }, 372 .attr = { .name = "profile5_buttons", .mode = 0440 },
536 .size = sizeof(struct koneplus_profile_buttons), 373 .size = KONEPLUS_SIZE_PROFILE_BUTTONS,
537 .read = koneplus_sysfs_read_profilex_buttons, 374 .read = koneplus_sysfs_read_profilex_buttons,
538 .private = &profile_numbers[4] 375 .private = &profile_numbers[4]
539 }, 376 },
540 {
541 .attr = { .name = "macro", .mode = 0220 },
542 .size = sizeof(struct koneplus_macro),
543 .write = koneplus_sysfs_write_macro
544 },
545 {
546 .attr = { .name = "talk", .mode = 0220 },
547 .size = sizeof(struct koneplus_talk),
548 .write = koneplus_sysfs_write_talk
549 },
550 __ATTR_NULL 377 __ATTR_NULL
551}; 378};
552 379
553static int koneplus_init_koneplus_device_struct(struct usb_device *usb_dev, 380static int koneplus_init_koneplus_device_struct(struct usb_device *usb_dev,
554 struct koneplus_device *koneplus) 381 struct koneplus_device *koneplus)
555{ 382{
556 int retval, i; 383 int retval;
557 static uint wait = 200;
558 384
559 mutex_init(&koneplus->koneplus_lock); 385 mutex_init(&koneplus->koneplus_lock);
560 386
561 retval = koneplus_get_info(usb_dev, &koneplus->info);
562 if (retval)
563 return retval;
564
565 for (i = 0; i < 5; ++i) {
566 msleep(wait);
567 retval = koneplus_get_profile_settings(usb_dev,
568 &koneplus->profile_settings[i], i);
569 if (retval)
570 return retval;
571
572 msleep(wait);
573 retval = koneplus_get_profile_buttons(usb_dev,
574 &koneplus->profile_buttons[i], i);
575 if (retval)
576 return retval;
577 }
578
579 msleep(wait);
580 retval = koneplus_get_actual_profile(usb_dev); 387 retval = koneplus_get_actual_profile(usb_dev);
581 if (retval < 0) 388 if (retval < 0)
582 return retval; 389 return retval;
diff --git a/drivers/hid/hid-roccat-koneplus.h b/drivers/hid/hid-roccat-koneplus.h
index 7074b2a4b94b..563b9d3fe5fb 100644
--- a/drivers/hid/hid-roccat-koneplus.h
+++ b/drivers/hid/hid-roccat-koneplus.h
@@ -14,11 +14,18 @@
14 14
15#include <linux/types.h> 15#include <linux/types.h>
16 16
17struct koneplus_talk { 17enum {
18 uint8_t command; /* KONEPLUS_COMMAND_TALK */ 18 KONEPLUS_SIZE_ACTUAL_PROFILE = 0x03,
19 uint8_t size; /* always 0x10 */ 19 KONEPLUS_SIZE_FIRMWARE_WRITE = 0x0402,
20 uint8_t data[14]; 20 KONEPLUS_SIZE_INFO = 0x06,
21} __packed; 21 KONEPLUS_SIZE_MACRO = 0x0822,
22 KONEPLUS_SIZE_PROFILE_SETTINGS = 0x2b,
23 KONEPLUS_SIZE_PROFILE_BUTTONS = 0x4d,
24 KONEPLUS_SIZE_SENSOR = 0x06,
25 KONEPLUS_SIZE_TALK = 0x10,
26 KONEPLUS_SIZE_TCU = 0x03,
27 KONEPLUS_SIZE_TCU_IMAGE = 0x0404,
28};
22 29
23enum koneplus_control_requests { 30enum koneplus_control_requests {
24 KONEPLUS_CONTROL_REQUEST_PROFILE_SETTINGS = 0x80, 31 KONEPLUS_CONTROL_REQUEST_PROFILE_SETTINGS = 0x80,
@@ -31,45 +38,6 @@ struct koneplus_actual_profile {
31 uint8_t actual_profile; /* Range 0-4! */ 38 uint8_t actual_profile; /* Range 0-4! */
32} __attribute__ ((__packed__)); 39} __attribute__ ((__packed__));
33 40
34struct koneplus_profile_settings {
35 uint8_t command; /* KONEPLUS_COMMAND_PROFILE_SETTINGS */
36 uint8_t size; /* always 43 */
37 uint8_t number; /* range 0-4 */
38 uint8_t advanced_sensitivity;
39 uint8_t sensitivity_x;
40 uint8_t sensitivity_y;
41 uint8_t cpi_levels_enabled;
42 uint8_t cpi_levels_x[5];
43 uint8_t cpi_startup_level; /* range 0-4 */
44 uint8_t cpi_levels_y[5]; /* range 1-60 means 100-6000 cpi */
45 uint8_t unknown1;
46 uint8_t polling_rate;
47 uint8_t lights_enabled;
48 uint8_t light_effect_mode;
49 uint8_t color_flow_effect;
50 uint8_t light_effect_type;
51 uint8_t light_effect_speed;
52 uint8_t lights[16];
53 uint16_t checksum;
54} __attribute__ ((__packed__));
55
56struct koneplus_profile_buttons {
57 uint8_t command; /* KONEPLUS_COMMAND_PROFILE_BUTTONS */
58 uint8_t size; /* always 77 */
59 uint8_t number; /* range 0-4 */
60 uint8_t data[72];
61 uint16_t checksum;
62} __attribute__ ((__packed__));
63
64struct koneplus_macro {
65 uint8_t command; /* KONEPLUS_COMMAND_MACRO */
66 uint16_t size; /* always 0x822 little endian */
67 uint8_t profile; /* range 0-4 */
68 uint8_t button; /* range 0-23 */
69 uint8_t data[2075];
70 uint16_t checksum;
71} __attribute__ ((__packed__));
72
73struct koneplus_info { 41struct koneplus_info {
74 uint8_t command; /* KONEPLUS_COMMAND_INFO */ 42 uint8_t command; /* KONEPLUS_COMMAND_INFO */
75 uint8_t size; /* always 6 */ 43 uint8_t size; /* always 6 */
@@ -77,44 +45,6 @@ struct koneplus_info {
77 uint8_t unknown[3]; 45 uint8_t unknown[3];
78} __attribute__ ((__packed__)); 46} __attribute__ ((__packed__));
79 47
80struct koneplus_e {
81 uint8_t command; /* KONEPLUS_COMMAND_E */
82 uint8_t size; /* always 3 */
83 uint8_t unknown; /* TODO 1; 0 before firmware update */
84} __attribute__ ((__packed__));
85
86struct koneplus_sensor {
87 uint8_t command; /* KONEPLUS_COMMAND_SENSOR */
88 uint8_t size; /* always 6 */
89 uint8_t data[4];
90} __attribute__ ((__packed__));
91
92struct koneplus_firmware_write {
93 uint8_t command; /* KONEPLUS_COMMAND_FIRMWARE_WRITE */
94 uint8_t unknown[1025];
95} __attribute__ ((__packed__));
96
97struct koneplus_firmware_write_control {
98 uint8_t command; /* KONEPLUS_COMMAND_FIRMWARE_WRITE_CONTROL */
99 /*
100 * value is 1 on success
101 * 3 means "not finished yet"
102 */
103 uint8_t value;
104 uint8_t unknown; /* always 0x75 */
105} __attribute__ ((__packed__));
106
107struct koneplus_tcu {
108 uint16_t usb_command; /* KONEPLUS_USB_COMMAND_TCU */
109 uint8_t data[2];
110} __attribute__ ((__packed__));
111
112struct koneplus_tcu_image {
113 uint16_t usb_command; /* KONEPLUS_USB_COMMAND_TCU */
114 uint8_t data[1024];
115 uint16_t checksum;
116} __attribute__ ((__packed__));
117
118enum koneplus_commands { 48enum koneplus_commands {
119 KONEPLUS_COMMAND_ACTUAL_PROFILE = 0x5, 49 KONEPLUS_COMMAND_ACTUAL_PROFILE = 0x5,
120 KONEPLUS_COMMAND_PROFILE_SETTINGS = 0x6, 50 KONEPLUS_COMMAND_PROFILE_SETTINGS = 0x6,
@@ -122,6 +52,7 @@ enum koneplus_commands {
122 KONEPLUS_COMMAND_MACRO = 0x8, 52 KONEPLUS_COMMAND_MACRO = 0x8,
123 KONEPLUS_COMMAND_INFO = 0x9, 53 KONEPLUS_COMMAND_INFO = 0x9,
124 KONEPLUS_COMMAND_TCU = 0xc, 54 KONEPLUS_COMMAND_TCU = 0xc,
55 KONEPLUS_COMMAND_TCU_IMAGE = 0xc,
125 KONEPLUS_COMMAND_E = 0xe, 56 KONEPLUS_COMMAND_E = 0xe,
126 KONEPLUS_COMMAND_SENSOR = 0xf, 57 KONEPLUS_COMMAND_SENSOR = 0xf,
127 KONEPLUS_COMMAND_TALK = 0x10, 58 KONEPLUS_COMMAND_TALK = 0x10,
@@ -187,10 +118,6 @@ struct koneplus_device {
187 int chrdev_minor; 118 int chrdev_minor;
188 119
189 struct mutex koneplus_lock; 120 struct mutex koneplus_lock;
190
191 struct koneplus_info info;
192 struct koneplus_profile_settings profile_settings[5];
193 struct koneplus_profile_buttons profile_buttons[5];
194}; 121};
195 122
196#endif 123#endif