linux/sound/usb/line6/toneport.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-only
   2/*
   3 * Line 6 Linux USB driver
   4 *
   5 * Copyright (C) 2004-2010 Markus Grabner (grabner@icg.tugraz.at)
   6 *                         Emil Myhrman (emil.myhrman@gmail.com)
   7 */
   8
   9#include <linux/wait.h>
  10#include <linux/usb.h>
  11#include <linux/slab.h>
  12#include <linux/module.h>
  13#include <linux/leds.h>
  14#include <sound/core.h>
  15#include <sound/control.h>
  16
  17#include "capture.h"
  18#include "driver.h"
  19#include "playback.h"
  20
  21enum line6_device_type {
  22        LINE6_GUITARPORT,
  23        LINE6_PODSTUDIO_GX,
  24        LINE6_PODSTUDIO_UX1,
  25        LINE6_PODSTUDIO_UX2,
  26        LINE6_TONEPORT_GX,
  27        LINE6_TONEPORT_UX1,
  28        LINE6_TONEPORT_UX2,
  29};
  30
  31struct usb_line6_toneport;
  32
  33struct toneport_led {
  34        struct led_classdev dev;
  35        char name[64];
  36        struct usb_line6_toneport *toneport;
  37        bool registered;
  38};
  39
  40struct usb_line6_toneport {
  41        /* Generic Line 6 USB data */
  42        struct usb_line6 line6;
  43
  44        /* Source selector */
  45        int source;
  46
  47        /* Serial number of device */
  48        u32 serial_number;
  49
  50        /* Firmware version (x 100) */
  51        u8 firmware_version;
  52
  53        /* Device type */
  54        enum line6_device_type type;
  55
  56        /* LED instances */
  57        struct toneport_led leds[2];
  58};
  59
  60#define line6_to_toneport(x) container_of(x, struct usb_line6_toneport, line6)
  61
  62static int toneport_send_cmd(struct usb_device *usbdev, int cmd1, int cmd2);
  63
  64#define TONEPORT_PCM_DELAY 1
  65
  66static const struct snd_ratden toneport_ratden = {
  67        .num_min = 44100,
  68        .num_max = 44100,
  69        .num_step = 1,
  70        .den = 1
  71};
  72
  73static struct line6_pcm_properties toneport_pcm_properties = {
  74        .playback_hw = {
  75                                  .info = (SNDRV_PCM_INFO_MMAP |
  76                                           SNDRV_PCM_INFO_INTERLEAVED |
  77                                           SNDRV_PCM_INFO_BLOCK_TRANSFER |
  78                                           SNDRV_PCM_INFO_MMAP_VALID |
  79                                           SNDRV_PCM_INFO_PAUSE |
  80                                           SNDRV_PCM_INFO_SYNC_START),
  81                                  .formats = SNDRV_PCM_FMTBIT_S16_LE,
  82                                  .rates = SNDRV_PCM_RATE_KNOT,
  83                                  .rate_min = 44100,
  84                                  .rate_max = 44100,
  85                                  .channels_min = 2,
  86                                  .channels_max = 2,
  87                                  .buffer_bytes_max = 60000,
  88                                  .period_bytes_min = 64,
  89                                  .period_bytes_max = 8192,
  90                                  .periods_min = 1,
  91                                  .periods_max = 1024},
  92        .capture_hw = {
  93                                 .info = (SNDRV_PCM_INFO_MMAP |
  94                                          SNDRV_PCM_INFO_INTERLEAVED |
  95                                          SNDRV_PCM_INFO_BLOCK_TRANSFER |
  96                                          SNDRV_PCM_INFO_MMAP_VALID |
  97                                          SNDRV_PCM_INFO_SYNC_START),
  98                                 .formats = SNDRV_PCM_FMTBIT_S16_LE,
  99                                 .rates = SNDRV_PCM_RATE_KNOT,
 100                                 .rate_min = 44100,
 101                                 .rate_max = 44100,
 102                                 .channels_min = 2,
 103                                 .channels_max = 2,
 104                                 .buffer_bytes_max = 60000,
 105                                 .period_bytes_min = 64,
 106                                 .period_bytes_max = 8192,
 107                                 .periods_min = 1,
 108                                 .periods_max = 1024},
 109        .rates = {
 110                            .nrats = 1,
 111                            .rats = &toneport_ratden},
 112        .bytes_per_channel = 2
 113};
 114
 115static const struct {
 116        const char *name;
 117        int code;
 118} toneport_source_info[] = {
 119        {"Microphone", 0x0a01},
 120        {"Line", 0x0801},
 121        {"Instrument", 0x0b01},
 122        {"Inst & Mic", 0x0901}
 123};
 124
 125static int toneport_send_cmd(struct usb_device *usbdev, int cmd1, int cmd2)
 126{
 127        int ret;
 128
 129        ret = usb_control_msg_send(usbdev, 0, 0x67,
 130                                   USB_TYPE_VENDOR | USB_RECIP_DEVICE | USB_DIR_OUT,
 131                                   cmd1, cmd2, NULL, 0, LINE6_TIMEOUT * HZ,
 132                                   GFP_KERNEL);
 133
 134        if (ret) {
 135                dev_err(&usbdev->dev, "send failed (error %d)\n", ret);
 136                return ret;
 137        }
 138
 139        return 0;
 140}
 141
 142/* monitor info callback */
 143static int snd_toneport_monitor_info(struct snd_kcontrol *kcontrol,
 144                                     struct snd_ctl_elem_info *uinfo)
 145{
 146        uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
 147        uinfo->count = 1;
 148        uinfo->value.integer.min = 0;
 149        uinfo->value.integer.max = 256;
 150        return 0;
 151}
 152
 153/* monitor get callback */
 154static int snd_toneport_monitor_get(struct snd_kcontrol *kcontrol,
 155                                    struct snd_ctl_elem_value *ucontrol)
 156{
 157        struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
 158
 159        ucontrol->value.integer.value[0] = line6pcm->volume_monitor;
 160        return 0;
 161}
 162
 163/* monitor put callback */
 164static int snd_toneport_monitor_put(struct snd_kcontrol *kcontrol,
 165                                    struct snd_ctl_elem_value *ucontrol)
 166{
 167        struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
 168        int err;
 169
 170        if (ucontrol->value.integer.value[0] == line6pcm->volume_monitor)
 171                return 0;
 172
 173        line6pcm->volume_monitor = ucontrol->value.integer.value[0];
 174
 175        if (line6pcm->volume_monitor > 0) {
 176                err = line6_pcm_acquire(line6pcm, LINE6_STREAM_MONITOR, true);
 177                if (err < 0) {
 178                        line6pcm->volume_monitor = 0;
 179                        line6_pcm_release(line6pcm, LINE6_STREAM_MONITOR);
 180                        return err;
 181                }
 182        } else {
 183                line6_pcm_release(line6pcm, LINE6_STREAM_MONITOR);
 184        }
 185
 186        return 1;
 187}
 188
 189/* source info callback */
 190static int snd_toneport_source_info(struct snd_kcontrol *kcontrol,
 191                                    struct snd_ctl_elem_info *uinfo)
 192{
 193        const int size = ARRAY_SIZE(toneport_source_info);
 194
 195        uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
 196        uinfo->count = 1;
 197        uinfo->value.enumerated.items = size;
 198
 199        if (uinfo->value.enumerated.item >= size)
 200                uinfo->value.enumerated.item = size - 1;
 201
 202        strcpy(uinfo->value.enumerated.name,
 203               toneport_source_info[uinfo->value.enumerated.item].name);
 204
 205        return 0;
 206}
 207
 208/* source get callback */
 209static int snd_toneport_source_get(struct snd_kcontrol *kcontrol,
 210                                   struct snd_ctl_elem_value *ucontrol)
 211{
 212        struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
 213        struct usb_line6_toneport *toneport = line6_to_toneport(line6pcm->line6);
 214
 215        ucontrol->value.enumerated.item[0] = toneport->source;
 216        return 0;
 217}
 218
 219/* source put callback */
 220static int snd_toneport_source_put(struct snd_kcontrol *kcontrol,
 221                                   struct snd_ctl_elem_value *ucontrol)
 222{
 223        struct snd_line6_pcm *line6pcm = snd_kcontrol_chip(kcontrol);
 224        struct usb_line6_toneport *toneport = line6_to_toneport(line6pcm->line6);
 225        unsigned int source;
 226
 227        source = ucontrol->value.enumerated.item[0];
 228        if (source >= ARRAY_SIZE(toneport_source_info))
 229                return -EINVAL;
 230        if (source == toneport->source)
 231                return 0;
 232
 233        toneport->source = source;
 234        toneport_send_cmd(toneport->line6.usbdev,
 235                          toneport_source_info[source].code, 0x0000);
 236        return 1;
 237}
 238
 239static void toneport_startup(struct usb_line6 *line6)
 240{
 241        line6_pcm_acquire(line6->line6pcm, LINE6_STREAM_MONITOR, true);
 242}
 243
 244/* control definition */
 245static const struct snd_kcontrol_new toneport_control_monitor = {
 246        .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
 247        .name = "Monitor Playback Volume",
 248        .index = 0,
 249        .access = SNDRV_CTL_ELEM_ACCESS_READWRITE,
 250        .info = snd_toneport_monitor_info,
 251        .get = snd_toneport_monitor_get,
 252        .put = snd_toneport_monitor_put
 253};
 254
 255/* source selector definition */
 256static const struct snd_kcontrol_new toneport_control_source = {
 257        .iface = SNDRV_CTL_ELEM_IFACE_MIXER,
 258        .name = "PCM Capture Source",
 259        .index = 0,
 260        .access = SNDRV_CTL_ELEM_ACCESS_READWRITE,
 261        .info = snd_toneport_source_info,
 262        .get = snd_toneport_source_get,
 263        .put = snd_toneport_source_put
 264};
 265
 266/*
 267        For the led on Guitarport.
 268        Brightness goes from 0x00 to 0x26. Set a value above this to have led
 269        blink.
 270        (void cmd_0x02(byte red, byte green)
 271*/
 272
 273static bool toneport_has_led(struct usb_line6_toneport *toneport)
 274{
 275        switch (toneport->type) {
 276        case LINE6_GUITARPORT:
 277        case LINE6_TONEPORT_GX:
 278        /* add your device here if you are missing support for the LEDs */
 279                return true;
 280
 281        default:
 282                return false;
 283        }
 284}
 285
 286static const char * const toneport_led_colors[2] = { "red", "green" };
 287static const int toneport_led_init_vals[2] = { 0x00, 0x26 };
 288
 289static void toneport_update_led(struct usb_line6_toneport *toneport)
 290{
 291        toneport_send_cmd(toneport->line6.usbdev,
 292                          (toneport->leds[0].dev.brightness << 8) | 0x0002,
 293                          toneport->leds[1].dev.brightness);
 294}
 295
 296static void toneport_led_brightness_set(struct led_classdev *led_cdev,
 297                                        enum led_brightness brightness)
 298{
 299        struct toneport_led *leds =
 300                container_of(led_cdev, struct toneport_led, dev);
 301        toneport_update_led(leds->toneport);
 302}
 303
 304static int toneport_init_leds(struct usb_line6_toneport *toneport)
 305{
 306        struct device *dev = &toneport->line6.usbdev->dev;
 307        int i, err;
 308
 309        for (i = 0; i < 2; i++) {
 310                struct toneport_led *led = &toneport->leds[i];
 311                struct led_classdev *leddev = &led->dev;
 312
 313                led->toneport = toneport;
 314                snprintf(led->name, sizeof(led->name), "%s::%s",
 315                         dev_name(dev), toneport_led_colors[i]);
 316                leddev->name = led->name;
 317                leddev->brightness = toneport_led_init_vals[i];
 318                leddev->max_brightness = 0x26;
 319                leddev->brightness_set = toneport_led_brightness_set;
 320                err = led_classdev_register(dev, leddev);
 321                if (err)
 322                        return err;
 323                led->registered = true;
 324        }
 325
 326        return 0;
 327}
 328
 329static void toneport_remove_leds(struct usb_line6_toneport *toneport)
 330{
 331        struct toneport_led *led;
 332        int i;
 333
 334        for (i = 0; i < 2; i++) {
 335                led = &toneport->leds[i];
 336                if (!led->registered)
 337                        break;
 338                led_classdev_unregister(&led->dev);
 339                led->registered = false;
 340        }
 341}
 342
 343static bool toneport_has_source_select(struct usb_line6_toneport *toneport)
 344{
 345        switch (toneport->type) {
 346        case LINE6_TONEPORT_UX1:
 347        case LINE6_TONEPORT_UX2:
 348        case LINE6_PODSTUDIO_UX1:
 349        case LINE6_PODSTUDIO_UX2:
 350                return true;
 351
 352        default:
 353                return false;
 354        }
 355}
 356
 357/*
 358        Setup Toneport device.
 359*/
 360static int toneport_setup(struct usb_line6_toneport *toneport)
 361{
 362        u32 *ticks;
 363        struct usb_line6 *line6 = &toneport->line6;
 364        struct usb_device *usbdev = line6->usbdev;
 365
 366        ticks = kmalloc(sizeof(*ticks), GFP_KERNEL);
 367        if (!ticks)
 368                return -ENOMEM;
 369
 370        /* sync time on device with host: */
 371        /* note: 32-bit timestamps overflow in year 2106 */
 372        *ticks = (u32)ktime_get_real_seconds();
 373        line6_write_data(line6, 0x80c6, ticks, 4);
 374        kfree(ticks);
 375
 376        /* enable device: */
 377        toneport_send_cmd(usbdev, 0x0301, 0x0000);
 378
 379        /* initialize source select: */
 380        if (toneport_has_source_select(toneport))
 381                toneport_send_cmd(usbdev,
 382                                  toneport_source_info[toneport->source].code,
 383                                  0x0000);
 384
 385        if (toneport_has_led(toneport))
 386                toneport_update_led(toneport);
 387
 388        schedule_delayed_work(&toneport->line6.startup_work,
 389                              msecs_to_jiffies(TONEPORT_PCM_DELAY * 1000));
 390        return 0;
 391}
 392
 393/*
 394        Toneport device disconnected.
 395*/
 396static void line6_toneport_disconnect(struct usb_line6 *line6)
 397{
 398        struct usb_line6_toneport *toneport = line6_to_toneport(line6);
 399
 400        if (toneport_has_led(toneport))
 401                toneport_remove_leds(toneport);
 402}
 403
 404
 405/*
 406         Try to init Toneport device.
 407*/
 408static int toneport_init(struct usb_line6 *line6,
 409                         const struct usb_device_id *id)
 410{
 411        int err;
 412        struct usb_line6_toneport *toneport = line6_to_toneport(line6);
 413
 414        toneport->type = id->driver_info;
 415
 416        line6->disconnect = line6_toneport_disconnect;
 417        line6->startup = toneport_startup;
 418
 419        /* initialize PCM subsystem: */
 420        err = line6_init_pcm(line6, &toneport_pcm_properties);
 421        if (err < 0)
 422                return err;
 423
 424        /* register monitor control: */
 425        err = snd_ctl_add(line6->card,
 426                          snd_ctl_new1(&toneport_control_monitor,
 427                                       line6->line6pcm));
 428        if (err < 0)
 429                return err;
 430
 431        /* register source select control: */
 432        if (toneport_has_source_select(toneport)) {
 433                err =
 434                    snd_ctl_add(line6->card,
 435                                snd_ctl_new1(&toneport_control_source,
 436                                             line6->line6pcm));
 437                if (err < 0)
 438                        return err;
 439        }
 440
 441        line6_read_serial_number(line6, &toneport->serial_number);
 442        line6_read_data(line6, 0x80c2, &toneport->firmware_version, 1);
 443
 444        if (toneport_has_led(toneport)) {
 445                err = toneport_init_leds(toneport);
 446                if (err < 0)
 447                        return err;
 448        }
 449
 450        err = toneport_setup(toneport);
 451        if (err)
 452                return err;
 453
 454        /* register audio system: */
 455        return snd_card_register(line6->card);
 456}
 457
 458#ifdef CONFIG_PM
 459/*
 460        Resume Toneport device after reset.
 461*/
 462static int toneport_reset_resume(struct usb_interface *interface)
 463{
 464        int err;
 465
 466        err = toneport_setup(usb_get_intfdata(interface));
 467        if (err)
 468                return err;
 469        return line6_resume(interface);
 470}
 471#endif
 472
 473#define LINE6_DEVICE(prod) USB_DEVICE(0x0e41, prod)
 474#define LINE6_IF_NUM(prod, n) USB_DEVICE_INTERFACE_NUMBER(0x0e41, prod, n)
 475
 476/* table of devices that work with this driver */
 477static const struct usb_device_id toneport_id_table[] = {
 478        { LINE6_DEVICE(0x4750),    .driver_info = LINE6_GUITARPORT },
 479        { LINE6_DEVICE(0x4153),    .driver_info = LINE6_PODSTUDIO_GX },
 480        { LINE6_DEVICE(0x4150),    .driver_info = LINE6_PODSTUDIO_UX1 },
 481        { LINE6_IF_NUM(0x4151, 0), .driver_info = LINE6_PODSTUDIO_UX2 },
 482        { LINE6_DEVICE(0x4147),    .driver_info = LINE6_TONEPORT_GX },
 483        { LINE6_DEVICE(0x4141),    .driver_info = LINE6_TONEPORT_UX1 },
 484        { LINE6_IF_NUM(0x4142, 0), .driver_info = LINE6_TONEPORT_UX2 },
 485        {}
 486};
 487
 488MODULE_DEVICE_TABLE(usb, toneport_id_table);
 489
 490static const struct line6_properties toneport_properties_table[] = {
 491        [LINE6_GUITARPORT] = {
 492                .id = "GuitarPort",
 493                .name = "GuitarPort",
 494                .capabilities   = LINE6_CAP_PCM,
 495                .altsetting = 2,  /* 1..4 seem to be ok */
 496                /* no control channel */
 497                .ep_audio_r = 0x82,
 498                .ep_audio_w = 0x01,
 499        },
 500        [LINE6_PODSTUDIO_GX] = {
 501                .id = "PODStudioGX",
 502                .name = "POD Studio GX",
 503                .capabilities   = LINE6_CAP_PCM,
 504                .altsetting = 2,  /* 1..4 seem to be ok */
 505                /* no control channel */
 506                .ep_audio_r = 0x82,
 507                .ep_audio_w = 0x01,
 508        },
 509        [LINE6_PODSTUDIO_UX1] = {
 510                .id = "PODStudioUX1",
 511                .name = "POD Studio UX1",
 512                .capabilities   = LINE6_CAP_PCM,
 513                .altsetting = 2,  /* 1..4 seem to be ok */
 514                /* no control channel */
 515                .ep_audio_r = 0x82,
 516                .ep_audio_w = 0x01,
 517        },
 518        [LINE6_PODSTUDIO_UX2] = {
 519                .id = "PODStudioUX2",
 520                .name = "POD Studio UX2",
 521                .capabilities   = LINE6_CAP_PCM,
 522                .altsetting = 2,  /* defaults to 44.1kHz, 16-bit */
 523                /* no control channel */
 524                .ep_audio_r = 0x82,
 525                .ep_audio_w = 0x01,
 526        },
 527        [LINE6_TONEPORT_GX] = {
 528                .id = "TonePortGX",
 529                .name = "TonePort GX",
 530                .capabilities   = LINE6_CAP_PCM,
 531                .altsetting = 2,  /* 1..4 seem to be ok */
 532                /* no control channel */
 533                .ep_audio_r = 0x82,
 534                .ep_audio_w = 0x01,
 535        },
 536        [LINE6_TONEPORT_UX1] = {
 537                .id = "TonePortUX1",
 538                .name = "TonePort UX1",
 539                .capabilities   = LINE6_CAP_PCM,
 540                .altsetting = 2,  /* 1..4 seem to be ok */
 541                /* no control channel */
 542                .ep_audio_r = 0x82,
 543                .ep_audio_w = 0x01,
 544        },
 545        [LINE6_TONEPORT_UX2] = {
 546                .id = "TonePortUX2",
 547                .name = "TonePort UX2",
 548                .capabilities   = LINE6_CAP_PCM,
 549                .altsetting = 2,  /* defaults to 44.1kHz, 16-bit */
 550                /* no control channel */
 551                .ep_audio_r = 0x82,
 552                .ep_audio_w = 0x01,
 553        },
 554};
 555
 556/*
 557        Probe USB device.
 558*/
 559static int toneport_probe(struct usb_interface *interface,
 560                          const struct usb_device_id *id)
 561{
 562        return line6_probe(interface, id, "Line6-TonePort",
 563                           &toneport_properties_table[id->driver_info],
 564                           toneport_init, sizeof(struct usb_line6_toneport));
 565}
 566
 567static struct usb_driver toneport_driver = {
 568        .name = KBUILD_MODNAME,
 569        .probe = toneport_probe,
 570        .disconnect = line6_disconnect,
 571#ifdef CONFIG_PM
 572        .suspend = line6_suspend,
 573        .resume = line6_resume,
 574        .reset_resume = toneport_reset_resume,
 575#endif
 576        .id_table = toneport_id_table,
 577};
 578
 579module_usb_driver(toneport_driver);
 580
 581MODULE_DESCRIPTION("TonePort USB driver");
 582MODULE_LICENSE("GPL");
 583