audioflinger: forward flush to direct output streams

Track flush should be forwarded to the audio HAL when playing
on a direct output stream.

Bug: 17704953.
Change-Id: Iafc94327fe9aebf1d4eaa97b76c6767b7ac5babe
diff --git a/services/audioflinger/Threads.cpp b/services/audioflinger/Threads.cpp
index 818bb05..faca7ab 100644
--- a/services/audioflinger/Threads.cpp
+++ b/services/audioflinger/Threads.cpp
@@ -4040,6 +4040,9 @@
                         track->mState = TrackBase::STOPPED;
                     }
                     if (track->isStopped()) {
+                        if (track->mState == TrackBase::FLUSHED) {
+                            flushHw_l();
+                        }
                         track->reset();
                     }
                     tracksToRemove->add(track);
@@ -4212,6 +4215,12 @@
     }
 }
 
+void AudioFlinger::DirectOutputThread::flushHw_l()
+{
+    if (mOutput->stream->flush != NULL)
+        mOutput->stream->flush(mOutput->stream);
+}
+
 // ----------------------------------------------------------------------------
 
 AudioFlinger::AsyncCallbackThread::AsyncCallbackThread(
@@ -4579,7 +4588,7 @@
 
 void AudioFlinger::OffloadThread::flushHw_l()
 {
-    mOutput->stream->flush(mOutput->stream);
+    DirectOutputThread::flushHw_l();
     // Flush anything still waiting in the mixbuffer
     mCurrentWriteLength = 0;
     mBytesRemaining = 0;
diff --git a/services/audioflinger/Threads.h b/services/audioflinger/Threads.h
index fd025b5..7af5264 100644
--- a/services/audioflinger/Threads.h
+++ b/services/audioflinger/Threads.h
@@ -894,6 +894,7 @@
 
     virtual     bool        checkForNewParameter_l(const String8& keyValuePair,
                                                    status_t& status);
+    virtual     void        flushHw_l();
 
 protected:
     virtual     int         getTrackName_l(audio_channel_mask_t channelMask,
@@ -929,6 +930,7 @@
     OffloadThread(const sp<AudioFlinger>& audioFlinger, AudioStreamOut* output,
                         audio_io_handle_t id, uint32_t device);
     virtual                 ~OffloadThread() {};
+    virtual     void        flushHw_l();
 
 protected:
     // threadLoop snippets
@@ -941,9 +943,6 @@
     virtual     void        onAddNewTrack_l();
 
 private:
-                void        flushHw_l();
-
-private:
     bool        mHwPaused;
     bool        mFlushPending;
     size_t      mPausedWriteLength;     // length in bytes of write interrupted by pause
diff --git a/services/audioflinger/Tracks.cpp b/services/audioflinger/Tracks.cpp
index c0a75b9..75190f3 100644
--- a/services/audioflinger/Tracks.cpp
+++ b/services/audioflinger/Tracks.cpp
@@ -824,6 +824,10 @@
             // remove from active track list, reset(), and trigger presentation complete
             if (playbackThread->mActiveTracks.indexOf(this) < 0) {
                 reset();
+                if (thread->type() == ThreadBase::DIRECT) {
+                    DirectOutputThread *t = (DirectOutputThread *)playbackThread;
+                    t->flushHw_l();
+                }
             }
         }
         // Prevent flush being lost if the track is flushed and then resumed