[PATCH] ALSA: snd-usb: fix calls to usb_set_interface
Daniel Mack
zonque at gmail.com
Tue Jul 10 22:52:56 CEST 2012
Don't call usb_set_interface() on snd_usb_endpoint creation and also
drop it from snd_usb_endpoint_deactivate(). Rather unselect the the
active interface before choosing a new alt setting upon the next stream
start.
Signed-off-by: Daniel Mack <zonque at gmail.com>
---
sound/usb/endpoint.c | 45 ++++++++++++++-------------------------------
1 file changed, 14 insertions(+), 31 deletions(-)
diff --git a/sound/usb/endpoint.c b/sound/usb/endpoint.c
index e690690..2226769 100644
--- a/sound/usb/endpoint.c
+++ b/sound/usb/endpoint.c
@@ -414,7 +414,7 @@ struct snd_usb_endpoint *snd_usb_add_endpoint(struct snd_usb_audio *chip,
{
struct list_head *p;
struct snd_usb_endpoint *ep;
- int ret, is_playback = direction == SNDRV_PCM_STREAM_PLAYBACK;
+ int is_playback = direction == SNDRV_PCM_STREAM_PLAYBACK;
mutex_lock(&chip->mutex);
@@ -434,16 +434,6 @@ struct snd_usb_endpoint *snd_usb_add_endpoint(struct snd_usb_audio *chip,
type == SND_USB_ENDPOINT_TYPE_DATA ? "data" : "sync",
ep_num);
- /* select the alt setting once so the endpoints become valid */
- ret = usb_set_interface(chip->dev, alts->desc.bInterfaceNumber,
- alts->desc.bAlternateSetting);
- if (ret < 0) {
- snd_printk(KERN_ERR "%s(): usb_set_interface() failed, ret = %d\n",
- __func__, ret);
- ep = NULL;
- goto __exit_unlock;
- }
-
ep = kzalloc(sizeof(*ep), GFP_KERNEL);
if (!ep)
goto __exit_unlock;
@@ -936,8 +926,8 @@ void snd_usb_endpoint_stop(struct snd_usb_endpoint *ep,
*
* In case of any active users, this functions does nothing.
*
- * Returns an error if usb_set_interface() failed, 0 in all other
- * cases.
+ * Returns an error if any of the usb_set_interface() calls failed, 0 in
+ * all other cases.
*/
int snd_usb_endpoint_activate(struct snd_usb_endpoint *ep)
{
@@ -948,6 +938,14 @@ int snd_usb_endpoint_activate(struct snd_usb_endpoint *ep)
!test_and_set_bit(EP_FLAG_ACTIVATED, &ep->flags)) {
int ret;
+ ret = usb_set_interface(ep->chip->dev, ep->iface, 0);
+ if (ret < 0) {
+ snd_printk(KERN_ERR "%s() usb_set_interface() failed, ret = %d\n",
+ __func__, ret);
+ clear_bit(EP_FLAG_ACTIVATED, &ep->flags);
+ return ret;
+ }
+
ret = usb_set_interface(ep->chip->dev, ep->iface, ep->alt_idx);
if (ret < 0) {
snd_printk(KERN_ERR "%s() usb_set_interface() failed, ret = %d\n",
@@ -967,13 +965,8 @@ int snd_usb_endpoint_activate(struct snd_usb_endpoint *ep)
*
* @ep: the endpoint to deactivate
*
- * If the endpoint is not currently in use, this functions will select the
- * alternate interface setting 0 for the interface of this endpoint.
- *
- * In case of any active users, this functions does nothing.
- *
- * Returns an error if usb_set_interface() failed, 0 in all other
- * cases.
+ * Returns 0 on success, -EINVAL if ep was NULL and -EBUSY if the endpoint
+ * is still in use.
*/
int snd_usb_endpoint_deactivate(struct snd_usb_endpoint *ep)
{
@@ -984,18 +977,8 @@ int snd_usb_endpoint_deactivate(struct snd_usb_endpoint *ep)
return 0;
if (!ep->chip->shutdown &&
- test_and_clear_bit(EP_FLAG_ACTIVATED, &ep->flags)) {
- int ret;
-
- ret = usb_set_interface(ep->chip->dev, ep->iface, 0);
- if (ret < 0) {
- snd_printk(KERN_ERR "%s(): usb_set_interface() failed, ret = %d\n",
- __func__, ret);
- return ret;
- }
-
+ test_and_clear_bit(EP_FLAG_ACTIVATED, &ep->flags))
return 0;
- }
return -EBUSY;
}
--
1.7.10.4
--------------080102090909090401070304--
More information about the Alsa-devel
mailing list