audio policy: session routes continued.

- Clear session routes when client process dies.
- Enforce the route only when the requesting session is active.
- Fix requested route not working if an output mix change is required
(e.g forcing to SPEAKER when the default route is USB or A2DP).
- Make sure all sessions sharing the strategy with a rerouted session
have the same route (needed for volume control consistency)

Change-Id: I0ab347a8fb97e73e2c5965374544c5f4fe509ef1
diff --git a/services/audiopolicy/AudioPolicyInterface.h b/services/audiopolicy/AudioPolicyInterface.h
index 9230750..8523fc5 100644
--- a/services/audiopolicy/AudioPolicyInterface.h
+++ b/services/audiopolicy/AudioPolicyInterface.h
@@ -106,6 +106,7 @@
                                         audio_io_handle_t *output,
                                         audio_session_t session,
                                         audio_stream_type_t *stream,
+                                        uid_t uid,
                                         uint32_t samplingRate,
                                         audio_format_t format,
                                         audio_channel_mask_t channelMask,
@@ -129,6 +130,7 @@
     virtual status_t getInputForAttr(const audio_attributes_t *attr,
                                      audio_io_handle_t *input,
                                      audio_session_t session,
+                                     uid_t uid,
                                      uint32_t samplingRate,
                                      audio_format_t format,
                                      audio_channel_mask_t channelMask,
@@ -209,7 +211,7 @@
                                       struct audio_patch *patches,
                                       unsigned int *generation) = 0;
     virtual status_t setAudioPortConfig(const struct audio_port_config *config) = 0;
-    virtual void clearAudioPatches(uid_t uid) = 0;
+    virtual void releaseResourcesForUid(uid_t uid) = 0;
 
     virtual status_t acquireSoundTriggerSession(audio_session_t *session,
                                            audio_io_handle_t *ioHandle,
diff --git a/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp b/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
index 77fc0b9..6f1998c 100644
--- a/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
+++ b/services/audiopolicy/common/managerdefinitions/src/AudioPolicyMix.cpp
@@ -176,14 +176,14 @@
 
     ssize_t index = indexOfKey(address);
     if (index < 0) {
-        ALOGW("getInputForAttr() no policy for address %s", address.string());
+        ALOGW("getInputMixForAttr() no policy for address %s", address.string());
         return BAD_VALUE;
     }
     sp<AudioPolicyMix> audioPolicyMix = valueAt(index);
     AudioMix *mix = audioPolicyMix->getMix();
 
     if (mix->mMixType != MIX_TYPE_PLAYERS) {
-        ALOGW("getInputForAttr() bad policy mix type for address %s", address.string());
+        ALOGW("getInputMixForAttr() bad policy mix type for address %s", address.string());
         return BAD_VALUE;
     }
     *policyMix = mix;
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
index 7de72de..127e22f 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.cpp
@@ -620,6 +620,7 @@
                                               audio_io_handle_t *output,
                                               audio_session_t session,
                                               audio_stream_type_t *stream,
+                                              uid_t uid,
                                               uint32_t samplingRate,
                                               audio_format_t format,
                                               audio_channel_mask_t channelMask,
@@ -659,8 +660,22 @@
         return BAD_VALUE;
     }
 
-    ALOGV("getOutputForAttr() usage=%d, content=%d, tag=%s flags=%08x",
-          attributes.usage, attributes.content_type, attributes.tags, attributes.flags);
+    ALOGV("getOutputForAttr() usage=%d, content=%d, tag=%s flags=%08x"
+            " session %d selectedDeviceId %d",
+            attributes.usage, attributes.content_type, attributes.tags, attributes.flags,
+            session, selectedDeviceId);
+
+    *stream = streamTypefromAttributesInt(&attributes);
+
+    // Explicit routing?
+    sp<DeviceDescriptor> deviceDesc;
+    for (size_t i = 0; i < mAvailableOutputDevices.size(); i++) {
+        if (mAvailableOutputDevices[i]->getId() == selectedDeviceId) {
+            deviceDesc = mAvailableOutputDevices[i];
+            break;
+        }
+    }
+    mOutputRoutes.addRoute(session, *stream, SessionRoute::SOURCE_TYPE_NA, deviceDesc, uid);
 
     routing_strategy strategy = (routing_strategy) getStrategyForAttr(&attributes);
     audio_devices_t device = getDeviceForStrategy(strategy, false /*fromCache*/);
