Add attributionTag to audio-recordings
... by replacing packageName/uid/pid by the Identity class.
This allows us to track which parts of the app trigger audio-recordings.
90% of the code is just sending around the additional parameters.
This adds it for the Java and native API.
Test: atest CtsAppOpsTestCases
CtsNativeMediaAAudioTestCases
Fixes: 160150145
Change-Id: Ibd7b884f7fcd4668a4e27f997e59cfc3217a9e89
diff --git a/services/oboeservice/AAudioEndpointManager.cpp b/services/oboeservice/AAudioEndpointManager.cpp
index 407f6d5..3224cfc 100644
--- a/services/oboeservice/AAudioEndpointManager.cpp
+++ b/services/oboeservice/AAudioEndpointManager.cpp
@@ -24,6 +24,7 @@
#include <mutex>
#include <sstream>
#include <utility/AAudioUtilities.h>
+#include <media/AidlConversion.h>
#include "AAudioClientTracker.h"
#include "AAudioEndpointManager.h"
@@ -182,7 +183,9 @@
// 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);
+ pid_t pid = VALUE_OR_FATAL(
+ aidl2legacy_int32_t_pid_t(request.getIdentity().pid));
+ AAudioClientTracker::getInstance().setExclusiveEnabled(pid, false);
endpointToSteal = endpoint; // return it to caller
}
return nullptr;
diff --git a/services/oboeservice/AAudioService.cpp b/services/oboeservice/AAudioService.cpp
index 69e58f6..8baf8dc 100644
--- a/services/oboeservice/AAudioService.cpp
+++ b/services/oboeservice/AAudioService.cpp
@@ -22,7 +22,9 @@
#include <iostream>
#include <sstream>
+#include <android/media/permission/Identity.h>
#include <aaudio/AAudio.h>
+#include <media/AidlConversion.h>
#include <mediautils/ServiceUtilities.h>
#include <utils/String16.h>
@@ -39,16 +41,24 @@
#define MAX_STREAMS_PER_PROCESS 8
#define AIDL_RETURN(x) *_aidl_return = (x); return Status::ok();
+#define VALUE_OR_RETURN_ILLEGAL_ARG_STATUS(x) \
+ ({ auto _tmp = (x); \
+ if (!_tmp.ok()) AIDL_RETURN(AAUDIO_ERROR_ILLEGAL_ARGUMENT); \
+ std::move(_tmp.value()); })
using android::AAudioService;
+using android::media::permission::Identity;
using binder::Status;
android::AAudioService::AAudioService()
: BnAAudioService(),
mAdapter(this) {
- mAudioClient.clientUid = getuid(); // TODO consider using geteuid()
- mAudioClient.clientPid = getpid();
- mAudioClient.packageName = String16("");
+ // TODO consider using geteuid()
+ // TODO b/182392769: use identity util
+ mAudioClient.identity.uid = VALUE_OR_FATAL(legacy2aidl_uid_t_int32_t(getuid()));
+ mAudioClient.identity.pid = VALUE_OR_FATAL(legacy2aidl_pid_t_int32_t(getpid()));
+ mAudioClient.identity.packageName = std::nullopt;
+ mAudioClient.identity.attributionTag = std::nullopt;
AAudioClientTracker::getInstance().setAAudioService(this);
}
@@ -105,8 +115,14 @@
aaudio_sharing_mode_t sharingMode = configurationInput.getSharingMode();
// Enforce limit on client processes.
- pid_t pid = request.getProcessId();
- if (pid != mAudioClient.clientPid) {
+ Identity callingIdentity = request.getIdentity();
+ callingIdentity.pid = VALUE_OR_RETURN_ILLEGAL_ARG_STATUS(
+ legacy2aidl_pid_t_int32_t(IPCThreadState::self()->getCallingPid()));
+ callingIdentity.uid = VALUE_OR_RETURN_ILLEGAL_ARG_STATUS(
+ legacy2aidl_uid_t_int32_t(IPCThreadState::self()->getCallingUid()));
+ pid_t pid = VALUE_OR_RETURN_ILLEGAL_ARG_STATUS(
+ aidl2legacy_int32_t_pid_t(callingIdentity.pid));
+ if (callingIdentity.pid != mAudioClient.identity.pid) {
int32_t count = AAudioClientTracker::getInstance().getStreamCount(pid);
if (count >= MAX_STREAMS_PER_PROCESS) {
ALOGE("openStream(): exceeded max streams per process %d >= %d",
@@ -121,7 +137,7 @@
}
if (sharingMode == AAUDIO_SHARING_MODE_EXCLUSIVE
- && AAudioClientTracker::getInstance().isExclusiveEnabled(request.getProcessId())) {
+ && AAudioClientTracker::getInstance().isExclusiveEnabled(pid)) {
// only trust audioserver for in service indication
bool inService = false;
if (isCallerInService()) {
@@ -154,7 +170,6 @@
} else {
aaudio_handle_t handle = mStreamTracker.addStreamForHandle(serviceStream.get());
serviceStream->setHandle(handle);
- pid_t pid = request.getProcessId();
AAudioClientTracker::getInstance().registerClientStream(pid, serviceStream);
paramsOut.copyFrom(*serviceStream);
*_paramsOut = std::move(paramsOut).parcelable();
@@ -266,8 +281,10 @@
}
bool AAudioService::isCallerInService() {
- return mAudioClient.clientPid == IPCThreadState::self()->getCallingPid() &&
- mAudioClient.clientUid == IPCThreadState::self()->getCallingUid();
+ pid_t clientPid = VALUE_OR_FATAL(aidl2legacy_int32_t_pid_t(mAudioClient.identity.pid));
+ uid_t clientUid = VALUE_OR_FATAL(aidl2legacy_int32_t_uid_t(mAudioClient.identity.uid));
+ return clientPid == IPCThreadState::self()->getCallingPid() &&
+ clientUid == IPCThreadState::self()->getCallingUid();
}
aaudio_result_t AAudioService::closeStream(sp<AAudioServiceStreamBase> serviceStream) {
@@ -290,9 +307,11 @@
// Only allow owner or the aaudio service to access the stream.
const uid_t callingUserId = IPCThreadState::self()->getCallingUid();
const uid_t ownerUserId = serviceStream->getOwnerUserId();
+ const uid_t clientUid = VALUE_OR_FATAL(
+ aidl2legacy_int32_t_uid_t(mAudioClient.identity.uid));
bool callerOwnsIt = callingUserId == ownerUserId;
- bool serverCalling = callingUserId == mAudioClient.clientUid;
- bool serverOwnsIt = ownerUserId == mAudioClient.clientUid;
+ bool serverCalling = callingUserId == clientUid;
+ bool serverOwnsIt = ownerUserId == clientUid;
bool allowed = callerOwnsIt || serverCalling || serverOwnsIt;
if (!allowed) {
ALOGE("AAudioService: calling uid %d cannot access stream 0x%08X owned by %d",
diff --git a/services/oboeservice/AAudioServiceEndpointMMAP.cpp b/services/oboeservice/AAudioServiceEndpointMMAP.cpp
index 85b2057..556710d 100644
--- a/services/oboeservice/AAudioServiceEndpointMMAP.cpp
+++ b/services/oboeservice/AAudioServiceEndpointMMAP.cpp
@@ -73,9 +73,12 @@
aaudio_result_t AAudioServiceEndpointMMAP::open(const aaudio::AAudioStreamRequest &request) {
aaudio_result_t result = AAUDIO_OK;
copyFrom(request.getConstantConfiguration());
- mMmapClient.clientUid = request.getUserId();
- mMmapClient.clientPid = request.getProcessId();
- mMmapClient.packageName.setTo(String16(""));
+ mMmapClient.identity = request.getIdentity();
+ // TODO b/182392769: use identity util
+ mMmapClient.identity.uid = VALUE_OR_FATAL(
+ legacy2aidl_uid_t_int32_t(IPCThreadState::self()->getCallingUid()));
+ mMmapClient.identity.pid = VALUE_OR_FATAL(
+ legacy2aidl_pid_t_int32_t(IPCThreadState::self()->getCallingPid()));
audio_format_t audioFormat = getFormat();
@@ -159,8 +162,8 @@
this, // callback
mMmapStream,
&mPortHandle);
- ALOGD("%s() mMapClient.uid = %d, pid = %d => portHandle = %d\n",
- __func__, mMmapClient.clientUid, mMmapClient.clientPid, mPortHandle);
+ ALOGD("%s() mMapClient.identity = %s => portHandle = %d\n",
+ __func__, mMmapClient.identity.toString().c_str(), mPortHandle);
if (status != OK) {
// This can happen if the resource is busy or the config does
// not match the hardware.
@@ -208,8 +211,9 @@
setBufferCapacity(mMmapBufferinfo.buffer_size_frames);
if (!isBufferShareable) {
// Exclusive mode can only be used by the service because the FD cannot be shared.
- uid_t audioServiceUid = getuid();
- if ((mMmapClient.clientUid != audioServiceUid) &&
+ int32_t audioServiceUid =
+ VALUE_OR_FATAL(legacy2aidl_uid_t_int32_t(getuid()));
+ if ((mMmapClient.identity.uid != audioServiceUid) &&
getSharingMode() == AAUDIO_SHARING_MODE_EXCLUSIVE) {
ALOGW("%s() - exclusive FD cannot be used by client", __func__);
result = AAUDIO_ERROR_UNAVAILABLE;
diff --git a/services/oboeservice/AAudioServiceStreamBase.cpp b/services/oboeservice/AAudioServiceStreamBase.cpp
index 7edc25c..694094c 100644
--- a/services/oboeservice/AAudioServiceStreamBase.cpp
+++ b/services/oboeservice/AAudioServiceStreamBase.cpp
@@ -39,6 +39,8 @@
using namespace android; // TODO just import names needed
using namespace aaudio; // TODO just import names needed
+using media::permission::Identity;
+
/**
* Base class for streams in the service.
* @return
@@ -48,9 +50,7 @@
: mTimestampThread("AATime")
, mAtomicStreamTimestamp()
, mAudioService(audioService) {
- mMmapClient.clientUid = -1;
- mMmapClient.clientPid = -1;
- mMmapClient.packageName = String16("");
+ mMmapClient.identity = Identity();
}
AAudioServiceStreamBase::~AAudioServiceStreamBase() {
@@ -82,7 +82,7 @@
result << " 0x" << std::setfill('0') << std::setw(8) << std::hex << mHandle
<< std::dec << std::setfill(' ') ;
- result << std::setw(6) << mMmapClient.clientUid;
+ result << std::setw(6) << mMmapClient.identity.uid;
result << std::setw(7) << mClientHandle;
result << std::setw(4) << (isRunning() ? "yes" : " no");
result << std::setw(6) << getState();
@@ -128,9 +128,12 @@
AAudioEndpointManager &mEndpointManager = AAudioEndpointManager::getInstance();
aaudio_result_t result = AAUDIO_OK;
- mMmapClient.clientUid = request.getUserId();
- mMmapClient.clientPid = request.getProcessId();
- mMmapClient.packageName.setTo(String16("")); // TODO What should we do here?
+ mMmapClient.identity = request.getIdentity();
+ // TODO b/182392769: use identity util
+ mMmapClient.identity.uid = VALUE_OR_FATAL(
+ legacy2aidl_uid_t_int32_t(IPCThreadState::self()->getCallingUid()));
+ mMmapClient.identity.pid = VALUE_OR_FATAL(
+ legacy2aidl_pid_t_int32_t(IPCThreadState::self()->getCallingPid()));
// Limit scope of lock to avoid recursive lock in close().
{
diff --git a/services/oboeservice/AAudioServiceStreamBase.h b/services/oboeservice/AAudioServiceStreamBase.h
index 0f752b7..06c9f21 100644
--- a/services/oboeservice/AAudioServiceStreamBase.h
+++ b/services/oboeservice/AAudioServiceStreamBase.h
@@ -21,6 +21,7 @@
#include <mutex>
#include <android-base/thread_annotations.h>
+#include <media/AidlConversion.h>
#include <media/AudioClient.h>
#include <utils/RefBase.h>
@@ -159,11 +160,11 @@
}
uid_t getOwnerUserId() const {
- return mMmapClient.clientUid;
+ return VALUE_OR_FATAL(android::aidl2legacy_int32_t_uid_t(mMmapClient.identity.uid));
}
pid_t getOwnerProcessId() const {
- return mMmapClient.clientPid;
+ return VALUE_OR_FATAL(android::aidl2legacy_int32_t_pid_t(mMmapClient.identity.pid));
}
aaudio_handle_t getHandle() const {
diff --git a/services/oboeservice/Android.bp b/services/oboeservice/Android.bp
index 21f3247..a419dd5 100644
--- a/services/oboeservice/Android.bp
+++ b/services/oboeservice/Android.bp
@@ -66,10 +66,13 @@
"liblog",
"libutils",
"aaudio-aidl-cpp",
+ "media_permission-aidl-cpp",
+ "libaudioclient_aidl_conversion",
],
export_shared_lib_headers: [
"libaaudio_internal",
+ "media_permission-aidl-cpp",
],
header_libs: [
diff --git a/services/oboeservice/fuzzer/Android.bp b/services/oboeservice/fuzzer/Android.bp
index 78ef3fc..f4e8a81 100644
--- a/services/oboeservice/fuzzer/Android.bp
+++ b/services/oboeservice/fuzzer/Android.bp
@@ -46,6 +46,8 @@
"liblog",
"libutils",
"aaudio-aidl-cpp",
+ "media_permission-aidl-cpp",
+ "libaudioclient_aidl_conversion",
],
static_libs: [
"libaaudioservice",
diff --git a/services/oboeservice/fuzzer/oboeservice_fuzzer.cpp b/services/oboeservice/fuzzer/oboeservice_fuzzer.cpp
index 163eae8..8e508d3 100644
--- a/services/oboeservice/fuzzer/oboeservice_fuzzer.cpp
+++ b/services/oboeservice/fuzzer/oboeservice_fuzzer.cpp
@@ -23,6 +23,7 @@
#include <AAudioService.h>
#include <aaudio/AAudio.h>
#include "aaudio/BnAAudioClient.h"
+#include <android/media/permission/Identity.h>
#define UNUSED_PARAM __attribute__((unused))
@@ -294,8 +295,11 @@
? fdp.ConsumeIntegral<int32_t>()
: kAAudioFormats[fdp.ConsumeIntegralInRange<int32_t>(0, kNumAAudioFormats - 1)]));
- request.setUserId(getuid());
- request.setProcessId(getpid());
+ // TODO b/182392769: use identity util
+ media::permission::Identity identity;
+ identity.uid = getuid();
+ identity.pid = getpid();
+ request.setIdentity(identity);
request.setInService(fdp.ConsumeBool());
request.getConfiguration().setDeviceId(fdp.ConsumeIntegral<int32_t>());