Allow voice recognition service to blame other apps access.
This is a workaround solution for Android R QPR2. We are not allowed to change the API for QPR release. This is a special case that allows the current voice recognizer to note proxy ops if it is also the voice interactor. In S, we will define a new permission that designed one as a trusted blamer and tie it to a role. Bug: 17095434 Test: manual Test: TreeHugger presubmit Change-Id: I506bbeb95e622b99693dbf5a135c7961b7fd81c1
This commit is contained in:
@@ -31,6 +31,7 @@ import android.compat.Compatibility;
|
||||
import android.compat.annotation.ChangeId;
|
||||
import android.compat.annotation.EnabledAfter;
|
||||
import android.compat.annotation.UnsupportedAppUsage;
|
||||
import android.content.ComponentName;
|
||||
import android.content.ContentResolver;
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageManager;
|
||||
@@ -52,6 +53,7 @@ import android.os.RemoteException;
|
||||
import android.os.ServiceManager;
|
||||
import android.os.SystemClock;
|
||||
import android.os.UserManager;
|
||||
import android.provider.Settings;
|
||||
import android.util.ArrayMap;
|
||||
import android.util.ArraySet;
|
||||
import android.util.LongSparseArray;
|
||||
@@ -7590,8 +7592,9 @@ public class AppOpsManager {
|
||||
collectNotedOpForSelf(op, proxiedAttributionTag);
|
||||
} else if (collectionMode == COLLECT_SYNC
|
||||
// Only collect app-ops when the proxy is trusted
|
||||
&& mContext.checkPermission(Manifest.permission.UPDATE_APP_OPS_STATS, -1,
|
||||
myUid) == PackageManager.PERMISSION_GRANTED) {
|
||||
&& (mContext.checkPermission(Manifest.permission.UPDATE_APP_OPS_STATS, -1,
|
||||
myUid) == PackageManager.PERMISSION_GRANTED
|
||||
|| isTrustedVoiceServiceProxy(mContext.getOpPackageName(), op))) {
|
||||
collectNotedOpSync(op, proxiedAttributionTag);
|
||||
}
|
||||
}
|
||||
@@ -7602,6 +7605,28 @@ public class AppOpsManager {
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isTrustedVoiceServiceProxy(String packageName, int code) {
|
||||
// This is a workaround for R QPR, new API change is not allowed. We only allow the current
|
||||
// voice recognizer is also the voice interactor to noteproxy op.
|
||||
if (code != OP_RECORD_AUDIO) {
|
||||
return false;
|
||||
}
|
||||
final String voiceRecognitionComponent = Settings.Secure.getString(
|
||||
mContext.getContentResolver(), Settings.Secure.VOICE_RECOGNITION_SERVICE);
|
||||
final String voiceInteractionComponent = Settings.Secure.getString(
|
||||
mContext.getContentResolver(), Settings.Secure.VOICE_INTERACTION_SERVICE);
|
||||
|
||||
final String voiceRecognitionServicePackageName =
|
||||
voiceRecognitionComponent != null ? ComponentName.unflattenFromString(
|
||||
voiceRecognitionComponent).getPackageName() : "";
|
||||
final String voiceInteractionServicePackageName =
|
||||
voiceInteractionComponent != null ? ComponentName.unflattenFromString(
|
||||
voiceInteractionComponent).getPackageName() : "";
|
||||
|
||||
return Objects.equals(packageName, voiceRecognitionServicePackageName) && Objects.equals(
|
||||
voiceRecognitionServicePackageName, voiceInteractionServicePackageName);
|
||||
}
|
||||
|
||||
/**
|
||||
* Do a quick check for whether an application might be able to perform an operation.
|
||||
* This is <em>not</em> a security check; you must use {@link #noteOp(String, int, String,
|
||||
|
||||
@@ -94,6 +94,7 @@ import android.app.AsyncNotedAppOp;
|
||||
import android.app.RuntimeAppOpAccessMessage;
|
||||
import android.app.SyncNotedAppOp;
|
||||
import android.content.BroadcastReceiver;
|
||||
import android.content.ComponentName;
|
||||
import android.content.ContentResolver;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
@@ -3015,6 +3016,25 @@ public class AppOpsService extends IAppOpsService.Stub {
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isTrustedVoiceServiceProxy(String packageName, int code) {
|
||||
if (code != OP_RECORD_AUDIO) {
|
||||
return false;
|
||||
}
|
||||
final String voiceRecognitionComponent = Settings.Secure.getString(
|
||||
mContext.getContentResolver(), Settings.Secure.VOICE_RECOGNITION_SERVICE);
|
||||
final String voiceInteractionComponent = Settings.Secure.getString(
|
||||
mContext.getContentResolver(), Settings.Secure.VOICE_INTERACTION_SERVICE);
|
||||
|
||||
final String voiceRecognitionServicePackageName =
|
||||
voiceRecognitionComponent != null ? ComponentName.unflattenFromString(
|
||||
voiceRecognitionComponent).getPackageName() : "";
|
||||
final String voiceInteractionServicePackageName =
|
||||
voiceInteractionComponent != null ? ComponentName.unflattenFromString(
|
||||
voiceInteractionComponent).getPackageName() : "";
|
||||
return Objects.equals(packageName, voiceRecognitionServicePackageName) && Objects.equals(
|
||||
voiceRecognitionServicePackageName, voiceInteractionServicePackageName);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int noteProxyOperation(int code, int proxiedUid, String proxiedPackageName,
|
||||
String proxiedAttributionTag, int proxyUid, String proxyPackageName,
|
||||
@@ -3030,9 +3050,12 @@ public class AppOpsService extends IAppOpsService.Stub {
|
||||
return AppOpsManager.MODE_IGNORED;
|
||||
}
|
||||
|
||||
// This is a workaround for R QPR, new API change is not allowed. We only allow the current
|
||||
// voice recognizer is also the voice interactor to noteproxy op.
|
||||
final boolean isTrustVoiceServiceProxy = isTrustedVoiceServiceProxy(proxyPackageName, code);
|
||||
final boolean isProxyTrusted = mContext.checkPermission(
|
||||
Manifest.permission.UPDATE_APP_OPS_STATS, -1, proxyUid)
|
||||
== PackageManager.PERMISSION_GRANTED;
|
||||
== PackageManager.PERMISSION_GRANTED || isTrustVoiceServiceProxy;
|
||||
|
||||
final int proxyFlags = isProxyTrusted ? AppOpsManager.OP_FLAG_TRUSTED_PROXY
|
||||
: AppOpsManager.OP_FLAG_UNTRUSTED_PROXY;
|
||||
@@ -3494,9 +3517,12 @@ public class AppOpsService extends IAppOpsService.Stub {
|
||||
return AppOpsManager.MODE_IGNORED;
|
||||
}
|
||||
|
||||
// This is a workaround for R QPR, new API change is not allowed. We only allow the current
|
||||
// voice recognizer is also the voice interactor to noteproxy op.
|
||||
final boolean isTrustVoiceServiceProxy = isTrustedVoiceServiceProxy(proxyPackageName, code);
|
||||
final boolean isProxyTrusted = mContext.checkPermission(
|
||||
Manifest.permission.UPDATE_APP_OPS_STATS, -1, proxyUid)
|
||||
== PackageManager.PERMISSION_GRANTED;
|
||||
== PackageManager.PERMISSION_GRANTED || isTrustVoiceServiceProxy;
|
||||
|
||||
final int proxyFlags = isProxyTrusted ? AppOpsManager.OP_FLAG_TRUSTED_PROXY
|
||||
: AppOpsManager.OP_FLAG_UNTRUSTED_PROXY;
|
||||
|
||||
Reference in New Issue
Block a user