@@ -672,24 +687,14 @@
     ALOGV("getOutputForAttr() device 0x%x, samplingRate %d, format %x, channelMask %x, flags %x",
           device, samplingRate, format, channelMask, flags);
 
-    *stream = streamTypefromAttributesInt(&attributes);
     *output = getOutputForDevice(device, session, *stream,
                                  samplingRate, format, channelMask,
                                  flags, offloadInfo);
     if (*output == AUDIO_IO_HANDLE_NONE) {
+        mOutputRoutes.removeRoute(session);
         return INVALID_OPERATION;
     }
 
-    // Explicit routing?
-    sp<DeviceDescriptor> deviceDesc;
-
-    for (size_t i = 0; i < mAvailableOutputDevices.size(); i++) {
-        if (mAvailableOutputDevices[i]->getId() == selectedDeviceId) {
-            deviceDesc = mAvailableOutputDevices[i];
-            break;
-        }
-    }
-    mOutputRoutes.addRoute(session, *stream, SessionRoute::SOURCE_TYPE_NA, deviceDesc);
     return NO_ERROR;
 }
 
@@ -966,24 +971,26 @@
 
     sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueAt(index);
 
+    // Routing?
+    mOutputRoutes.incRouteActivity(session);
+
     audio_devices_t newDevice;
     if (outputDesc->mPolicyMix != NULL) {
         newDevice = AUDIO_DEVICE_OUT_REMOTE_SUBMIX;
     } else if (mOutputRoutes.hasRouteChanged(session)) {
         newDevice = getNewOutputDevice(outputDesc, false /*fromCache*/);
+        checkStrategyRoute(getStrategy(stream), output);
     } else {
         newDevice = AUDIO_DEVICE_NONE;
     }
 
     uint32_t delayMs = 0;
 
-    // Routing?
-    mOutputRoutes.incRouteActivity(session);
-
     status_t status = startSource(outputDesc, stream, newDevice, &delayMs);
 
     if (status != NO_ERROR) {
         mOutputRoutes.decRouteActivity(session);
+        return status;
     }
     // Automatically enable the remote submix input when output is started on a re routing mix
     // of type MIX_TYPE_RECORDERS
@@ -1112,15 +1119,22 @@
     }
 
     // Routing?
+    bool forceDeviceUpdate = false;
     if (outputDesc->mRefCount[stream] > 0) {
-        mOutputRoutes.decRouteActivity(session);
+        int activityCount = mOutputRoutes.decRouteActivity(session);
+        forceDeviceUpdate = (mOutputRoutes.hasRoute(session) && (activityCount == 0));
+
+        if (forceDeviceUpdate) {
+            checkStrategyRoute(getStrategy(stream), AUDIO_IO_HANDLE_NONE);
+        }
     }
 
