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 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 */ 134 static void line6_pod_process_message(struct usb_line6 *line6) 135 { 136 struct usb_line6_pod *pod = (struct usb_line6_pod *) line6; 137 const unsigned char *buf = pod->line6.buffer_message; 138 139 if (memcmp(buf, pod_version_header, sizeof(pod_version_header)) == 0) { 140 pod->firmware_version = buf[13] * 100 + buf[14] * 10 + buf[15]; 141 pod->device_id = ((int)buf[8] << 16) | ((int)buf[9] << 8) | 142 (int) buf[10]; 143 pod_startup3(pod); 144 return; 145 } 146 147 /* Only look for sysex messages from this device */ 148 if (buf[0] != (LINE6_SYSEX_BEGIN | LINE6_CHANNEL_DEVICE) && 149 buf[0] != (LINE6_SYSEX_BEGIN | LINE6_CHANNEL_UNKNOWN)) { 150 return; 151 } 152 if (memcmp(buf + 1, line6_midi_id, sizeof(line6_midi_id)) != 0) 153 return; 154 155 if (buf[5] == POD_SYSEX_SYSTEM && buf[6] == POD_MONITOR_LEVEL) { 156 short value = ((int)buf[7] << 12) | ((int)buf[8] << 8) | 157 ((int)buf[9] << 4) | (int)buf[10]; 158 pod->monitor_level = value; 159 } 160 } 161 162 /* 163 Send system parameter (from integer). 164 */ 165 static int pod_set_system_param_int(struct usb_line6_pod *pod, int value, 166 int code) 167 { 168 char *sysex; 169 static const int size = 5; 170 171 sysex = pod_alloc_sysex_buffer(pod, POD_SYSEX_SYSTEM, size); 172 if (!sysex) 173 return -ENOMEM; 174 sysex[SYSEX_DATA_OFS] = code; 175 sysex[SYSEX_DATA_OFS + 1] = (value >> 12) & 0x0f; 176 sysex[SYSEX_DATA_OFS + 2] = (value >> 8) & 0x0f; 177 sysex[SYSEX_DATA_OFS + 3] = (value >> 4) & 0x0f; 178 sysex[SYSEX_DATA_OFS + 4] = (value) & 0x0f; 179 line6_send_sysex_message(&pod->line6, sysex, size); 180 kfree(sysex); 181 return 0; 182 } 183 184 /* 185 "read" request on "serial_number" special file. 186 */ 187 static ssize_t serial_number_show(struct device *dev, 188 struct device_attribute *attr, char *buf) 189 { 190 struct usb_interface *interface = to_usb_interface(dev); 191 struct usb_line6_pod *pod = usb_get_intfdata(interface); 192 193 return sprintf(buf, "%d\n", pod->serial_number); 194 } 195 196 /* 197 "read" request on "firmware_version" special file. 198 */ 199 static ssize_t firmware_version_show(struct device *dev, 200 struct device_attribute *attr, char *buf) 201 { 202 struct usb_interface *interface = to_usb_interface(dev); 203 struct usb_line6_pod *pod = usb_get_intfdata(interface); 204 205 return sprintf(buf, "%d.%02d\n", pod->firmware_version / 100, 206 pod->firmware_version % 100); 207 } 208 209 /* 210 "read" request on "device_id" special file. 211 */ 212 static ssize_t device_id_show(struct device *dev, 213 struct device_attribute *attr, char *buf) 214 { 215 struct usb_interface *interface = to_usb_interface(dev); 216 struct usb_line6_pod *pod = usb_get_intfdata(interface); 217 218 return sprintf(buf, "%d\n", pod->device_id); 219 } 220 221 /* 222 POD startup procedure. 223 This is a sequence of functions with special requirements (e.g., must 224 not run immediately after initialization, must not run in interrupt 225 context). After the last one has finished, the device is ready to use. 226 */ 227 228 static void pod_startup1(struct usb_line6_pod *pod) 229 { 230 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_INIT); 231 232 /* delay startup procedure: */ 233 line6_start_timer(&pod->startup_timer, POD_STARTUP_DELAY, pod_startup2, 234 (unsigned long)pod); 235 } 236 237 static void pod_startup2(unsigned long data) 238 { 239 struct usb_line6_pod *pod = (struct usb_line6_pod *)data; 240 struct usb_line6 *line6 = &pod->line6; 241 242 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_VERSIONREQ); 243 244 /* request firmware version: */ 245 line6_version_request_async(line6); 246 } 247 248 static void pod_startup3(struct usb_line6_pod *pod) 249 { 250 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_WORKQUEUE); 251 252 /* schedule work for global work queue: */ 253 schedule_work(&pod->startup_work); 254 } 255 256 static void pod_startup4(struct work_struct *work) 257 { 258 struct usb_line6_pod *pod = 259 container_of(work, struct usb_line6_pod, startup_work); 260 struct usb_line6 *line6 = &pod->line6; 261 262 CHECK_STARTUP_PROGRESS(pod->startup_progress, POD_STARTUP_SETUP); 263 264 /* serial number: */ 265 line6_read_serial_number(&pod->line6, &pod->serial_number); 266 267 /* ALSA audio interface: */ 268 line6_register_audio(line6); 269 } 270 271 /* POD special files: */ 272 static DEVICE_ATTR_RO(device_id); 273 static DEVICE_ATTR_RO(firmware_version); 274 static DEVICE_ATTR_RO(serial_number); 275 276 /* control info callback */ 277 static int snd_pod_control_monitor_info(struct snd_kcontrol *kcontrol, 278 struct snd_ctl_elem_info *uinfo) 279 { 280 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; 281 uinfo->count = 1; 282 uinfo->value.integer.min = 0; 283 uinfo->value.integer.max = 65535; 284 return 0; 285 } 286 287 /* control get callback */ 288 static int snd_pod_control_monitor_get(struct snd_kcontrol *kcontrol, 289 struct snd_ctl_elem_value *ucontrol) 290 { 291 struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol); 292 struct usb_line6_pod *pod = (struct usb_line6_pod *)line6pcm->line6; 293 294 ucontrol->value.integer.value[0] = pod->monitor_level; 295 return 0; 296 } 297 298 /* control put callback */ 299 static int snd_pod_control_monitor_put(struct snd_kcontrol *kcontrol, 300 struct snd_ctl_elem_value *ucontrol) 301 { 302 struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol); 303 struct usb_line6_pod *pod = (struct usb_line6_pod *)line6pcm->line6; 304 305 if (ucontrol->value.integer.value[0] == pod->monitor_level) 306 return 0; 307 308 pod->monitor_level = ucontrol->value.integer.value[0]; 309 pod_set_system_param_int(pod, ucontrol->value.integer.value[0], 310 POD_MONITOR_LEVEL); 311 return 1; 312 } 313 314 /* control definition */ 315 static struct snd_kcontrol_new pod_control_monitor = { 316 .iface = SNDRV_CTL_ELEM_IFACE_MIXER, 317 .name = "Monitor Playback Volume", 318 .index = 0, 319 .access = SNDRV_CTL_ELEM_ACCESS_READWRITE, 320 .info = snd_pod_control_monitor_info, 321 .get = snd_pod_control_monitor_get, 322 .put = snd_pod_control_monitor_put 323 }; 324 325 /* 326 POD destructor. 327 */ 328 static void pod_destruct(struct usb_interface *interface) 329 { 330 struct usb_line6_pod *pod = usb_get_intfdata(interface); 331 332 if (pod == NULL) 333 return; 334 line6_cleanup_audio(&pod->line6); 335 336 del_timer(&pod->startup_timer); 337 cancel_work_sync(&pod->startup_work); 338 } 339 340 /* 341 POD device disconnected. 342 */ 343 static void line6_pod_disconnect(struct usb_interface *interface) 344 { 345 struct usb_line6_pod *pod; 346 347 if (interface == NULL) 348 return; 349 pod = usb_get_intfdata(interface); 350 351 if (pod != NULL) { 352 struct snd_line6_pcm *line6pcm = pod->line6.line6pcm; 353 struct device *dev = &interface->dev; 354 355 if (line6pcm != NULL) 356 line6_pcm_disconnect(line6pcm); 357 358 if (dev != NULL) { 359 /* remove sysfs entries: */ 360 device_remove_file(dev, &dev_attr_device_id); 361 device_remove_file(dev, &dev_attr_firmware_version); 362 device_remove_file(dev, &dev_attr_serial_number); 363 } 364 } 365 366 pod_destruct(interface); 367 } 368 369 /* 370 Create sysfs entries. 371 */ 372 static int pod_create_files2(struct device *dev) 373 { 374 int err; 375 376 CHECK_RETURN(device_create_file(dev, &dev_attr_device_id)); 377 CHECK_RETURN(device_create_file(dev, &dev_attr_firmware_version)); 378 CHECK_RETURN(device_create_file(dev, &dev_attr_serial_number)); 379 return 0; 380 } 381 382 /* 383 Try to init POD device. 384 */ 385 static int pod_try_init(struct usb_interface *interface, 386 struct usb_line6 *line6) 387 { 388 int err; 389 struct usb_line6_pod *pod = (struct usb_line6_pod *) line6; 390 391 line6->process_message = line6_pod_process_message; 392 line6->disconnect = line6_pod_disconnect; 393 394 init_timer(&pod->startup_timer); 395 INIT_WORK(&pod->startup_work, pod_startup4); 396 397 if ((interface == NULL) || (pod == NULL)) 398 return -ENODEV; 399 400 /* create sysfs entries: */ 401 err = pod_create_files2(&interface->dev); 402 if (err < 0) 403 return err; 404 405 /* initialize audio system: */ 406 err = line6_init_audio(line6); 407 if (err < 0) 408 return err; 409 410 /* initialize MIDI subsystem: */ 411 err = line6_init_midi(line6); 412 if (err < 0) 413 return err; 414 415 /* initialize PCM subsystem: */ 416 err = line6_init_pcm(line6, &pod_pcm_properties); 417 if (err < 0) 418 return err; 419 420 /* register monitor control: */ 421 err = snd_ctl_add(line6->card, 422 snd_ctl_new1(&pod_control_monitor, line6->line6pcm)); 423 if (err < 0) 424 return err; 425 426 /* 427 When the sound card is registered at this point, the PODxt Live 428 displays "Invalid Code Error 07", so we do it later in the event 429 handler. 430 */ 431 432 if (pod->line6.properties->capabilities & LINE6_CAP_CONTROL) { 433 pod->monitor_level = POD_SYSTEM_INVALID; 434 435 /* initiate startup procedure: */ 436 pod_startup1(pod); 437 } 438 439 return 0; 440 } 441 442 /* 443 Init POD device (and clean up in case of failure). 444 */ 445 int line6_pod_init(struct usb_interface *interface, struct usb_line6 *line6) 446 { 447 int err = pod_try_init(interface, line6); 448 449 if (err < 0) 450 pod_destruct(interface); 451 452 return err; 453 } 454