From 9ca42c45aedcd9d36a21c52f5895d07baf5dac98 Mon Sep 17 00:00:00 2001
From: Mike Lockwood <lockwood@google.com>
Date: Thu, 13 Mar 2014 11:42:47 -0700
Subject: [PATCH] usb: gadget: audio: Fix problem resuming playback on alt
 interface change

If the alternate interface is set back to 1, we now resume playback
if still triggered.

Bug: 12549807
(cherry picked from commit 898bafb4722ac04cda46249e39b0be96ab9d2bbd)

Change-Id: I6c3eb43ebafbc8a101ae83e7864097be5b07a0f9
---
 drivers/usb/gadget/f_audio_source.c | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/drivers/usb/gadget/f_audio_source.c b/drivers/usb/gadget/f_audio_source.c
index 003f5fa6b804..353219141d99 100644
--- a/drivers/usb/gadget/f_audio_source.c
+++ b/drivers/usb/gadget/f_audio_source.c
@@ -260,6 +260,7 @@ struct audio_dev {
 	s64				frames_sent;
 
 	bool				audio_ep_enabled;
+	bool				triggered;
 };
 
 static inline struct audio_dev *func_to_audio_source(struct usb_function *f)
@@ -267,6 +268,8 @@ static inline struct audio_dev *func_to_audio_source(struct usb_function *f)
 	return container_of(f, struct audio_dev, func);
 }
 
+static void audio_pcm_playback_start(struct audio_dev *audio);
+
 /*-------------------------------------------------------------------------*/
 
 static struct usb_request *audio_request_new(struct usb_ep *ep, int buffer_size)
@@ -545,6 +548,10 @@ static int audio_set_alt(struct usb_function *f, unsigned intf, unsigned alt)
 				return ret;
 			}
 			audio->audio_ep_enabled = true;
+			if (audio->triggered) {
+				// resume playing if we are still triggered
+				audio_pcm_playback_start(audio);
+			}
 		} else if (!alt && audio->audio_ep_enabled) {
 			usb_ep_disable(audio->in_ep);
 			audio->audio_ep_enabled = false;
@@ -767,11 +774,13 @@ static int audio_pcm_playback_trigger(struct snd_pcm_substream *substream,
 	switch (cmd) {
 	case SNDRV_PCM_TRIGGER_START:
 	case SNDRV_PCM_TRIGGER_RESUME:
+		audio->triggered = 1;
 		audio_pcm_playback_start(audio);
 		break;
 
 	case SNDRV_PCM_TRIGGER_STOP:
 	case SNDRV_PCM_TRIGGER_SUSPEND:
+		audio->triggered = 0;
 		audio_pcm_playback_stop(audio);
 		break;
 
-- 
GitLab