-    return stopSource(outputDesc, stream);
+    return stopSource(outputDesc, stream, forceDeviceUpdate);
 }
 
 status_t AudioPolicyManager::stopSource(sp<AudioOutputDescriptor> outputDesc,
-                                            audio_stream_type_t stream)
+                                            audio_stream_type_t stream,
+                                            bool forceDeviceUpdate)
 {
     // always handle stream stop, check which stream type is stopping
     handleEventForBeacon(stream == AUDIO_STREAM_TTS ? STOPPING_BEACON : STOPPING_OUTPUT);
@@ -1135,7 +1149,7 @@
         outputDesc->changeRefCount(stream, -1);
 
         // store time at which the stream was stopped - see isStreamActive()
-        if (outputDesc->mRefCount[stream] == 0) {
+        if (outputDesc->mRefCount[stream] == 0 || forceDeviceUpdate) {
             outputDesc->mStopTime[stream] = systemTime();
             audio_devices_t newDevice = getNewOutputDevice(outputDesc, false /*fromCache*/);
             // delay the device switch by twice the latency because stopOutput() is executed when
@@ -1222,6 +1236,7 @@
 status_t AudioPolicyManager::getInputForAttr(const audio_attributes_t *attr,
                                              audio_io_handle_t *input,
                                              audio_session_t session,
+                                             uid_t uid,
                                              uint32_t samplingRate,
                                              audio_format_t format,
                                              audio_channel_mask_t channelMask,
@@ -1256,7 +1271,7 @@
             break;
         }
     }
-    mInputRoutes.addRoute(session, SessionRoute::STREAM_TYPE_NA, inputSource, deviceDesc);
+    mInputRoutes.addRoute(session, SessionRoute::STREAM_TYPE_NA, inputSource, deviceDesc, uid);
 
     if (inputSource == AUDIO_SOURCE_REMOTE_SUBMIX &&
             strncmp(attr->tags, "addr=", strlen("addr=")) == 0) {
@@ -1431,6 +1446,9 @@
         }
     }
 
+    // Routing?
+    mInputRoutes.incRouteActivity(session);
+
     if (inputDesc->mRefCount == 0 || mInputRoutes.hasRouteChanged(session)) {
         // if input maps to a dynamic policy with an activity listener, notify of state change
         if ((inputDesc->mPolicyMix != NULL)
@@ -1439,9 +1457,6 @@
                     MIX_STATE_MIXING);
         }
 
-        // Routing?
-        mInputRoutes.incRouteActivity(session);
-
         if (mInputs.activeInputsCount() == 0) {
             SoundTrigger::setCaptureState(true);
         }
@@ -2479,6 +2494,12 @@
     return status;
 }
 
+void AudioPolicyManager::releaseResourcesForUid(uid_t uid)
+{
+    clearAudioPatches(uid);
+    clearSessionRoutes(uid);
+}
+
 void AudioPolicyManager::clearAudioPatches(uid_t uid)
 {
     for (ssize_t i = (ssize_t)mAudioPatches.size() - 1; i >= 0; i--)  {
@@ -2489,6 +2510,82 @@
     }
 }
 
