summaryrefslogtreecommitdiffstats
path: root/sound/usb/caiaq
diff options
context:
space:
mode:
authorRussell King <rmk@dyn-67.arm.linux.org.uk>2009-03-28 20:29:51 +0000
committerRussell King <rmk+kernel@arm.linux.org.uk>2009-03-28 20:29:51 +0000
commited40d0c472b136682b2fcba05f89762859c7374f (patch)
tree076b83a26bcd63d6158463735dd34c10bbc591dc /sound/usb/caiaq
parent9e495834e59ca9b29f1a1f63b9f5533bb022ac49 (diff)
parent5d80f8e5a9dc9c9a94d4aeaa567e219a808b8a4a (diff)
Merge branch 'origin' into devel
Conflicts: sound/soc/pxa/pxa2xx-i2s.c
Diffstat (limited to 'sound/usb/caiaq')
-rw-r--r--sound/usb/caiaq/caiaq-audio.c15
-rw-r--r--sound/usb/caiaq/caiaq-control.c42
-rw-r--r--sound/usb/caiaq/caiaq-device.c46
-rw-r--r--sound/usb/caiaq/caiaq-device.h6
4 files changed, 88 insertions, 21 deletions
diff --git a/sound/usb/caiaq/caiaq-audio.c b/sound/usb/caiaq/caiaq-audio.c
index b3a60332583..08d51e0c9fe 100644
--- a/sound/usb/caiaq/caiaq-audio.c
+++ b/sound/usb/caiaq/caiaq-audio.c
@@ -114,6 +114,7 @@ static int stream_start(struct snd_usb_caiaqdev *dev)
dev->output_panic = 0;
dev->first_packet = 1;
dev->streaming = 1;
+ dev->warned = 0;
for (i = 0; i < N_URBS; i++) {
ret = usb_submit_urb(dev->data_urbs_in[i], GFP_ATOMIC);
@@ -376,6 +377,9 @@ static void read_in_urb_mode2(struct snd_usb_caiaqdev *dev,
for (stream = 0; stream < dev->n_streams; stream++, i++) {
sub = dev->sub_capture[stream];
+ if (dev->input_panic)
+ usb_buf[i] = 0;
+
if (sub) {
struct snd_pcm_runtime *rt = sub->runtime;
char *audio_buf = rt->dma_area;
@@ -397,6 +401,9 @@ static void read_in_urb(struct snd_usb_caiaqdev *dev,
if (!dev->streaming)
return;
+ if (iso->actual_length < dev->bpp)
+ return;
+
switch (dev->spec.data_alignment) {
case 0:
read_in_urb_mode0(dev, urb, iso);
@@ -406,10 +413,11 @@ static void read_in_urb(struct snd_usb_caiaqdev *dev,
break;
}
- if (dev->input_panic || dev->output_panic) {
+ if ((dev->input_panic || dev->output_panic) && !dev->warned) {
debug("streaming error detected %s %s\n",
dev->input_panic ? "(input)" : "",
dev->output_panic ? "(output)" : "");
+ dev->warned = 1;
}
}
@@ -638,9 +646,10 @@ int snd_usb_caiaq_audio_init(struct snd_usb_caiaqdev *dev)
case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AK1):
case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_RIGKONTROL3):
case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_SESSIONIO):
- dev->samplerates |= SNDRV_PCM_RATE_88200;
+ case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_GUITARRIGMOBILE):
dev->samplerates |= SNDRV_PCM_RATE_192000;
- break;
+ /* fall thru */
+ case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO4DJ):
case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO8DJ):
dev->samplerates |= SNDRV_PCM_RATE_88200;
break;
diff --git a/sound/usb/caiaq/caiaq-control.c b/sound/usb/caiaq/caiaq-control.c
index ccd763dd716..e92c2bbf4fe 100644
--- a/sound/usb/caiaq/caiaq-control.c
+++ b/sound/usb/caiaq/caiaq-control.c
@@ -39,12 +39,12 @@ static int control_info(struct snd_kcontrol *kcontrol,
struct snd_usb_caiaqdev *dev = caiaqdev(chip->card);
int pos = kcontrol->private_value;
int is_intval = pos & CNT_INTVAL;
+ unsigned int id = dev->chip.usb_id;
uinfo->count = 1;
pos &= ~CNT_INTVAL;
- if (dev->chip.usb_id ==
- USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO8DJ)
+ if (id == USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO8DJ)
&& (pos == 0)) {
/* current input mode of A8DJ */
uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
@@ -53,6 +53,15 @@ static int control_info(struct snd_kcontrol *kcontrol,
return 0;
}
+ if (id == USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO4DJ)
+ && (pos == 0)) {
+ /* current input mode of A4DJ */
+ uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
+ uinfo->value.integer.min = 0;
+ uinfo->value.integer.max = 1;
+ return 0;
+ }
+
if (is_intval) {
uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
uinfo->value.integer.min = 0;
@@ -73,6 +82,14 @@ static int control_get(struct snd_kcontrol *kcontrol,
struct snd_usb_caiaqdev *dev = caiaqdev(chip->card);
int pos = kcontrol->private_value;
+ if (dev->chip.usb_id ==
+ USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO4DJ)) {
+ /* A4DJ has only one control */
+ /* do not expose hardware input mode 0 */
+ ucontrol->value.integer.value[0] = dev->control_state[0] - 1;
+ return 0;
+ }
+
if (pos & CNT_INTVAL)
ucontrol->value.integer.value[0]
= dev->control_state[pos & ~CNT_INTVAL];
@@ -90,10 +107,20 @@ static int control_put(struct snd_kcontrol *kcontrol,
struct snd_usb_caiaqdev *dev = caiaqdev(chip->card);
int pos = kcontrol->private_value;
+ if (dev->chip.usb_id ==
+ USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO4DJ)) {
+ /* A4DJ has only one control */
+ /* do not expose hardware input mode 0 */
+ dev->control_state[0] = ucontrol->value.integer.value[0] + 1;
+ snd_usb_caiaq_send_command(dev, EP1_CMD_WRITE_IO,
+ dev->control_state, sizeof(dev->control_state));
+ return 1;
+ }
+
if (pos & CNT_INTVAL) {
dev->control_state[pos & ~CNT_INTVAL]
= ucontrol->value.integer.value[0];
- snd_usb_caiaq_send_command(dev, EP1_CMD_DIMM_LEDS,
+ snd_usb_caiaq_send_command(dev, EP1_CMD_WRITE_IO,
dev->control_state, sizeof(dev->control_state));
} else {
if (ucontrol->value.integer.value[0])
@@ -243,10 +270,13 @@ static struct caiaq_controller a8dj_controller[] = {
{ "GND lift for TC Vinyl mode", 24 + 0 },
{ "GND lift for TC CD/Line mode", 24 + 1 },
{ "GND lift for phono mode", 24 + 2 },
- { "GND lift for TC Vinyl mode", 24 + 3 },
{ "Software lock", 40 }
};
+static struct caiaq_controller a4dj_controller[] = {
+ { "Current input mode", 0 | CNT_INTVAL }
+};
+
static int __devinit add_controls(struct caiaq_controller *c, int num,
struct snd_usb_caiaqdev *dev)
{
@@ -295,6 +325,10 @@ int __devinit snd_usb_caiaq_control_init(struct snd_usb_caiaqdev *dev)
ret = add_controls(a8dj_controller,
ARRAY_SIZE(a8dj_controller), dev);
break;
+ case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO4DJ):
+ ret = add_controls(a4dj_controller,
+ ARRAY_SIZE(a4dj_controller), dev);
+ break;
}
return ret;
diff --git a/sound/usb/caiaq/caiaq-device.c b/sound/usb/caiaq/caiaq-device.c
index 41c36b055f6..cf573a982fd 100644
--- a/sound/usb/caiaq/caiaq-device.c
+++ b/sound/usb/caiaq/caiaq-device.c
@@ -42,15 +42,17 @@
#endif
MODULE_AUTHOR("Daniel Mack <daniel@caiaq.de>");
-MODULE_DESCRIPTION("caiaq USB audio, version 1.3.10");
+MODULE_DESCRIPTION("caiaq USB audio, version 1.3.13");
MODULE_LICENSE("GPL");
MODULE_SUPPORTED_DEVICE("{{Native Instruments, RigKontrol2},"
"{Native Instruments, RigKontrol3},"
"{Native Instruments, Kore Controller},"
"{Native Instruments, Kore Controller 2},"
"{Native Instruments, Audio Kontrol 1},"
+ "{Native Instruments, Audio 4 DJ},"
"{Native Instruments, Audio 8 DJ},"
- "{Native Instruments, Session I/O}}");
+ "{Native Instruments, Session I/O},"
+ "{Native Instruments, GuitarRig mobile}");
static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX; /* Index 0-max */
static char* id[SNDRV_CARDS] = SNDRV_DEFAULT_STR; /* Id for this card */
@@ -116,6 +118,16 @@ static struct usb_device_id snd_usb_id_table[] = {
.idVendor = USB_VID_NATIVEINSTRUMENTS,
.idProduct = USB_PID_SESSIONIO
},
+ {
+ .match_flags = USB_DEVICE_ID_MATCH_DEVICE,
+ .idVendor = USB_VID_NATIVEINSTRUMENTS,
+ .idProduct = USB_PID_GUITARRIGMOBILE
+ },
+ {
+ .match_flags = USB_DEVICE_ID_MATCH_DEVICE,
+ .idVendor = USB_VID_NATIVEINSTRUMENTS,
+ .idProduct = USB_PID_AUDIO4DJ
+ },
{ /* terminator */ }
};
@@ -239,6 +251,8 @@ int snd_usb_caiaq_set_audio_params (struct snd_usb_caiaqdev *dev,
if (dev->audio_parm_answer != 1)
debug("unable to set the device's audio params\n");
+ else
+ dev->bpp = bpp;
return dev->audio_parm_answer == 1 ? 0 : -EINVAL;
}
@@ -300,6 +314,12 @@ static void __devinit setup_card(struct snd_usb_caiaqdev *dev)
}
break;
+ case USB_ID(USB_VID_NATIVEINSTRUMENTS, USB_PID_AUDIO4DJ):
+ /* Audio 4 DJ - default input mode to phono */
+ dev->control_state[0] = 2;
+ snd_usb_caiaq_send_command(dev, EP1_CMD_WRITE_IO,
+ dev->control_state, 1);
+ break;
}
if (dev->spec.num_analog_audio_out +
@@ -336,9 +356,10 @@ static void __devinit setup_card(struct snd_usb_caiaqdev *dev)
log("Unable to set up control system (ret=%d)\n", ret);
}
-static struct snd_card* create_card(struct usb_device* usb_dev)
+static int create_card(struct usb_device* usb_dev, struct snd_card **cardp)
{
int devnum;
+ int err;
struct snd_card *card;
struct snd_usb_caiaqdev *dev;
@@ -347,12 +368,12 @@ static struct snd_card* create_card(struct usb_device* usb_dev)
break;
if (devnum >= SNDRV_CARDS)
- return NULL;
+ return -ENODEV;
- card = snd_card_new(index[devnum], id[devnum], THIS_MODULE,
- sizeof(struct snd_usb_caiaqdev));
- if (!card)
- return NULL;
+ err = snd_card_create(index[devnum], id[devnum], THIS_MODULE,
+ sizeof(struct snd_usb_caiaqdev), &card);
+ if (err < 0)
+ return err;
dev = caiaqdev(card);
dev->chip.dev = usb_dev;
@@ -362,7 +383,8 @@ static struct snd_card* create_card(struct usb_device* usb_dev)
spin_lock_init(&dev->spinlock);
snd_card_set_dev(card, &usb_dev->dev);
- return card;
+ *cardp = card;
+ return 0;
}
static int __devinit init_card(struct snd_usb_caiaqdev *dev)
@@ -441,10 +463,10 @@ static int __devinit snd_probe(struct usb_interface *intf,
struct snd_card *card;
struct usb_device *device = interface_to_usbdev(intf);
- card = create_card(device);
+ ret = create_card(device, &card);
- if (!card)
- return -ENOMEM;
+ if (ret < 0)
+ return ret;
usb_set_intfdata(intf, card);
ret = init_card(caiaqdev(card));
diff --git a/sound/usb/caiaq/caiaq-device.h b/sound/usb/caiaq/caiaq-device.h
index ab56e738c5f..4cce1ad7493 100644
--- a/sound/usb/caiaq/caiaq-device.h
+++ b/sound/usb/caiaq/caiaq-device.h
@@ -10,8 +10,10 @@
#define USB_PID_KORECONTROLLER 0x4711
#define USB_PID_KORECONTROLLER2 0x4712
#define USB_PID_AK1 0x0815
+#define USB_PID_AUDIO4DJ 0x0839
#define USB_PID_AUDIO8DJ 0x1978
#define USB_PID_SESSIONIO 0x1915
+#define USB_PID_GUITARRIGMOBILE 0x0d8d
#define EP1_BUFSIZE 64
#define CAIAQ_USB_STR_LEN 0xff
@@ -87,9 +89,9 @@ struct snd_usb_caiaqdev {
int audio_out_buf_pos[MAX_STREAMS];
int period_in_count[MAX_STREAMS];
int period_out_count[MAX_STREAMS];
- int input_panic, output_panic;
+ int input_panic, output_panic, warned;
char *audio_in_buf, *audio_out_buf;
- unsigned int samplerates;
+ unsigned int samplerates, bpp;
struct snd_pcm_substream *sub_playback[MAX_STREAMS];
struct snd_pcm_substream *sub_capture[MAX_STREAMS];