aaudio: disable exclusive mode after steal
Prevent a process that had its exclusive stream stolen
from obtaining another exclusive stream.
This can prevent a collision between two processes after
they both try to open EXCLUSIVE streams after
a DISCONNECT event.
Bug: 157777324
Test: adb shell test_steal_exclusive -r0 -d100
Change-Id: I0fe12be95a8fbd05ed03f10796e1ca716025c885
diff --git a/services/oboeservice/AAudioEndpointManager.cpp b/services/oboeservice/AAudioEndpointManager.cpp
index c9bf72f..9f34153 100644
--- a/services/oboeservice/AAudioEndpointManager.cpp
+++ b/services/oboeservice/AAudioEndpointManager.cpp
@@ -25,6 +25,7 @@
#include <sstream>
#include <utility/AAudioUtilities.h>
+#include "AAudioClientTracker.h"
#include "AAudioEndpointManager.h"
#include "AAudioServiceEndpointShared.h"
#include "AAudioServiceEndpointMMAP.h"
@@ -174,7 +175,15 @@
&& !request.isSharingModeMatchRequired()) { // app did not request a shared stream
ALOGD("%s() endpoint in EXCLUSIVE use. Steal it!", __func__);
mExclusiveStolenCount++;
- endpointToSteal = endpoint;
+ // Prevent this process from getting another EXCLUSIVE stream.
+ // This will prevent two clients from colliding after a DISCONNECTION
+ // when they both try to open an exclusive stream at the same time.
+ // That can result in a stream getting disconnected between the OPEN
+ // and START calls. This will help preserve app compatibility.
+ // An app can avoid having this happen by closing their streams when
+ // the app is paused.
+ AAudioClientTracker::getInstance().setExclusiveEnabled(request.getProcessId(), false);
+ endpointToSteal = endpoint; // return it to caller
}
return nullptr;
} else {