+
+void AudioPolicyManager::checkStrategyRoute(routing_strategy strategy,
+                                            audio_io_handle_t ouptutToSkip)
+{
+    audio_devices_t device = getDeviceForStrategy(strategy, false /*fromCache*/);
+    SortedVector<audio_io_handle_t> outputs = getOutputsForDevice(device, mOutputs);
+    for (size_t j = 0; j < mOutputs.size(); j++) {
+        if (mOutputs.keyAt(j) == ouptutToSkip) {
+            continue;
+        }
+        sp<SwAudioOutputDescriptor> outputDesc = mOutputs.valueAt(j);
+        if (!isStrategyActive(outputDesc, (routing_strategy)strategy)) {
+            continue;
+        }
+        // If the default device for this strategy is on another output mix,
+        // invalidate all tracks in this strategy to force re connection.
+        // Otherwise select new device on the output mix.
+        if (outputs.indexOf(mOutputs.keyAt(j)) < 0) {
+            for (int stream = 0; stream < AUDIO_STREAM_CNT; stream++) {
+                if (stream == AUDIO_STREAM_PATCH) {
+                    continue;
+                }
+                if (getStrategy((audio_stream_type_t)stream) == strategy) {
+                    mpClientInterface->invalidateStream((audio_stream_type_t)stream);
+                }
+            }
+        } else {
+            audio_devices_t newDevice = getNewOutputDevice(outputDesc, false /*fromCache*/);
+            setOutputDevice(outputDesc, newDevice, false);
+        }
+    }
+}
+
+void AudioPolicyManager::clearSessionRoutes(uid_t uid)
+{
+    // remove output routes associated with this uid
+    SortedVector<routing_strategy> affectedStrategies;
+    for (ssize_t i = (ssize_t)mOutputRoutes.size() - 1; i >= 0; i--)  {
+        sp<SessionRoute> route = mOutputRoutes.valueAt(i);
+        if (route->mUid == uid) {
+            mOutputRoutes.removeItemsAt(i);
+            if (route->mDeviceDescriptor != 0) {
+                affectedStrategies.add(getStrategy(route->mStreamType));
+            }
+        }
+    }
+    // reroute outputs if necessary
+    for (size_t i = 0; i < affectedStrategies.size(); i++) {
+        checkStrategyRoute(affectedStrategies[i], AUDIO_IO_HANDLE_NONE);
+    }
+
+    // remove input routes associated with this uid
+    SortedVector<audio_source_t> affectedSources;
+    for (ssize_t i = (ssize_t)mInputRoutes.size() - 1; i >= 0; i--)  {
+        sp<SessionRoute> route = mInputRoutes.valueAt(i);
+        if (route->mUid == uid) {
+            mInputRoutes.removeItemsAt(i);
+            if (route->mDeviceDescriptor != 0) {
+                affectedSources.add(route->mSource);
+            }
+        }
+    }
+    // reroute inputs if necessary
+    SortedVector<audio_io_handle_t> inputsToClose;
+    for (size_t i = 0; i < mInputs.size(); i++) {
+        sp<AudioInputDescriptor> inputDesc = mInputs.valueAt(i);
+        if (affectedSources.indexOf(inputDesc->mInputSource) >= 0) {
+            inputsToClose.add(inputDesc->mIoHandle);
+        }
+    }
+    for (size_t i = 0; i < inputsToClose.size(); i++) {
+        closeInput(inputsToClose[i]);
+    }
+}
+
+
 status_t AudioPolicyManager::acquireSoundTriggerSession(audio_session_t *session,
                                        audio_io_handle_t *ioHandle,
                                        audio_devices_t *device)
