1 /*
2 * Line6 Linux USB driver - 0.9.1beta
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 <sound/control.h>
15
16 #include "audio.h"
17 #include "capture.h"
18 #include "driver.h"
19 #include "playback.h"
20 #include "pod.h"
21
22 #define POD_SYSEX_CODE 3
23 #define POD_BYTES_PER_FRAME 6 /* 24bit audio (stereo) */
24
25 /* *INDENT-OFF* */
26
27 enum {
28 POD_SYSEX_SAVE = 0x24,
29 POD_SYSEX_SYSTEM = 0x56,
30 POD_SYSEX_SYSTEMREQ = 0x57,
31 /* POD_SYSEX_UPDATE = 0x6c, */ /* software update! */
32 POD_SYSEX_STORE = 0x71,
33 POD_SYSEX_FINISH = 0x72,
34 POD_SYSEX_DUMPMEM = 0x73,
35 POD_SYSEX_DUMP = 0x74,
36 POD_SYSEX_DUMPREQ = 0x75
37
38 /* dumps entire internal memory of PODxt Pro */
39 /* POD_SYSEX_DUMPMEM2 = 0x76 */
40 };
41
42 enum {
43 POD_MONITOR_LEVEL = 0x04,
44 POD_SYSTEM_INVALID = 0x10000
45 };
46
47 /* *INDENT-ON* */
48
49 enum {
50 POD_DUMP_MEMORY = 2
51 };
52
53 enum {
54 POD_BUSY_READ,
55 POD_BUSY_WRITE,
56 POD_CHANNEL_DIRTY,
57 POD_SAVE_PRESSED,
58 POD_BUSY_MIDISEND
59 };
60
61 static struct snd_ratden pod_ratden = {
62 .num_min = 78125,
63 .num_max = 78125,
64 .num_step = 1,
65 .den = 2
66 };
67
68 static struct line6_pcm_properties pod_pcm_properties = {
69 .snd_line6_playback_hw = {
70 .info = (SNDRV_PCM_INFO_MMAP |
71 SNDRV_PCM_INFO_INTERLEAVED |
72 SNDRV_PCM_INFO_BLOCK_TRANSFER |
73 SNDRV_PCM_INFO_MMAP_VALID |
74 SNDRV_PCM_INFO_PAUSE |
75 #ifdef CONFIG_PM
76 SNDRV_PCM_INFO_RESUME |
77 #endif
78 SNDRV_PCM_INFO_SYNC_START),
79 .formats = SNDRV_PCM_FMTBIT_S24_3LE,
80 .rates = SNDRV_PCM_RATE_KNOT,
81 .rate_min = 39062,
82 .rate_max = 39063,
83 .channels_min = 2,
84 .channels_max = 2,
85 .buffer_bytes_max = 60000,
86 .period_bytes_min = 64,
87 .period_bytes_max = 8192,
88 .periods_min = 1,
89 .periods_max = 1024},
90 .snd_line6_capture_hw = {
91 .info = (SNDRV_PCM_INFO_MMAP |
92 SNDRV_PCM_INFO_INTERLEAVED |
93 SNDRV_PCM_INFO_BLOCK_TRANSFER |
94 SNDRV_PCM_INFO_MMAP_VALID |
95 #ifdef CONFIG_PM
96 SNDRV_PCM_INFO_RESUME |
97 #endif
98 SNDRV_PCM_INFO_SYNC_START),
99 .formats = SNDRV_PCM_FMTBIT_S24_3LE,
100 .rates = SNDRV_PCM_RATE_KNOT,
101 .rate_min = 39062,
102 .rate_max = 39063,
103 .channels_min = 2,
104 .channels_max = 2,
105 .buffer_bytes_max = 60000,
106 .period_bytes_min = 64,
107 .period_bytes_max = 8192,
108 .periods_min = 1,
109 .periods_max = 1024},
110 .snd_line6_rates = {
111 .nrats = 1,
112 .rats = &pod_ratden},
113 .bytes_per_frame = POD_BYTES_PER_FRAME
114 };
115
116 static const char pod_version_header[] = {
117 0xf2, 0x7e, 0x7f, 0x06, 0x02
118 };
119
120 /* forward declarations: */
121 static void pod_startup2(unsigned long data);
122 static void pod_startup3(struct usb_line6_pod *pod);
123
pod_alloc_sysex_buffer(struct usb_line6_pod * pod,int code,int size)124 static char *pod_alloc_sysex_buffer(struct usb_line6_pod *pod, int code,
125 int size)
126 {
127 return line6_alloc_sysex_buffer(&pod->line6, POD_SYSEX_CODE, code,
128 size);
129 }
130
131 /*
132 Process a completely received message.
133 */
line6_pod_process_message(struct usb_line6_pod * pod)134 void line6_pod_process_message(struct usb_line6_pod *pod)
135 {
136 const unsigned char *buf = pod->line6.buffer_message;
137
138 if (memcmp(buf, pod_version_header, sizeof(pod_version_header)) == 0) {
139 pod->firmware_version = buf[13] * 100 + buf[14] * 10 + buf[15];
140 pod->device_id = ((int)buf[8] << 16) | ((int)buf[9] << 8) |
141 (int) buf[10];
142 pod_startup3(pod);
143 return;
144 }
145
146 /* Only look for sysex messages from this device */
147 if (buf[0] != (LINE6_SYSEX_BEGIN | LINE6_CHANNEL_DEVICE) &&
148 buf[0] != (LINE6_SYSEX_BEGIN | LINE6_CHANNEL_UNKNOWN)) {
149 return;
150 }
151 if (memcmp(buf + 1, line6_midi_id, sizeof(line6_midi_id)) != 0)
152 return;
153
154 if (buf[5] == POD_SYSEX_SYSTEM && buf[6] == POD_MONITOR_LEVEL) {
155 short value = ((int)buf[7] << 12) | ((int)buf[8] << 8) |
156 ((int)buf[9] << 4) | (int)buf[10];
157 pod->monitor_level = value;
158 }
159 }
160
161 /*
162 Transmit PODxt Pro control parameter.
163 */
line6_pod_transmit_parameter(struct usb_line6_pod * pod,int param,u8 value)164 void line6_pod_transmit_parameter(struct usb_line6_pod *pod, int param,
165 u8 value)
166 {
167 line6_transmit_parameter(&pod->line6, param, value);
168 }
169
170 /*
171 Send system parameter (from integer).
172 */
pod_set_system_param_int(struct usb_line6_pod * pod,int value,int code)173 static int pod_set_system_param_int(struct usb_line6_pod *pod, int value,
174 int code)
175 {
176 char *sysex;
177 static const int size = 5;
178
179 sysex = pod_alloc_sysex_buffer(pod, POD_SYSEX_SYSTEM, size);
180 if (!sysex)
181 return -ENOMEM;
182 sysex[SYSEX_DATA_OFS] = code;
183 sysex[SYSEX_DATA_OFS + 1] = (value >> 12) & 0x0f;
184 sysex[SYSEX_DATA_OFS + 2] = (value >> 8) & 0x0f;
185 sysex[SYSEX_DATA_OFS + 3] = (value >> 4) & 0x0f;
186 sysex[SYSEX_DATA_OFS + 4] = (value) & 0x0f;
187 line6_send_sysex_message(&pod->line6, sysex, size);
188 kfree(sysex);
189 return 0;
190 }
191
192 /*
193 "read" request on "serial_number" special file.
194 */
pod_get_serial_number(struct device * dev,struct device_attribute * attr,char * buf)195 static ssize_t pod_get_serial_number(struct device *dev,
196 struct device_attribute *attr, char *buf)
197 {
198 struct usb_interface *interface = to_usb_interface(dev);
199 struct usb_line6_pod *pod = usb_get_intfdata(interface);
200 return sprintf(buf, "%d\n", pod->serial_number);
201 }
202
203 /*
204 "read" request on "firmware_version" special file.
205 */
pod_get_firmware_version(struct device * dev,struct device_attribute * attr,char * buf)206 static ssize_t pod_get_firmware_version(struct device *dev,
207 struct device_attribute *attr,
208 char *buf)
209 {
210 struct usb_interface *interface = to_usb_interface(dev);
211 struct usb_line6_pod *pod = usb_get_intfdata(interface);
212 return sprintf(buf, "%d.%02d\n", pod->firmware_version / 100,
213 pod->firmware_version % 100);
214 }
215
216 /*
217 "read" request on "device_id" special file.
218 */
pod_get_device_id(struct device * dev,struct device_attribute * attr,char * buf)219 static ssize_t pod_get_device_id(struct device *dev,
220 struct device_attribute *attr, char *buf)
221 {
222 struct usb_interface *interface = to_usb_interface(dev);
223 struct usb_line6_pod *pod = usb_get_intfdata(interface);
224 return sprintf(buf, "%d\n", pod->device_id);
225 }
226
227 /*
228 POD startup procedure.
229 This is a sequence of functions with special requirements (e.g., must
230 not run immediately after initialization, must not run in interrupt
231 context). After the last one has finished, the device is ready to use.
232 */
233
pod_startup1(struct usb_line6_pod * pod)234 static void pod_startup1(struct usb_line6_pod *pod)
235 {
236 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_INIT);
237
238 /* delay startup procedure: */
239 line6_start_timer(&pod->startup_timer, POD_STARTUP_DELAY, pod_startup2,
240 (unsigned long)pod);
241 }
242
pod_startup2(unsigned long data)243 static void pod_startup2(unsigned long data)
244 {
245 struct usb_line6_pod *pod = (struct usb_line6_pod *)data;
246 struct usb_line6 *line6 = &pod->line6;
247 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_VERSIONREQ);
248
249 /* request firmware version: */
250 line6_version_request_async(line6);
251 }
252
pod_startup3(struct usb_line6_pod * pod)253 static void pod_startup3(struct usb_line6_pod *pod)
254 {
255 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_WORKQUEUE);
256
257 /* schedule work for global work queue: */
258 schedule_work(&pod->startup_work);
259 }
260
pod_startup4(struct work_struct * work)261 static void pod_startup4(struct work_struct *work)
262 {
263 struct usb_line6_pod *pod =
264 container_of(work, struct usb_line6_pod, startup_work);
265 struct usb_line6 *line6 = &pod->line6;
266
267 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_SETUP);
268
269 /* serial number: */
270 line6_read_serial_number(&pod->line6, &pod->serial_number);
271
272 /* ALSA audio interface: */
273 line6_register_audio(line6);
274 }
275
276 /* POD special files: */
277 static DEVICE_ATTR(device_id, S_IRUGO, pod_get_device_id, line6_nop_write);
278 static DEVICE_ATTR(firmware_version, S_IRUGO, pod_get_firmware_version,
279 line6_nop_write);
280 static DEVICE_ATTR(serial_number, S_IRUGO, pod_get_serial_number,
281 line6_nop_write);
282
283 /* control info callback */
snd_pod_control_monitor_info(struct snd_kcontrol * kcontrol,struct snd_ctl_elem_info * uinfo)284 static int snd_pod_control_monitor_info(struct snd_kcontrol *kcontrol,
285 struct snd_ctl_elem_info *uinfo)
286 {
287 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
288 uinfo->count = 1;
289 uinfo->value.integer.min = 0;
290 uinfo->value.integer.max = 65535;
291 return 0;
292 }
293
294 /* control get callback */
snd_pod_control_monitor_get(struct snd_kcontrol * kcontrol,struct snd_ctl_elem_value * ucontrol)295 static int snd_pod_control_monitor_get(struct snd_kcontrol *kcontrol,
296 struct snd_ctl_elem_value *ucontrol)
297 {
298 struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
299 struct usb_line6_pod *pod = (struct usb_line6_pod *)line6pcm->line6;
300 ucontrol->value.integer.value[0] = pod->monitor_level;
301 return 0;
302 }
303
304 /* control put callback */
snd_pod_control_monitor_put(struct snd_kcontrol * kcontrol,struct snd_ctl_elem_value * ucontrol)305 static int snd_pod_control_monitor_put(struct snd_kcontrol *kcontrol,
306 struct snd_ctl_elem_value *ucontrol)
307 {
308 struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
309 struct usb_line6_pod *pod = (struct usb_line6_pod *)line6pcm->line6;
310
311 if (ucontrol->value.integer.value[0] == pod->monitor_level)
312 return 0;
313
314 pod->monitor_level = ucontrol->value.integer.value[0];
315 pod_set_system_param_int(pod, ucontrol->value.integer.value[0],
316 POD_MONITOR_LEVEL);
317 return 1;
318 }
319
320 /* control definition */
321 static struct snd_kcontrol_new pod_control_monitor = {
322 .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
323 .name = "Monitor Playback Volume",
324 .index = 0,
325 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE,
326 .info = snd_pod_control_monitor_info,
327 .get = snd_pod_control_monitor_get,
328 .put = snd_pod_control_monitor_put
329 };
330
331 /*
332 POD destructor.
333 */
pod_destruct(struct usb_interface * interface)334 static void pod_destruct(struct usb_interface *interface)
335 {
336 struct usb_line6_pod *pod = usb_get_intfdata(interface);
337
338 if (pod == NULL)
339 return;
340 line6_cleanup_audio(&pod->line6);
341
342 del_timer(&pod->startup_timer);
343 cancel_work_sync(&pod->startup_work);
344 }
345
346 /*
347 Create sysfs entries.
348 */
pod_create_files2(struct device * dev)349 static int pod_create_files2(struct device *dev)
350 {
351 int err;
352
353 CHECK_RETURN(device_create_file(dev, &dev_attr_device_id));
354 CHECK_RETURN(device_create_file(dev, &dev_attr_firmware_version));
355 CHECK_RETURN(device_create_file(dev, &dev_attr_serial_number));
356 return 0;
357 }
358
359 /*
360 Try to init POD device.
361 */
pod_try_init(struct usb_interface * interface,struct usb_line6_pod * pod)362 static int pod_try_init(struct usb_interface *interface,
363 struct usb_line6_pod *pod)
364 {
365 int err;
366 struct usb_line6 *line6 = &pod->line6;
367
368 init_timer(&pod->startup_timer);
369 INIT_WORK(&pod->startup_work, pod_startup4);
370
371 if ((interface == NULL) || (pod == NULL))
372 return -ENODEV;
373
374 /* create sysfs entries: */
375 err = pod_create_files2(&interface->dev);
376 if (err < 0)
377 return err;
378
379 /* initialize audio system: */
380 err = line6_init_audio(line6);
381 if (err < 0)
382 return err;
383
384 /* initialize MIDI subsystem: */
385 err = line6_init_midi(line6);
386 if (err < 0)
387 return err;
388
389 /* initialize PCM subsystem: */
390 err = line6_init_pcm(line6, &pod_pcm_properties);
391 if (err < 0)
392 return err;
393
394 /* register monitor control: */
395 err = snd_ctl_add(line6->card,
396 snd_ctl_new1(&pod_control_monitor, line6->line6pcm));
397 if (err < 0)
398 return err;
399
400 /*
401 When the sound card is registered at this point, the PODxt Live
402 displays "Invalid Code Error 07", so we do it later in the event
403 handler.
404 */
405
406 if (pod->line6.properties->capabilities & LINE6_BIT_CONTROL) {
407 pod->monitor_level = POD_SYSTEM_INVALID;
408
409 /* initiate startup procedure: */
410 pod_startup1(pod);
411 }
412
413 return 0;
414 }
415
416 /*
417 Init POD device (and clean up in case of failure).
418 */
line6_pod_init(struct usb_interface * interface,struct usb_line6_pod * pod)419 int line6_pod_init(struct usb_interface *interface, struct usb_line6_pod *pod)
420 {
421 int err = pod_try_init(interface, pod);
422
423 if (err < 0)
424 pod_destruct(interface);
425
426 return err;
427 }
428
429 /*
430 POD device disconnected.
431 */
line6_pod_disconnect(struct usb_interface * interface)432 void line6_pod_disconnect(struct usb_interface *interface)
433 {
434 struct usb_line6_pod *pod;
435
436 if (interface == NULL)
437 return;
438 pod = usb_get_intfdata(interface);
439
440 if (pod != NULL) {
441 struct snd_line6_pcm *line6pcm = pod->line6.line6pcm;
442 struct device *dev = &interface->dev;
443
444 if (line6pcm != NULL)
445 line6_pcm_disconnect(line6pcm);
446
447 if (dev != NULL) {
448 /* remove sysfs entries: */
449 device_remove_file(dev, &dev_attr_device_id);
450 device_remove_file(dev, &dev_attr_firmware_version);
451 device_remove_file(dev, &dev_attr_serial_number);
452 }
453 }
454
455 pod_destruct(interface);
456 }
457