aaudio: prevent onAudioDeviceUpdate past close
To prevent late device update callbacks, the AudioStream
was made into a RefBase AudioDeviceCallback.
So now we can use a smart pointer to delay deletion of the
stream if any callbacks are in flight while the stream is closed.
So an AudioStream is now a RefBased object and can be used with
android::sp. That required some changes to the way it is referenced
in several places.
MyPlayerBase was modified to use a weak pointer to the parent stream.
Use delete[] for mDistributionBuffer
Bug: 161914201
Bug: 163165126
Bug: 164411271
Test: see bug for repro of the crash
Test: atest CtsNativeMediaAAudioTestCases
Change-Id: Ic24aca3eaf5d1610504bb89c06001a37d0d4a1c3
Merged-In: Ic24aca3eaf5d1610504bb89c06001a37d0d4a1c3
diff --git a/media/libaaudio/src/legacy/AudioStreamTrack.cpp b/media/libaaudio/src/legacy/AudioStreamTrack.cpp
index ab38839..3831046 100644
--- a/media/libaaudio/src/legacy/AudioStreamTrack.cpp
+++ b/media/libaaudio/src/legacy/AudioStreamTrack.cpp
@@ -224,7 +224,7 @@
     mInitialBufferCapacity = getBufferCapacity();
     mInitialFramesPerBurst = getFramesPerBurst();
 
-    mAudioTrack->addAudioDeviceCallback(mDeviceCallback);
+    mAudioTrack->addAudioDeviceCallback(this);
 
     // Update performance mode based on the actual stream flags.
     // For example, if the sample rate is not allowed then you won't get a FAST track.
@@ -253,7 +253,8 @@
 
 aaudio_result_t AudioStreamTrack::release_l() {
     if (getState() != AAUDIO_STREAM_STATE_CLOSING) {
-        mAudioTrack->removeAudioDeviceCallback(mDeviceCallback);
+        status_t err = mAudioTrack->removeAudioDeviceCallback(this);
+        ALOGE_IF(err, "%s() removeAudioDeviceCallback returned %d", __func__, err);
         logReleaseBufferState();
         // Data callbacks may still be running!
         return AudioStream::release_l();
@@ -265,7 +266,10 @@
 void AudioStreamTrack::close_l() {
     // Stop callbacks before deleting mFixedBlockReader memory.
     mAudioTrack.clear();
-    mFixedBlockReader.close();
+    // Do not close mFixedBlockReader because a data callback
+    // thread might still be running if someone else has a reference
+    // to mAudioRecord.
+    // It has a unique_ptr to its buffer so it will clean up by itself.
     AudioStream::close_l();
 }