@@ -3563,7 +3660,8 @@
     ALOGVV("getOutputsForDevice() device %04x", device);
     for (size_t i = 0; i < openOutputs.size(); i++) {
         ALOGVV("output %d isDuplicated=%d device=%04x",
-                i, openOutputs.valueAt(i)->isDuplicated(), openOutputs.valueAt(i)->supportedDevices());
+                i, openOutputs.valueAt(i)->isDuplicated(),
+                openOutputs.valueAt(i)->supportedDevices());
         if ((device & openOutputs.valueAt(i)->supportedDevices()) == device) {
             ALOGVV("getOutputsForDevice() found output %d", openOutputs.keyAt(i));
             outputs.add(openOutputs.keyAt(i));
@@ -3925,7 +4023,7 @@
     for (size_t routeIndex = 0; routeIndex < mOutputRoutes.size(); routeIndex++) {
         sp<SessionRoute> route = mOutputRoutes.valueAt(routeIndex);
         routing_strategy strat = getStrategy(route->mStreamType);
-        if (strat == strategy && route->mDeviceDescriptor != 0 /*&& route->mActivityCount != 0*/) {
+        if (strat == strategy && route->isActive()) {
             return route->mDeviceDescriptor->type();
         }
     }
@@ -4315,8 +4413,7 @@
 {
     for (size_t routeIndex = 0; routeIndex < mInputRoutes.size(); routeIndex++) {
          sp<SessionRoute> route = mInputRoutes.valueAt(routeIndex);
-         if (inputSource == route->mSource && route->mDeviceDescriptor != 0
-                 /*&& route->mActivityCount != 0*/) {
+         if (inputSource == route->mSource && route->isActive()) {
              return route->mDeviceDescriptor->type();
          }
      }
@@ -4605,7 +4702,8 @@
 void AudioPolicyManager::SessionRouteMap::addRoute(audio_session_t session,
                                                    audio_stream_type_t streamType,
                                                    audio_source_t source,
-                                                   sp<DeviceDescriptor> descriptor)
+                                                   sp<DeviceDescriptor> descriptor,
+                                                   uid_t uid)
 {
     if (mMapType == MAPTYPE_INPUT && streamType != SessionRoute::STREAM_TYPE_NA) {
         ALOGE("Adding Output Route to InputRouteMap");
@@ -4618,14 +4716,15 @@
     sp<SessionRoute> route = indexOfKey(session) >= 0 ? valueFor(session) : 0;
 
     if (route != 0) {
-        if ((route->mDeviceDescriptor == 0 && descriptor != 0) ||
-                (!route->mDeviceDescriptor->equals(descriptor))) {
+        if (((route->mDeviceDescriptor == 0) && (descriptor != 0)) ||
+                ((route->mDeviceDescriptor != 0) &&
+                 ((descriptor == 0) || (!route->mDeviceDescriptor->equals(descriptor))))) {
             route->mChanged = true;
         }
         route->mRefCount++;
         route->mDeviceDescriptor = descriptor;
     } else {
-        route = new AudioPolicyManager::SessionRoute(session, streamType, source, descriptor);
+        route = new AudioPolicyManager::SessionRoute(session, streamType, source, descriptor, uid);
         route->mRefCount++;
         add(session, route);
         if (descriptor != 0) {
diff --git a/services/audiopolicy/managerdefault/AudioPolicyManager.h b/services/audiopolicy/managerdefault/AudioPolicyManager.h
index b965411..ea16864 100644
--- a/services/audiopolicy/managerdefault/AudioPolicyManager.h
+++ b/services/audiopolicy/managerdefault/AudioPolicyManager.h
@@ -109,6 +109,7 @@
                                           audio_io_handle_t *output,
                                           audio_session_t session,
                                           audio_stream_type_t *stream,
+                                          uid_t uid,
                                           uint32_t samplingRate,
                                           audio_format_t format,
                                           audio_channel_mask_t channelMask,
@@ -127,6 +128,7 @@
         virtual status_t getInputForAttr(const audio_attributes_t *attr,
                                          audio_io_handle_t *input,
                                          audio_session_t session,
+                                         uid_t uid,
                                          uint32_t samplingRate,
                                          audio_format_t format,
                                          audio_channel_mask_t channelMask,
@@ -207,7 +209,6 @@
                                           struct audio_patch *patches,
                                           unsigned int *generation);
         virtual status_t setAudioPortConfig(const struct audio_port_config *config);
-        virtual void clearAudioPatches(uid_t uid);
 
         virtual status_t acquireSoundTriggerSession(audio_session_t *session,
                                                audio_io_handle_t *ioHandle,
@@ -226,6 +227,8 @@
                                           audio_io_handle_t *handle);
         virtual status_t stopAudioSource(audio_io_handle_t handle);
 
+        virtual void     releaseResourcesForUid(uid_t uid);
+
         // Audio policy configuration file parsing (audio_policy.conf)
         // TODO candidates to be moved to ConfigParsingUtils
                 void defaultAudioPolicyConfig(void);
@@ -248,31 +251,36 @@
             SessionRoute(audio_session_t session,
                          audio_stream_type_t streamType,
                          audio_source_t source,
-                         sp<DeviceDescriptor> deviceDescriptor)
-               : mSession(session),
+                         sp<DeviceDescriptor> deviceDescriptor,
+                         uid_t uid)
+               : mUid(uid),
+                 mSession(session),
                  mDeviceDescriptor(deviceDescriptor),
                  mRefCount(0),
                  mActivityCount(0),
                  mChanged(false),
                  mStreamType(streamType),
-                 mSource(source) {}
-
-            audio_session_t         mSession;
-
-            sp<DeviceDescriptor>    mDeviceDescriptor;
+                 mSource(source)
+                  {}
 
             void log(const char* prefix);
 
+            bool isActive() {
+                return (mDeviceDescriptor != 0) && (mChanged || (mActivityCount > 0));
+            }
+
+            uid_t                       mUid;
+            audio_session_t             mSession;
+            sp<DeviceDescriptor>        mDeviceDescriptor;
+
             // "reference" counting
-            int                     mRefCount;      // +/- on references
-            int                     mActivityCount; // +/- on start/stop
-            bool                    mChanged;
-
+            int                         mRefCount;      // +/- on references
+            int                         mActivityCount; // +/- on start/stop
+            bool                        mChanged;
             // for outputs
-            const audio_stream_type_t     mStreamType;
-
+            const audio_stream_type_t   mStreamType;
             // for inputs
-            const audio_source_t          mSource;
+            const audio_source_t        mSource;
         };
 
         class SessionRouteMap: public KeyedVector<audio_session_t, sp<SessionRoute>> {
@@ -292,6 +300,7 @@
             }
 
             bool hasRoute(audio_session_t session);
+
             void removeRoute(audio_session_t session);
 
             int incRouteActivity(audio_session_t session);
@@ -306,7 +315,8 @@
             void addRoute(audio_session_t session,
                           audio_stream_type_t streamType,
                           audio_source_t source,
-                          sp<DeviceDescriptor> deviceDescriptor);
+                          sp<DeviceDescriptor> deviceDescriptor,
+                          uid_t uid);
 
         private:
             // Used to mark a SessionRoute as for either inputs (mMapType == kSessionRouteMap_Input)
@@ -559,7 +569,12 @@
                              audio_devices_t device,
                              uint32_t *delayMs);
         status_t stopSource(sp<AudioOutputDescriptor> outputDesc,
-                            audio_stream_type_t stream);
+                            audio_stream_type_t stream,
+                            bool forceDeviceUpdate);
+
+        void clearAudioPatches(uid_t uid);
+        void clearSessionRoutes(uid_t uid);
+        void checkStrategyRoute(routing_strategy strategy, audio_io_handle_t ouptutToSkip);
 
         uid_t mUidCached;
         AudioPolicyClientInterface *mpClientInterface;  // audio policy client interface
diff --git a/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp b/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp
index 5ceb1cf..65639c3 100644
--- a/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp
+++ b/services/audiopolicy/service/AudioPolicyInterfaceImpl.cpp
@@ -146,6 +146,7 @@
                                               audio_io_handle_t *output,
                                               audio_session_t session,
                                               audio_stream_type_t *stream,
+                                              uid_t uid,
                                               uint32_t samplingRate,
                                               audio_format_t format,
                                               audio_channel_mask_t channelMask,
@@ -158,7 +159,16 @@
     }
     ALOGV("getOutput()");
     Mutex::Autolock _l(mLock);
-    return mAudioPolicyManager->getOutputForAttr(attr, output, session, stream, samplingRate,
+
+    // if the caller is us, trust the specified uid
+    if (IPCThreadState::self()->getCallingPid() != getpid_cached || uid == (uid_t)-1) {
+        uid_t newclientUid = IPCThreadState::self()->getCallingUid();
+        if (uid != (uid_t)-1 && uid != newclientUid) {
+            ALOGW("%s uid %d tried to pass itself off as %d", __FUNCTION__, newclientUid, uid);
+        }
+        uid = newclientUid;
+    }
+    return mAudioPolicyManager->getOutputForAttr(attr, output, session, stream, uid, samplingRate,
                                     format, channelMask, flags, selectedDeviceId, offloadInfo);
 }
 
@@ -248,6 +258,7 @@
 status_t AudioPolicyService::getInputForAttr(const audio_attributes_t *attr,
                                              audio_io_handle_t *input,
                                              audio_session_t session,
+                                             uid_t uid,
                                              uint32_t samplingRate,
                                              audio_format_t format,
                                              audio_channel_mask_t channelMask,
@@ -269,12 +280,22 @@
     sp<AudioPolicyEffects>audioPolicyEffects;
     status_t status;
     AudioPolicyInterface::input_type_t inputType;
+    // if the caller is us, trust the specified uid
+    if (IPCThreadState::self()->getCallingPid() != getpid_cached || uid == (uid_t)-1) {
+        uid_t newclientUid = IPCThreadState::self()->getCallingUid();
+        if (uid != (uid_t)-1 && uid != newclientUid) {
+            ALOGW("%s uid %d tried to pass itself off as %d", __FUNCTION__, newclientUid, uid);
+        }
+        uid = newclientUid;
+    }
+
     {
         Mutex::Autolock _l(mLock);
         // the audio_in_acoustics_t parameter is ignored by get_input()
-        status = mAudioPolicyManager->getInputForAttr(attr, input, session,
+        status = mAudioPolicyManager->getInputForAttr(attr, input, session, uid,
                                                      samplingRate, format, channelMask,
-                                                     flags, selectedDeviceId, &inputType);
+                                                     flags, selectedDeviceId,
+                                                     &inputType);
         audioPolicyEffects = mAudioPolicyEffects;
 
         if (status == NO_ERROR) {
diff --git a/services/audiopolicy/service/AudioPolicyInterfaceImplLegacy.cpp b/services/audiopolicy/service/AudioPolicyInterfaceImplLegacy.cpp
index 433e712..13af3ef 100644
--- a/services/audiopolicy/service/AudioPolicyInterfaceImplLegacy.cpp
+++ b/services/audiopolicy/service/AudioPolicyInterfaceImplLegacy.cpp
@@ -234,6 +234,7 @@
 status_t AudioPolicyService::getInputForAttr(const audio_attributes_t *attr,
                                              audio_io_handle_t *input,
                                              audio_session_t session,
+                                             uid_t uid __unused,
                                              uint32_t samplingRate,
                                              audio_format_t format,
                                              audio_channel_mask_t channelMask,
@@ -565,6 +566,7 @@
                                               audio_io_handle_t *output,
                                               audio_session_t session __unused,
                                               audio_stream_type_t *stream,
+                                              uid_t uid __unused,
                                               uint32_t samplingRate,
                                               audio_format_t format,
                                               audio_channel_mask_t channelMask,
diff --git a/services/audiopolicy/service/AudioPolicyService.cpp b/services/audiopolicy/service/AudioPolicyService.cpp
index ccf9f9b..c5f4fb7 100644
--- a/services/audiopolicy/service/AudioPolicyService.cpp
+++ b/services/audiopolicy/service/AudioPolicyService.cpp
@@ -177,7 +177,7 @@
     {
         Mutex::Autolock _l(mLock);
         if (mAudioPolicyManager) {
-            mAudioPolicyManager->clearAudioPatches(uid);
+            mAudioPolicyManager->releaseResourcesForUid(uid);
         }
     }
 #endif
diff --git a/services/audiopolicy/service/AudioPolicyService.h b/services/audiopolicy/service/AudioPolicyService.h
index 07ea96b..eb50cdd 100644
--- a/services/audiopolicy/service/AudioPolicyService.h
+++ b/services/audiopolicy/service/AudioPolicyService.h
@@ -80,6 +80,7 @@
                                       audio_io_handle_t *output,
                                       audio_session_t session,
                                       audio_stream_type_t *stream,
+                                      uid_t uid,
                                       uint32_t samplingRate = 0,
                                       audio_format_t format = AUDIO_FORMAT_DEFAULT,
                                       audio_channel_mask_t channelMask = 0,
@@ -98,6 +99,7 @@
     virtual status_t getInputForAttr(const audio_attributes_t *attr,
                                      audio_io_handle_t *input,
                                      audio_session_t session,
+                                     uid_t uid,
                                      uint32_t samplingRate,
                                      audio_format_t format,
                                      audio_channel_mask_t channelMask,