1/* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package android.support.v4.app; 18 19import static android.os.Build.VERSION.SDK_INT; 20 21import android.app.AppOpsManager; 22import android.content.Context; 23import android.support.annotation.NonNull; 24 25/** 26 * Helper for accessing features in android.app.AppOpsManager 27 * introduced after API level 4 in a backwards compatible fashion. 28 */ 29public final class AppOpsManagerCompat { 30 31 /** 32 * Result from {@link #noteOp}: the given caller is allowed to 33 * perform the given operation. 34 */ 35 public static final int MODE_ALLOWED = 0; 36 37 /** 38 * Result from {@link #noteOp}: the given caller is not allowed to perform 39 * the given operation, and this attempt should <em>silently fail</em> (it 40 * should not cause the app to crash). 41 */ 42 public static final int MODE_IGNORED = 1; 43 44 /** 45 * Result from {@link #noteOp}: the given caller should use its default 46 * security check. This mode is not normally used; it should only be used 47 * with appop permissions, and callers must explicitly check for it and 48 * deal with it. 49 */ 50 public static final int MODE_DEFAULT = 3; 51 52 private AppOpsManagerCompat() {} 53 54 /** 55 * Gets the app op name associated with a given permission. 56 * 57 * @param permission The permission. 58 * @return The app op associated with the permission or null. 59 */ 60 public static String permissionToOp(@NonNull String permission) { 61 if (SDK_INT >= 23) { 62 return AppOpsManager.permissionToOp(permission); 63 } else { 64 return null; 65 } 66 } 67 68 /** 69 * Make note of an application performing an operation. Note that you must pass 70 * in both the uid and name of the application to be checked; this function will verify 71 * that these two match, and if not, return {@link #MODE_IGNORED}. If this call 72 * succeeds, the last execution time of the operation for this app will be updated to 73 * the current time. 74 * @param context Your context. 75 * @param op The operation to note. One of the OPSTR_* constants. 76 * @param uid The user id of the application attempting to perform the operation. 77 * @param packageName The name of the application attempting to perform the operation. 78 * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or 79 * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without 80 * causing the app to crash). 81 * @throws SecurityException If the app has been configured to crash on this op. 82 */ 83 public static int noteOp(@NonNull Context context, @NonNull String op, int uid, 84 @NonNull String packageName) { 85 if (SDK_INT >= 23) { 86 AppOpsManager appOpsManager = context.getSystemService(AppOpsManager.class); 87 return appOpsManager.noteOp(op, uid, packageName); 88 } else { 89 return MODE_IGNORED; 90 } 91 } 92 93 /** 94 * Make note of an application performing an operation on behalf of another 95 * application when handling an IPC. Note that you must pass the package name 96 * of the application that is being proxied while its UID will be inferred from 97 * the IPC state; this function will verify that the calling uid and proxied 98 * package name match, and if not, return {@link #MODE_IGNORED}. If this call 99 * succeeds, the last execution time of the operation for the proxied app and 100 * your app will be updated to the current time. 101 * @param context Your context. 102 * @param op The operation to note. One of the OPSTR_* constants. 103 * @param proxiedPackageName The name of the application calling into the proxy application. 104 * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or 105 * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without 106 * causing the app to crash). 107 * @throws SecurityException If the app has been configured to crash on this op. 108 */ 109 public static int noteProxyOp(@NonNull Context context, @NonNull String op, 110 @NonNull String proxiedPackageName) { 111 if (SDK_INT >= 23) { 112 AppOpsManager appOpsManager = context.getSystemService(AppOpsManager.class); 113 return appOpsManager.noteProxyOp(op, proxiedPackageName); 114 } else { 115 return MODE_IGNORED; 116 } 117 } 118} 119