diff options
author | Clemens Ladisch <clemens@ladisch.de> | 2009-05-27 04:49:30 -0400 |
---|---|---|
committer | Takashi Iwai <tiwai@suse.de> | 2009-05-27 05:25:33 -0400 |
commit | 55de5ef970c680d8d75f2a9aa7e4f172140dbd9c (patch) | |
tree | 3fed0a032ccc3050ceacbe4f230d1c02cd122f1c /sound | |
parent | 59a3759d0fe8d969888c741bb33f4946e4d3750d (diff) |
sound: usb-audio: make the MotU Fastlane work again
Kernel 2.6.18 broke the MotU Fastlane, which uses duplicate endpoint
numbers in a manner that is not only illegal but also confuses the
kernel's endpoint descriptor caching mechanism. To work around this, we
have to add a separate usb_set_interface() call to guide the USB core to
the correct descriptors.
Signed-off-by: Clemens Ladisch <clemens@ladisch.de>
Reported-and-tested-by: David Fries <david@fries.net>
Cc: <stable@kernel.org>
Signed-off-by: Takashi Iwai <tiwai@suse.de>
Diffstat (limited to 'sound')
-rw-r--r-- | sound/usb/usbaudio.c | 2 | ||||
-rw-r--r-- | sound/usb/usbaudio.h | 2 | ||||
-rw-r--r-- | sound/usb/usbmidi.c | 12 | ||||
-rw-r--r-- | sound/usb/usbquirks.h | 2 |
4 files changed, 14 insertions, 4 deletions
diff --git a/sound/usb/usbaudio.c b/sound/usb/usbaudio.c index 823296d7d578..a6b88482637b 100644 --- a/sound/usb/usbaudio.c +++ b/sound/usb/usbaudio.c | |||
@@ -3347,7 +3347,7 @@ static int snd_usb_create_quirk(struct snd_usb_audio *chip, | |||
3347 | [QUIRK_MIDI_YAMAHA] = snd_usb_create_midi_interface, | 3347 | [QUIRK_MIDI_YAMAHA] = snd_usb_create_midi_interface, |
3348 | [QUIRK_MIDI_MIDIMAN] = snd_usb_create_midi_interface, | 3348 | [QUIRK_MIDI_MIDIMAN] = snd_usb_create_midi_interface, |
3349 | [QUIRK_MIDI_NOVATION] = snd_usb_create_midi_interface, | 3349 | [QUIRK_MIDI_NOVATION] = snd_usb_create_midi_interface, |
3350 | [QUIRK_MIDI_RAW] = snd_usb_create_midi_interface, | 3350 | [QUIRK_MIDI_FASTLANE] = snd_usb_create_midi_interface, |
3351 | [QUIRK_MIDI_EMAGIC] = snd_usb_create_midi_interface, | 3351 | [QUIRK_MIDI_EMAGIC] = snd_usb_create_midi_interface, |
3352 | [QUIRK_MIDI_CME] = snd_usb_create_midi_interface, | 3352 | [QUIRK_MIDI_CME] = snd_usb_create_midi_interface, |
3353 | [QUIRK_AUDIO_STANDARD_INTERFACE] = create_standard_audio_quirk, | 3353 | [QUIRK_AUDIO_STANDARD_INTERFACE] = create_standard_audio_quirk, |
diff --git a/sound/usb/usbaudio.h b/sound/usb/usbaudio.h index 36e4f7a29adc..8e7f78941ba6 100644 --- a/sound/usb/usbaudio.h +++ b/sound/usb/usbaudio.h | |||
@@ -153,7 +153,7 @@ enum quirk_type { | |||
153 | QUIRK_MIDI_YAMAHA, | 153 | QUIRK_MIDI_YAMAHA, |
154 | QUIRK_MIDI_MIDIMAN, | 154 | QUIRK_MIDI_MIDIMAN, |
155 | QUIRK_MIDI_NOVATION, | 155 | QUIRK_MIDI_NOVATION, |
156 | QUIRK_MIDI_RAW, | 156 | QUIRK_MIDI_FASTLANE, |
157 | QUIRK_MIDI_EMAGIC, | 157 | QUIRK_MIDI_EMAGIC, |
158 | QUIRK_MIDI_CME, | 158 | QUIRK_MIDI_CME, |
159 | QUIRK_MIDI_US122L, | 159 | QUIRK_MIDI_US122L, |
diff --git a/sound/usb/usbmidi.c b/sound/usb/usbmidi.c index 26bad373fe65..2fb35cc22a30 100644 --- a/sound/usb/usbmidi.c +++ b/sound/usb/usbmidi.c | |||
@@ -1778,8 +1778,18 @@ int snd_usb_create_midi_interface(struct snd_usb_audio* chip, | |||
1778 | umidi->usb_protocol_ops = &snd_usbmidi_novation_ops; | 1778 | umidi->usb_protocol_ops = &snd_usbmidi_novation_ops; |
1779 | err = snd_usbmidi_detect_per_port_endpoints(umidi, endpoints); | 1779 | err = snd_usbmidi_detect_per_port_endpoints(umidi, endpoints); |
1780 | break; | 1780 | break; |
1781 | case QUIRK_MIDI_RAW: | 1781 | case QUIRK_MIDI_FASTLANE: |
1782 | umidi->usb_protocol_ops = &snd_usbmidi_raw_ops; | 1782 | umidi->usb_protocol_ops = &snd_usbmidi_raw_ops; |
1783 | /* | ||
1784 | * Interface 1 contains isochronous endpoints, but with the same | ||
1785 | * numbers as in interface 0. Since it is interface 1 that the | ||
1786 | * USB core has most recently seen, these descriptors are now | ||
1787 | * associated with the endpoint numbers. This will foul up our | ||
1788 | * attempts to submit bulk/interrupt URBs to the endpoints in | ||
1789 | * interface 0, so we have to make sure that the USB core looks | ||
1790 | * again at interface 0 by calling usb_set_interface() on it. | ||
1791 | */ | ||
1792 | usb_set_interface(umidi->chip->dev, 0, 0); | ||
1783 | err = snd_usbmidi_detect_per_port_endpoints(umidi, endpoints); | 1793 | err = snd_usbmidi_detect_per_port_endpoints(umidi, endpoints); |
1784 | break; | 1794 | break; |
1785 | case QUIRK_MIDI_EMAGIC: | 1795 | case QUIRK_MIDI_EMAGIC: |
diff --git a/sound/usb/usbquirks.h b/sound/usb/usbquirks.h index 647ef5029651..5d955aaad85f 100644 --- a/sound/usb/usbquirks.h +++ b/sound/usb/usbquirks.h | |||
@@ -1868,7 +1868,7 @@ YAMAHA_DEVICE(0x7010, "UB99"), | |||
1868 | .data = & (const struct snd_usb_audio_quirk[]) { | 1868 | .data = & (const struct snd_usb_audio_quirk[]) { |
1869 | { | 1869 | { |
1870 | .ifnum = 0, | 1870 | .ifnum = 0, |
1871 | .type = QUIRK_MIDI_RAW | 1871 | .type = QUIRK_MIDI_FASTLANE |
1872 | }, | 1872 | }, |
1873 | { | 1873 | { |
1874 | .ifnum = 1, | 1874 | .ifnum = 1, |