xref: /openbmc/linux/sound/usb/line6/pod.c (revision 516d3d1b)
1 /*
2  * Line 6 Linux USB driver
3  *
4  * Copyright (C) 2004-2010 Markus Grabner (grabner@icg.tugraz.at)
5  *
6  *	This program is free software; you can redistribute it and/or
7  *	modify it under the terms of the GNU General Public License as
8  *	published by the Free Software Foundation, version 2.
9  *
10  */
11 
12 #include <linux/slab.h>
13 #include <linux/wait.h>
14 #include <linux/interrupt.h>
15 #include <linux/module.h>
16 #include <linux/usb.h>
17 
18 #include <sound/core.h>
19 #include <sound/control.h>
20 
21 #include "capture.h"
22 #include "driver.h"
23 #include "playback.h"
24 
25 /*
26 	Locate name in binary program dump
27 */
28 #define	POD_NAME_OFFSET 0
29 #define	POD_NAME_LENGTH 16
30 
31 /*
32 	Other constants
33 */
34 #define POD_CONTROL_SIZE 0x80
35 #define POD_BUFSIZE_DUMPREQ 7
36 #define POD_STARTUP_DELAY 1000
37 
38 /*
39 	Stages of POD startup procedure
40 */
41 enum {
42 	POD_STARTUP_VERSIONREQ,
43 	POD_STARTUP_SETUP,
44 	POD_STARTUP_DONE,
45 };
46 
47 enum {
48 	LINE6_BASSPODXT,
49 	LINE6_BASSPODXTLIVE,
50 	LINE6_BASSPODXTPRO,
51 	LINE6_POCKETPOD,
52 	LINE6_PODXT,
53 	LINE6_PODXTLIVE_POD,
54 	LINE6_PODXTPRO,
55 };
56 
57 struct usb_line6_pod {
58 	/* Generic Line 6 USB data */
59 	struct usb_line6 line6;
60 
61 	/* Instrument monitor level */
62 	int monitor_level;
63 
64 	/* Current progress in startup procedure */
65 	int startup_progress;
66 
67 	/* Serial number of device */
68 	u32 serial_number;
69 
70 	/* Firmware version (x 100) */
71 	int firmware_version;
72 
73 	/* Device ID */
74 	int device_id;
75 };
76 
77 #define POD_SYSEX_CODE 3
78 
79 /* *INDENT-OFF* */
80 
81 enum {
82 	POD_SYSEX_SAVE      = 0x24,
83 	POD_SYSEX_SYSTEM    = 0x56,
84 	POD_SYSEX_SYSTEMREQ = 0x57,
85 	/* POD_SYSEX_UPDATE    = 0x6c, */  /* software update! */
86 	POD_SYSEX_STORE     = 0x71,
87 	POD_SYSEX_FINISH    = 0x72,
88 	POD_SYSEX_DUMPMEM   = 0x73,
89 	POD_SYSEX_DUMP      = 0x74,
90 	POD_SYSEX_DUMPREQ   = 0x75
91 
92 	/* dumps entire internal memory of PODxt Pro */
93 	/* POD_SYSEX_DUMPMEM2  = 0x76 */
94 };
95 
96 enum {
97 	POD_MONITOR_LEVEL  = 0x04,
98 	POD_SYSTEM_INVALID = 0x10000
99 };
100 
101 /* *INDENT-ON* */
102 
103 enum {
104 	POD_DUMP_MEMORY = 2
105 };
106 
107 enum {
108 	POD_BUSY_READ,
109 	POD_BUSY_WRITE,
110 	POD_CHANNEL_DIRTY,
111 	POD_SAVE_PRESSED,
112 	POD_BUSY_MIDISEND
113 };
114 
115 static struct snd_ratden pod_ratden = {
116 	.num_min = 78125,
117 	.num_max = 78125,
118 	.num_step = 1,
119 	.den = 2
120 };
121 
122 static struct line6_pcm_properties pod_pcm_properties = {
123 	.playback_hw = {
124 				  .info = (SNDRV_PCM_INFO_MMAP |
125 					   SNDRV_PCM_INFO_INTERLEAVED |
126 					   SNDRV_PCM_INFO_BLOCK_TRANSFER |
127 					   SNDRV_PCM_INFO_MMAP_VALID |
128 					   SNDRV_PCM_INFO_PAUSE |
129 					   SNDRV_PCM_INFO_SYNC_START),
130 				  .formats = SNDRV_PCM_FMTBIT_S24_3LE,
131 				  .rates = SNDRV_PCM_RATE_KNOT,
132 				  .rate_min = 39062,
133 				  .rate_max = 39063,
134 				  .channels_min = 2,
135 				  .channels_max = 2,
136 				  .buffer_bytes_max = 60000,
137 				  .period_bytes_min = 64,
138 				  .period_bytes_max = 8192,
139 				  .periods_min = 1,
140 				  .periods_max = 1024},
141 	.capture_hw = {
142 				 .info = (SNDRV_PCM_INFO_MMAP |
143 					  SNDRV_PCM_INFO_INTERLEAVED |
144 					  SNDRV_PCM_INFO_BLOCK_TRANSFER |
145 					  SNDRV_PCM_INFO_MMAP_VALID |
146 					  SNDRV_PCM_INFO_SYNC_START),
147 				 .formats = SNDRV_PCM_FMTBIT_S24_3LE,
148 				 .rates = SNDRV_PCM_RATE_KNOT,
149 				 .rate_min = 39062,
150 				 .rate_max = 39063,
151 				 .channels_min = 2,
152 				 .channels_max = 2,
153 				 .buffer_bytes_max = 60000,
154 				 .period_bytes_min = 64,
155 				 .period_bytes_max = 8192,
156 				 .periods_min = 1,
157 				 .periods_max = 1024},
158 	.rates = {
159 			    .nrats = 1,
160 			    .rats = &pod_ratden},
161 	.bytes_per_channel = 3 /* SNDRV_PCM_FMTBIT_S24_3LE */
162 };
163 
164 static const char pod_version_header[] = {
165 	0xf2, 0x7e, 0x7f, 0x06, 0x02
166 };
167 
168 static char *pod_alloc_sysex_buffer(struct usb_line6_pod *pod, int code,
169 				    int size)
170 {
171 	return line6_alloc_sysex_buffer(&pod->line6, POD_SYSEX_CODE, code,
172 					size);
173 }
174 
175 /*
176 	Process a completely received message.
177 */
178 static void line6_pod_process_message(struct usb_line6 *line6)
179 {
180 	struct usb_line6_pod *pod = (struct usb_line6_pod *) line6;
181 	const unsigned char *buf = pod->line6.buffer_message;
182 
183 	if (memcmp(buf, pod_version_header, sizeof(pod_version_header)) == 0) {
184 		pod->firmware_version = buf[13] * 100 + buf[14] * 10 + buf[15];
185 		pod->device_id = ((int)buf[8] << 16) | ((int)buf[9] << 8) |
186 				 (int) buf[10];
187 		if (pod->startup_progress == POD_STARTUP_VERSIONREQ) {
188 			pod->startup_progress = POD_STARTUP_SETUP;
189 			schedule_delayed_work(&line6->startup_work, 0);
190 		}
191 		return;
192 	}
193 
194 	/* Only look for sysex messages from this device */
195 	if (buf[0] != (LINE6_SYSEX_BEGIN | LINE6_CHANNEL_DEVICE) &&
196 	    buf[0] != (LINE6_SYSEX_BEGIN | LINE6_CHANNEL_UNKNOWN)) {
197 		return;
198 	}
199 	if (memcmp(buf + 1, line6_midi_id, sizeof(line6_midi_id)) != 0)
200 		return;
201 
202 	if (buf[5] == POD_SYSEX_SYSTEM && buf[6] == POD_MONITOR_LEVEL) {
203 		short value = ((int)buf[7] << 12) | ((int)buf[8] << 8) |
204 			      ((int)buf[9] << 4) | (int)buf[10];
205 		pod->monitor_level = value;
206 	}
207 }
208 
209 /*
210 	Send system parameter (from integer).
211 */
212 static int pod_set_system_param_int(struct usb_line6_pod *pod, int value,
213 				    int code)
214 {
215 	char *sysex;
216 	static const int size = 5;
217 
218 	sysex = pod_alloc_sysex_buffer(pod, POD_SYSEX_SYSTEM, size);
219 	if (!sysex)
220 		return -ENOMEM;
221 	sysex[SYSEX_DATA_OFS] = code;
222 	sysex[SYSEX_DATA_OFS + 1] = (value >> 12) & 0x0f;
223 	sysex[SYSEX_DATA_OFS + 2] = (value >> 8) & 0x0f;
224 	sysex[SYSEX_DATA_OFS + 3] = (value >> 4) & 0x0f;
225 	sysex[SYSEX_DATA_OFS + 4] = (value) & 0x0f;
226 	line6_send_sysex_message(&pod->line6, sysex, size);
227 	kfree(sysex);
228 	return 0;
229 }
230 
231 /*
232 	"read" request on "serial_number" special file.
233 */
234 static ssize_t serial_number_show(struct device *dev,
235 				  struct device_attribute *attr, char *buf)
236 {
237 	struct snd_card *card = dev_to_snd_card(dev);
238 	struct usb_line6_pod *pod = card->private_data;
239 
240 	return sprintf(buf, "%u\n", pod->serial_number);
241 }
242 
243 /*
244 	"read" request on "firmware_version" special file.
245 */
246 static ssize_t firmware_version_show(struct device *dev,
247 				     struct device_attribute *attr, char *buf)
248 {
249 	struct snd_card *card = dev_to_snd_card(dev);
250 	struct usb_line6_pod *pod = card->private_data;
251 
252 	return sprintf(buf, "%d.%02d\n", pod->firmware_version / 100,
253 		       pod->firmware_version % 100);
254 }
255 
256 /*
257 	"read" request on "device_id" special file.
258 */
259 static ssize_t device_id_show(struct device *dev,
260 			      struct device_attribute *attr, char *buf)
261 {
262 	struct snd_card *card = dev_to_snd_card(dev);
263 	struct usb_line6_pod *pod = card->private_data;
264 
265 	return sprintf(buf, "%d\n", pod->device_id);
266 }
267 
268 /*
269 	POD startup procedure.
270 	This is a sequence of functions with special requirements (e.g., must
271 	not run immediately after initialization, must not run in interrupt
272 	context). After the last one has finished, the device is ready to use.
273 */
274 
275 static void pod_startup(struct usb_line6 *line6)
276 {
277 	struct usb_line6_pod *pod = (struct usb_line6_pod *) line6;
278 
279 	switch (pod->startup_progress) {
280 	case POD_STARTUP_VERSIONREQ:
281 		/* request firmware version: */
282 		line6_version_request_async(line6);
283 		break;
284 	case POD_STARTUP_SETUP:
285 		/* serial number: */
286 		line6_read_serial_number(&pod->line6, &pod->serial_number);
287 
288 		/* ALSA audio interface: */
289 		if (snd_card_register(line6->card))
290 			dev_err(line6->ifcdev, "Failed to register POD card.\n");
291 		pod->startup_progress = POD_STARTUP_DONE;
292 		break;
293 	default:
294 		break;
295 	}
296 }
297 
298 /* POD special files: */
299 static DEVICE_ATTR_RO(device_id);
300 static DEVICE_ATTR_RO(firmware_version);
301 static DEVICE_ATTR_RO(serial_number);
302 
303 static struct attribute *pod_dev_attrs[] = {
304 	&dev_attr_device_id.attr,
305 	&dev_attr_firmware_version.attr,
306 	&dev_attr_serial_number.attr,
307 	NULL
308 };
309 
310 static const struct attribute_group pod_dev_attr_group = {
311 	.name = "pod",
312 	.attrs = pod_dev_attrs,
313 };
314 
315 /* control info callback */
316 static int snd_pod_control_monitor_info(struct snd_kcontrol *kcontrol,
317 					struct snd_ctl_elem_info *uinfo)
318 {
319 	uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
320 	uinfo->count = 1;
321 	uinfo->value.integer.min = 0;
322 	uinfo->value.integer.max = 65535;
323 	return 0;
324 }
325 
326 /* control get callback */
327 static int snd_pod_control_monitor_get(struct snd_kcontrol *kcontrol,
328 				       struct snd_ctl_elem_value *ucontrol)
329 {
330 	struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
331 	struct usb_line6_pod *pod = (struct usb_line6_pod *)line6pcm->line6;
332 
333 	ucontrol->value.integer.value[0] = pod->monitor_level;
334 	return 0;
335 }
336 
337 /* control put callback */
338 static int snd_pod_control_monitor_put(struct snd_kcontrol *kcontrol,
339 				       struct snd_ctl_elem_value *ucontrol)
340 {
341 	struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
342 	struct usb_line6_pod *pod = (struct usb_line6_pod *)line6pcm->line6;
343 
344 	if (ucontrol->value.integer.value[0] == pod->monitor_level)
345 		return 0;
346 
347 	pod->monitor_level = ucontrol->value.integer.value[0];
348 	pod_set_system_param_int(pod, ucontrol->value.integer.value[0],
349 				 POD_MONITOR_LEVEL);
350 	return 1;
351 }
352 
353 /* control definition */
354 static const struct snd_kcontrol_new pod_control_monitor = {
355 	.iface = SNDRV_CTL_ELEM_IFACE_MIXER,
356 	.name = "Monitor Playback Volume",
357 	.index = 0,
358 	.access = SNDRV_CTL_ELEM_ACCESS_READWRITE,
359 	.info = snd_pod_control_monitor_info,
360 	.get = snd_pod_control_monitor_get,
361 	.put = snd_pod_control_monitor_put
362 };
363 
364 /*
365 	 Try to init POD device.
366 */
367 static int pod_init(struct usb_line6 *line6,
368 		    const struct usb_device_id *id)
369 {
370 	int err;
371 	struct usb_line6_pod *pod = (struct usb_line6_pod *) line6;
372 
373 	line6->process_message = line6_pod_process_message;
374 	line6->startup = pod_startup;
375 
376 	/* create sysfs entries: */
377 	err = snd_card_add_dev_attr(line6->card, &pod_dev_attr_group);
378 	if (err < 0)
379 		return err;
380 
381 	/* initialize MIDI subsystem: */
382 	err = line6_init_midi(line6);
383 	if (err < 0)
384 		return err;
385 
386 	/* initialize PCM subsystem: */
387 	err = line6_init_pcm(line6, &pod_pcm_properties);
388 	if (err < 0)
389 		return err;
390 
391 	/* register monitor control: */
392 	err = snd_ctl_add(line6->card,
393 			  snd_ctl_new1(&pod_control_monitor, line6->line6pcm));
394 	if (err < 0)
395 		return err;
396 
397 	/*
398 	   When the sound card is registered at this point, the PODxt Live
399 	   displays "Invalid Code Error 07", so we do it later in the event
400 	   handler.
401 	 */
402 
403 	if (pod->line6.properties->capabilities & LINE6_CAP_CONTROL) {
404 		pod->monitor_level = POD_SYSTEM_INVALID;
405 
406 		/* initiate startup procedure: */
407 		schedule_delayed_work(&line6->startup_work,
408 				      msecs_to_jiffies(POD_STARTUP_DELAY));
409 	}
410 
411 	return 0;
412 }
413 
414 #define LINE6_DEVICE(prod) USB_DEVICE(0x0e41, prod)
415 #define LINE6_IF_NUM(prod, n) USB_DEVICE_INTERFACE_NUMBER(0x0e41, prod, n)
416 
417 /* table of devices that work with this driver */
418 static const struct usb_device_id pod_id_table[] = {
419 	{ LINE6_DEVICE(0x4250),    .driver_info = LINE6_BASSPODXT },
420 	{ LINE6_DEVICE(0x4642),    .driver_info = LINE6_BASSPODXTLIVE },
421 	{ LINE6_DEVICE(0x4252),    .driver_info = LINE6_BASSPODXTPRO },
422 	{ LINE6_IF_NUM(0x5051, 1), .driver_info = LINE6_POCKETPOD },
423 	{ LINE6_DEVICE(0x5044),    .driver_info = LINE6_PODXT },
424 	{ LINE6_IF_NUM(0x4650, 0), .driver_info = LINE6_PODXTLIVE_POD },
425 	{ LINE6_DEVICE(0x5050),    .driver_info = LINE6_PODXTPRO },
426 	{}
427 };
428 
429 MODULE_DEVICE_TABLE(usb, pod_id_table);
430 
431 static const struct line6_properties pod_properties_table[] = {
432 	[LINE6_BASSPODXT] = {
433 		.id = "BassPODxt",
434 		.name = "BassPODxt",
435 		.capabilities	= LINE6_CAP_CONTROL
436 				| LINE6_CAP_CONTROL_MIDI
437 				| LINE6_CAP_PCM
438 				| LINE6_CAP_HWMON,
439 		.altsetting = 5,
440 		.ep_ctrl_r = 0x84,
441 		.ep_ctrl_w = 0x03,
442 		.ep_audio_r = 0x82,
443 		.ep_audio_w = 0x01,
444 	},
445 	[LINE6_BASSPODXTLIVE] = {
446 		.id = "BassPODxtLive",
447 		.name = "BassPODxt Live",
448 		.capabilities	= LINE6_CAP_CONTROL
449 				| LINE6_CAP_CONTROL_MIDI
450 				| LINE6_CAP_PCM
451 				| LINE6_CAP_HWMON,
452 		.altsetting = 1,
453 		.ep_ctrl_r = 0x84,
454 		.ep_ctrl_w = 0x03,
455 		.ep_audio_r = 0x82,
456 		.ep_audio_w = 0x01,
457 	},
458 	[LINE6_BASSPODXTPRO] = {
459 		.id = "BassPODxtPro",
460 		.name = "BassPODxt Pro",
461 		.capabilities	= LINE6_CAP_CONTROL
462 				| LINE6_CAP_CONTROL_MIDI
463 				| LINE6_CAP_PCM
464 				| LINE6_CAP_HWMON,
465 		.altsetting = 5,
466 		.ep_ctrl_r = 0x84,
467 		.ep_ctrl_w = 0x03,
468 		.ep_audio_r = 0x82,
469 		.ep_audio_w = 0x01,
470 	},
471 	[LINE6_POCKETPOD] = {
472 		.id = "PocketPOD",
473 		.name = "Pocket POD",
474 		.capabilities	= LINE6_CAP_CONTROL
475 				| LINE6_CAP_CONTROL_MIDI,
476 		.altsetting = 0,
477 		.ep_ctrl_r = 0x82,
478 		.ep_ctrl_w = 0x02,
479 		/* no audio channel */
480 	},
481 	[LINE6_PODXT] = {
482 		.id = "PODxt",
483 		.name = "PODxt",
484 		.capabilities	= LINE6_CAP_CONTROL
485 				| LINE6_CAP_CONTROL_MIDI
486 				| LINE6_CAP_PCM
487 				| LINE6_CAP_HWMON,
488 		.altsetting = 5,
489 		.ep_ctrl_r = 0x84,
490 		.ep_ctrl_w = 0x03,
491 		.ep_audio_r = 0x82,
492 		.ep_audio_w = 0x01,
493 	},
494 	[LINE6_PODXTLIVE_POD] = {
495 		.id = "PODxtLive",
496 		.name = "PODxt Live",
497 		.capabilities	= LINE6_CAP_CONTROL
498 				| LINE6_CAP_CONTROL_MIDI
499 				| LINE6_CAP_PCM
500 				| LINE6_CAP_HWMON,
501 		.altsetting = 1,
502 		.ep_ctrl_r = 0x84,
503 		.ep_ctrl_w = 0x03,
504 		.ep_audio_r = 0x82,
505 		.ep_audio_w = 0x01,
506 	},
507 	[LINE6_PODXTPRO] = {
508 		.id = "PODxtPro",
509 		.name = "PODxt Pro",
510 		.capabilities	= LINE6_CAP_CONTROL
511 				| LINE6_CAP_CONTROL_MIDI
512 				| LINE6_CAP_PCM
513 				| LINE6_CAP_HWMON,
514 		.altsetting = 5,
515 		.ep_ctrl_r = 0x84,
516 		.ep_ctrl_w = 0x03,
517 		.ep_audio_r = 0x82,
518 		.ep_audio_w = 0x01,
519 	},
520 };
521 
522 /*
523 	Probe USB device.
524 */
525 static int pod_probe(struct usb_interface *interface,
526 		     const struct usb_device_id *id)
527 {
528 	return line6_probe(interface, id, "Line6-POD",
529 			   &pod_properties_table[id->driver_info],
530 			   pod_init, sizeof(struct usb_line6_pod));
531 }
532 
533 static struct usb_driver pod_driver = {
534 	.name = KBUILD_MODNAME,
535 	.probe = pod_probe,
536 	.disconnect = line6_disconnect,
537 #ifdef CONFIG_PM
538 	.suspend = line6_suspend,
539 	.resume = line6_resume,
540 	.reset_resume = line6_resume,
541 #endif
542 	.id_table = pod_id_table,
543 };
544 
545 module_usb_driver(pod_driver);
546 
547 MODULE_DESCRIPTION("Line 6 POD USB driver");
548 MODULE_LICENSE("GPL");
549