1 /*
2  * Copyright (C) 2012 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 
17 package android.app;
18 
19 import android.Manifest;
20 import android.annotation.SystemApi;
21 import android.app.usage.UsageStatsManager;
22 import android.content.Context;
23 import android.media.AudioAttributes.AttributeUsage;
24 import android.os.Binder;
25 import android.os.IBinder;
26 import android.os.Parcel;
27 import android.os.Parcelable;
28 import android.os.Process;
29 import android.os.RemoteException;
30 import android.os.UserHandle;
31 import android.os.UserManager;
32 import android.util.ArrayMap;
33 
34 import com.android.internal.app.IAppOpsCallback;
35 import com.android.internal.app.IAppOpsService;
36 
37 import java.util.ArrayList;
38 import java.util.HashMap;
39 import java.util.List;
40 
41 /**
42  * API for interacting with "application operation" tracking.
43  *
44  * <p>This API is not generally intended for third party application developers; most
45  * features are only available to system applications.  Obtain an instance of it through
46  * {@link Context#getSystemService(String) Context.getSystemService} with
47  * {@link Context#APP_OPS_SERVICE Context.APP_OPS_SERVICE}.</p>
48  */
49 public class AppOpsManager {
50     /**
51      * <p>App ops allows callers to:</p>
52      *
53      * <ul>
54      * <li> Note when operations are happening, and find out if they are allowed for the current
55      * caller.</li>
56      * <li> Disallow specific apps from doing specific operations.</li>
57      * <li> Collect all of the current information about operations that have been executed or
58      * are not being allowed.</li>
59      * <li> Monitor for changes in whether an operation is allowed.</li>
60      * </ul>
61      *
62      * <p>Each operation is identified by a single integer; these integers are a fixed set of
63      * operations, enumerated by the OP_* constants.
64      *
65      * <p></p>When checking operations, the result is a "mode" integer indicating the current
66      * setting for the operation under that caller: MODE_ALLOWED, MODE_IGNORED (don't execute
67      * the operation but fake its behavior enough so that the caller doesn't crash),
68      * MODE_ERRORED (throw a SecurityException back to the caller; the normal operation calls
69      * will do this for you).
70      */
71 
72     final Context mContext;
73     final IAppOpsService mService;
74     final ArrayMap<OnOpChangedListener, IAppOpsCallback> mModeWatchers
75             = new ArrayMap<OnOpChangedListener, IAppOpsCallback>();
76 
77     static IBinder sToken;
78 
79     /**
80      * Result from {@link #checkOp}, {@link #noteOp}, {@link #startOp}: the given caller is
81      * allowed to perform the given operation.
82      */
83     public static final int MODE_ALLOWED = 0;
84 
85     /**
86      * Result from {@link #checkOp}, {@link #noteOp}, {@link #startOp}: the given caller is
87      * not allowed to perform the given operation, and this attempt should
88      * <em>silently fail</em> (it should not cause the app to crash).
89      */
90     public static final int MODE_IGNORED = 1;
91 
92     /**
93      * Result from {@link #checkOpNoThrow}, {@link #noteOpNoThrow}, {@link #startOpNoThrow}: the
94      * given caller is not allowed to perform the given operation, and this attempt should
95      * cause it to have a fatal error, typically a {@link SecurityException}.
96      */
97     public static final int MODE_ERRORED = 2;
98 
99     /**
100      * Result from {@link #checkOp}, {@link #noteOp}, {@link #startOp}: the given caller should
101      * use its default security check.  This mode is not normally used; it should only be used
102      * with appop permissions, and callers must explicitly check for it and deal with it.
103      */
104     public static final int MODE_DEFAULT = 3;
105 
106     // when adding one of these:
107     //  - increment _NUM_OP
108     //  - add rows to sOpToSwitch, sOpToString, sOpNames, sOpPerms, sOpDefaultMode
109     //  - add descriptive strings to Settings/res/values/arrays.xml
110     //  - add the op to the appropriate template in AppOpsState.OpsTemplate (settings app)
111 
112     /** @hide No operation specified. */
113     public static final int OP_NONE = -1;
114     /** @hide Access to coarse location information. */
115     public static final int OP_COARSE_LOCATION = 0;
116     /** @hide Access to fine location information. */
117     public static final int OP_FINE_LOCATION = 1;
118     /** @hide Causing GPS to run. */
119     public static final int OP_GPS = 2;
120     /** @hide */
121     public static final int OP_VIBRATE = 3;
122     /** @hide */
123     public static final int OP_READ_CONTACTS = 4;
124     /** @hide */
125     public static final int OP_WRITE_CONTACTS = 5;
126     /** @hide */
127     public static final int OP_READ_CALL_LOG = 6;
128     /** @hide */
129     public static final int OP_WRITE_CALL_LOG = 7;
130     /** @hide */
131     public static final int OP_READ_CALENDAR = 8;
132     /** @hide */
133     public static final int OP_WRITE_CALENDAR = 9;
134     /** @hide */
135     public static final int OP_WIFI_SCAN = 10;
136     /** @hide */
137     public static final int OP_POST_NOTIFICATION = 11;
138     /** @hide */
139     public static final int OP_NEIGHBORING_CELLS = 12;
140     /** @hide */
141     public static final int OP_CALL_PHONE = 13;
142     /** @hide */
143     public static final int OP_READ_SMS = 14;
144     /** @hide */
145     public static final int OP_WRITE_SMS = 15;
146     /** @hide */
147     public static final int OP_RECEIVE_SMS = 16;
148     /** @hide */
149     public static final int OP_RECEIVE_EMERGECY_SMS = 17;
150     /** @hide */
151     public static final int OP_RECEIVE_MMS = 18;
152     /** @hide */
153     public static final int OP_RECEIVE_WAP_PUSH = 19;
154     /** @hide */
155     public static final int OP_SEND_SMS = 20;
156     /** @hide */
157     public static final int OP_READ_ICC_SMS = 21;
158     /** @hide */
159     public static final int OP_WRITE_ICC_SMS = 22;
160     /** @hide */
161     public static final int OP_WRITE_SETTINGS = 23;
162     /** @hide */
163     public static final int OP_SYSTEM_ALERT_WINDOW = 24;
164     /** @hide */
165     public static final int OP_ACCESS_NOTIFICATIONS = 25;
166     /** @hide */
167     public static final int OP_CAMERA = 26;
168     /** @hide */
169     public static final int OP_RECORD_AUDIO = 27;
170     /** @hide */
171     public static final int OP_PLAY_AUDIO = 28;
172     /** @hide */
173     public static final int OP_READ_CLIPBOARD = 29;
174     /** @hide */
175     public static final int OP_WRITE_CLIPBOARD = 30;
176     /** @hide */
177     public static final int OP_TAKE_MEDIA_BUTTONS = 31;
178     /** @hide */
179     public static final int OP_TAKE_AUDIO_FOCUS = 32;
180     /** @hide */
181     public static final int OP_AUDIO_MASTER_VOLUME = 33;
182     /** @hide */
183     public static final int OP_AUDIO_VOICE_VOLUME = 34;
184     /** @hide */
185     public static final int OP_AUDIO_RING_VOLUME = 35;
186     /** @hide */
187     public static final int OP_AUDIO_MEDIA_VOLUME = 36;
188     /** @hide */
189     public static final int OP_AUDIO_ALARM_VOLUME = 37;
190     /** @hide */
191     public static final int OP_AUDIO_NOTIFICATION_VOLUME = 38;
192     /** @hide */
193     public static final int OP_AUDIO_BLUETOOTH_VOLUME = 39;
194     /** @hide */
195     public static final int OP_WAKE_LOCK = 40;
196     /** @hide Continually monitoring location data. */
197     public static final int OP_MONITOR_LOCATION = 41;
198     /** @hide Continually monitoring location data with a relatively high power request. */
199     public static final int OP_MONITOR_HIGH_POWER_LOCATION = 42;
200     /** @hide Retrieve current usage stats via {@link UsageStatsManager}. */
201     public static final int OP_GET_USAGE_STATS = 43;
202     /** @hide */
203     public static final int OP_MUTE_MICROPHONE = 44;
204     /** @hide */
205     public static final int OP_TOAST_WINDOW = 45;
206     /** @hide Capture the device's display contents and/or audio */
207     public static final int OP_PROJECT_MEDIA = 46;
208     /** @hide Activate a VPN connection without user intervention. */
209     public static final int OP_ACTIVATE_VPN = 47;
210     /** @hide Access the WallpaperManagerAPI to write wallpapers. */
211     public static final int OP_WRITE_WALLPAPER = 48;
212     /** @hide Received the assist structure from an app. */
213     public static final int OP_ASSIST_STRUCTURE = 49;
214     /** @hide Received a screenshot from assist. */
215     public static final int OP_ASSIST_SCREENSHOT = 50;
216     /** @hide Read the phone state. */
217     public static final int OP_READ_PHONE_STATE = 51;
218     /** @hide Add voicemail messages to the voicemail content provider. */
219     public static final int OP_ADD_VOICEMAIL = 52;
220     /** @hide Access APIs for SIP calling over VOIP or WiFi. */
221     public static final int OP_USE_SIP = 53;
222     /** @hide Intercept outgoing calls. */
223     public static final int OP_PROCESS_OUTGOING_CALLS = 54;
224     /** @hide User the fingerprint API. */
225     public static final int OP_USE_FINGERPRINT = 55;
226     /** @hide Access to body sensors such as heart rate, etc. */
227     public static final int OP_BODY_SENSORS = 56;
228     /** @hide Read previously received cell broadcast messages. */
229     public static final int OP_READ_CELL_BROADCASTS = 57;
230     /** @hide Inject mock location into the system. */
231     public static final int OP_MOCK_LOCATION = 58;
232     /** @hide Read external storage. */
233     public static final int OP_READ_EXTERNAL_STORAGE = 59;
234     /** @hide Write external storage. */
235     public static final int OP_WRITE_EXTERNAL_STORAGE = 60;
236     /** @hide Turned on the screen. */
237     public static final int OP_TURN_SCREEN_ON = 61;
238     /** @hide Get device accounts. */
239     public static final int OP_GET_ACCOUNTS = 62;
240     /** @hide */
241     public static final int _NUM_OP = 63;
242 
243     /** Access to coarse location information. */
244     public static final String OPSTR_COARSE_LOCATION = "android:coarse_location";
245     /** Access to fine location information. */
246     public static final String OPSTR_FINE_LOCATION =
247             "android:fine_location";
248     /** Continually monitoring location data. */
249     public static final String OPSTR_MONITOR_LOCATION
250             = "android:monitor_location";
251     /** Continually monitoring location data with a relatively high power request. */
252     public static final String OPSTR_MONITOR_HIGH_POWER_LOCATION
253             = "android:monitor_location_high_power";
254     /** Access to {@link android.app.usage.UsageStatsManager}. */
255     public static final String OPSTR_GET_USAGE_STATS
256             = "android:get_usage_stats";
257     /** Activate a VPN connection without user intervention. @hide */
258     @SystemApi
259     public static final String OPSTR_ACTIVATE_VPN
260             = "android:activate_vpn";
261     /** Allows an application to read the user's contacts data. */
262     public static final String OPSTR_READ_CONTACTS
263             = "android:read_contacts";
264     /** Allows an application to write to the user's contacts data. */
265     public static final String OPSTR_WRITE_CONTACTS
266             = "android:write_contacts";
267     /** Allows an application to read the user's call log. */
268     public static final String OPSTR_READ_CALL_LOG
269             = "android:read_call_log";
270     /** Allows an application to write to the user's call log. */
271     public static final String OPSTR_WRITE_CALL_LOG
272             = "android:write_call_log";
273     /** Allows an application to read the user's calendar data. */
274     public static final String OPSTR_READ_CALENDAR
275             = "android:read_calendar";
276     /** Allows an application to write to the user's calendar data. */
277     public static final String OPSTR_WRITE_CALENDAR
278             = "android:write_calendar";
279     /** Allows an application to initiate a phone call. */
280     public static final String OPSTR_CALL_PHONE
281             = "android:call_phone";
282     /** Allows an application to read SMS messages. */
283     public static final String OPSTR_READ_SMS
284             = "android:read_sms";
285     /** Allows an application to receive SMS messages. */
286     public static final String OPSTR_RECEIVE_SMS
287             = "android:receive_sms";
288     /** Allows an application to receive MMS messages. */
289     public static final String OPSTR_RECEIVE_MMS
290             = "android:receive_mms";
291     /** Allows an application to receive WAP push messages. */
292     public static final String OPSTR_RECEIVE_WAP_PUSH
293             = "android:receive_wap_push";
294     /** Allows an application to send SMS messages. */
295     public static final String OPSTR_SEND_SMS
296             = "android:send_sms";
297     /** Required to be able to access the camera device. */
298     public static final String OPSTR_CAMERA
299             = "android:camera";
300     /** Required to be able to access the microphone device. */
301     public static final String OPSTR_RECORD_AUDIO
302             = "android:record_audio";
303     /** Required to access phone state related information. */
304     public static final String OPSTR_READ_PHONE_STATE
305             = "android:read_phone_state";
306     /** Required to access phone state related information. */
307     public static final String OPSTR_ADD_VOICEMAIL
308             = "android:add_voicemail";
309     /** Access APIs for SIP calling over VOIP or WiFi */
310     public static final String OPSTR_USE_SIP
311             = "android:use_sip";
312     /** Use the fingerprint API. */
313     public static final String OPSTR_USE_FINGERPRINT
314             = "android:use_fingerprint";
315     /** Access to body sensors such as heart rate, etc. */
316     public static final String OPSTR_BODY_SENSORS
317             = "android:body_sensors";
318     /** Read previously received cell broadcast messages. */
319     public static final String OPSTR_READ_CELL_BROADCASTS
320             = "android:read_cell_broadcasts";
321     /** Inject mock location into the system. */
322     public static final String OPSTR_MOCK_LOCATION
323             = "android:mock_location";
324     /** Read external storage. */
325     public static final String OPSTR_READ_EXTERNAL_STORAGE
326             = "android:read_external_storage";
327     /** Write external storage. */
328     public static final String OPSTR_WRITE_EXTERNAL_STORAGE
329             = "android:write_external_storage";
330     /** Required to draw on top of other apps. */
331     public static final String OPSTR_SYSTEM_ALERT_WINDOW
332             = "android:system_alert_window";
333     /** Required to write/modify/update system settingss. */
334     public static final String OPSTR_WRITE_SETTINGS
335             = "android:write_settings";
336     /** @hide Get device accounts. */
337     public static final String OPSTR_GET_ACCOUNTS
338             = "android:get_accounts";
339 
340     /**
341      * This maps each operation to the operation that serves as the
342      * switch to determine whether it is allowed.  Generally this is
343      * a 1:1 mapping, but for some things (like location) that have
344      * multiple low-level operations being tracked that should be
345      * presented to the user as one switch then this can be used to
346      * make them all controlled by the same single operation.
347      */
348     private static int[] sOpToSwitch = new int[] {
349             OP_COARSE_LOCATION,
350             OP_COARSE_LOCATION,
351             OP_COARSE_LOCATION,
352             OP_VIBRATE,
353             OP_READ_CONTACTS,
354             OP_WRITE_CONTACTS,
355             OP_READ_CALL_LOG,
356             OP_WRITE_CALL_LOG,
357             OP_READ_CALENDAR,
358             OP_WRITE_CALENDAR,
359             OP_COARSE_LOCATION,
360             OP_POST_NOTIFICATION,
361             OP_COARSE_LOCATION,
362             OP_CALL_PHONE,
363             OP_READ_SMS,
364             OP_WRITE_SMS,
365             OP_RECEIVE_SMS,
366             OP_RECEIVE_SMS,
367             OP_RECEIVE_SMS,
368             OP_RECEIVE_SMS,
369             OP_SEND_SMS,
370             OP_READ_SMS,
371             OP_WRITE_SMS,
372             OP_WRITE_SETTINGS,
373             OP_SYSTEM_ALERT_WINDOW,
374             OP_ACCESS_NOTIFICATIONS,
375             OP_CAMERA,
376             OP_RECORD_AUDIO,
377             OP_PLAY_AUDIO,
378             OP_READ_CLIPBOARD,
379             OP_WRITE_CLIPBOARD,
380             OP_TAKE_MEDIA_BUTTONS,
381             OP_TAKE_AUDIO_FOCUS,
382             OP_AUDIO_MASTER_VOLUME,
383             OP_AUDIO_VOICE_VOLUME,
384             OP_AUDIO_RING_VOLUME,
385             OP_AUDIO_MEDIA_VOLUME,
386             OP_AUDIO_ALARM_VOLUME,
387             OP_AUDIO_NOTIFICATION_VOLUME,
388             OP_AUDIO_BLUETOOTH_VOLUME,
389             OP_WAKE_LOCK,
390             OP_COARSE_LOCATION,
391             OP_COARSE_LOCATION,
392             OP_GET_USAGE_STATS,
393             OP_MUTE_MICROPHONE,
394             OP_TOAST_WINDOW,
395             OP_PROJECT_MEDIA,
396             OP_ACTIVATE_VPN,
397             OP_WRITE_WALLPAPER,
398             OP_ASSIST_STRUCTURE,
399             OP_ASSIST_SCREENSHOT,
400             OP_READ_PHONE_STATE,
401             OP_ADD_VOICEMAIL,
402             OP_USE_SIP,
403             OP_PROCESS_OUTGOING_CALLS,
404             OP_USE_FINGERPRINT,
405             OP_BODY_SENSORS,
406             OP_READ_CELL_BROADCASTS,
407             OP_MOCK_LOCATION,
408             OP_READ_EXTERNAL_STORAGE,
409             OP_WRITE_EXTERNAL_STORAGE,
410             OP_TURN_SCREEN_ON,
411             OP_GET_ACCOUNTS,
412     };
413 
414     /**
415      * This maps each operation to the public string constant for it.
416      * If it doesn't have a public string constant, it maps to null.
417      */
418     private static String[] sOpToString = new String[] {
419             OPSTR_COARSE_LOCATION,
420             OPSTR_FINE_LOCATION,
421             null,
422             null,
423             OPSTR_READ_CONTACTS,
424             OPSTR_WRITE_CONTACTS,
425             OPSTR_READ_CALL_LOG,
426             OPSTR_WRITE_CALL_LOG,
427             OPSTR_READ_CALENDAR,
428             OPSTR_WRITE_CALENDAR,
429             null,
430             null,
431             null,
432             OPSTR_CALL_PHONE,
433             OPSTR_READ_SMS,
434             null,
435             OPSTR_RECEIVE_SMS,
436             null,
437             OPSTR_RECEIVE_MMS,
438             OPSTR_RECEIVE_WAP_PUSH,
439             OPSTR_SEND_SMS,
440             null,
441             null,
442             OPSTR_WRITE_SETTINGS,
443             OPSTR_SYSTEM_ALERT_WINDOW,
444             null,
445             OPSTR_CAMERA,
446             OPSTR_RECORD_AUDIO,
447             null,
448             null,
449             null,
450             null,
451             null,
452             null,
453             null,
454             null,
455             null,
456             null,
457             null,
458             null,
459             null,
460             OPSTR_MONITOR_LOCATION,
461             OPSTR_MONITOR_HIGH_POWER_LOCATION,
462             OPSTR_GET_USAGE_STATS,
463             null,
464             null,
465             null,
466             OPSTR_ACTIVATE_VPN,
467             null,
468             null,
469             null,
470             OPSTR_READ_PHONE_STATE,
471             OPSTR_ADD_VOICEMAIL,
472             OPSTR_USE_SIP,
473             null,
474             OPSTR_USE_FINGERPRINT,
475             OPSTR_BODY_SENSORS,
476             OPSTR_READ_CELL_BROADCASTS,
477             OPSTR_MOCK_LOCATION,
478             OPSTR_READ_EXTERNAL_STORAGE,
479             OPSTR_WRITE_EXTERNAL_STORAGE,
480             null,
481             OPSTR_GET_ACCOUNTS
482     };
483 
484     /**
485      * This provides a simple name for each operation to be used
486      * in debug output.
487      */
488     private static String[] sOpNames = new String[] {
489             "COARSE_LOCATION",
490             "FINE_LOCATION",
491             "GPS",
492             "VIBRATE",
493             "READ_CONTACTS",
494             "WRITE_CONTACTS",
495             "READ_CALL_LOG",
496             "WRITE_CALL_LOG",
497             "READ_CALENDAR",
498             "WRITE_CALENDAR",
499             "WIFI_SCAN",
500             "POST_NOTIFICATION",
501             "NEIGHBORING_CELLS",
502             "CALL_PHONE",
503             "READ_SMS",
504             "WRITE_SMS",
505             "RECEIVE_SMS",
506             "RECEIVE_EMERGECY_SMS",
507             "RECEIVE_MMS",
508             "RECEIVE_WAP_PUSH",
509             "SEND_SMS",
510             "READ_ICC_SMS",
511             "WRITE_ICC_SMS",
512             "WRITE_SETTINGS",
513             "SYSTEM_ALERT_WINDOW",
514             "ACCESS_NOTIFICATIONS",
515             "CAMERA",
516             "RECORD_AUDIO",
517             "PLAY_AUDIO",
518             "READ_CLIPBOARD",
519             "WRITE_CLIPBOARD",
520             "TAKE_MEDIA_BUTTONS",
521             "TAKE_AUDIO_FOCUS",
522             "AUDIO_MASTER_VOLUME",
523             "AUDIO_VOICE_VOLUME",
524             "AUDIO_RING_VOLUME",
525             "AUDIO_MEDIA_VOLUME",
526             "AUDIO_ALARM_VOLUME",
527             "AUDIO_NOTIFICATION_VOLUME",
528             "AUDIO_BLUETOOTH_VOLUME",
529             "WAKE_LOCK",
530             "MONITOR_LOCATION",
531             "MONITOR_HIGH_POWER_LOCATION",
532             "GET_USAGE_STATS",
533             "MUTE_MICROPHONE",
534             "TOAST_WINDOW",
535             "PROJECT_MEDIA",
536             "ACTIVATE_VPN",
537             "WRITE_WALLPAPER",
538             "ASSIST_STRUCTURE",
539             "ASSIST_SCREENSHOT",
540             "OP_READ_PHONE_STATE",
541             "ADD_VOICEMAIL",
542             "USE_SIP",
543             "PROCESS_OUTGOING_CALLS",
544             "USE_FINGERPRINT",
545             "BODY_SENSORS",
546             "READ_CELL_BROADCASTS",
547             "MOCK_LOCATION",
548             "READ_EXTERNAL_STORAGE",
549             "WRITE_EXTERNAL_STORAGE",
550             "TURN_ON_SCREEN",
551             "GET_ACCOUNTS",
552     };
553 
554     /**
555      * This optionally maps a permission to an operation.  If there
556      * is no permission associated with an operation, it is null.
557      */
558     private static String[] sOpPerms = new String[] {
559             android.Manifest.permission.ACCESS_COARSE_LOCATION,
560             android.Manifest.permission.ACCESS_FINE_LOCATION,
561             null,
562             android.Manifest.permission.VIBRATE,
563             android.Manifest.permission.READ_CONTACTS,
564             android.Manifest.permission.WRITE_CONTACTS,
565             android.Manifest.permission.READ_CALL_LOG,
566             android.Manifest.permission.WRITE_CALL_LOG,
567             android.Manifest.permission.READ_CALENDAR,
568             android.Manifest.permission.WRITE_CALENDAR,
569             android.Manifest.permission.ACCESS_WIFI_STATE,
570             null, // no permission required for notifications
571             null, // neighboring cells shares the coarse location perm
572             android.Manifest.permission.CALL_PHONE,
573             android.Manifest.permission.READ_SMS,
574             null, // no permission required for writing sms
575             android.Manifest.permission.RECEIVE_SMS,
576             android.Manifest.permission.RECEIVE_EMERGENCY_BROADCAST,
577             android.Manifest.permission.RECEIVE_MMS,
578             android.Manifest.permission.RECEIVE_WAP_PUSH,
579             android.Manifest.permission.SEND_SMS,
580             android.Manifest.permission.READ_SMS,
581             null, // no permission required for writing icc sms
582             android.Manifest.permission.WRITE_SETTINGS,
583             android.Manifest.permission.SYSTEM_ALERT_WINDOW,
584             android.Manifest.permission.ACCESS_NOTIFICATIONS,
585             android.Manifest.permission.CAMERA,
586             android.Manifest.permission.RECORD_AUDIO,
587             null, // no permission for playing audio
588             null, // no permission for reading clipboard
589             null, // no permission for writing clipboard
590             null, // no permission for taking media buttons
591             null, // no permission for taking audio focus
592             null, // no permission for changing master volume
593             null, // no permission for changing voice volume
594             null, // no permission for changing ring volume
595             null, // no permission for changing media volume
596             null, // no permission for changing alarm volume
597             null, // no permission for changing notification volume
598             null, // no permission for changing bluetooth volume
599             android.Manifest.permission.WAKE_LOCK,
600             null, // no permission for generic location monitoring
601             null, // no permission for high power location monitoring
602             android.Manifest.permission.PACKAGE_USAGE_STATS,
603             null, // no permission for muting/unmuting microphone
604             null, // no permission for displaying toasts
605             null, // no permission for projecting media
606             null, // no permission for activating vpn
607             null, // no permission for supporting wallpaper
608             null, // no permission for receiving assist structure
609             null, // no permission for receiving assist screenshot
610             Manifest.permission.READ_PHONE_STATE,
611             Manifest.permission.ADD_VOICEMAIL,
612             Manifest.permission.USE_SIP,
613             Manifest.permission.PROCESS_OUTGOING_CALLS,
614             Manifest.permission.USE_FINGERPRINT,
615             Manifest.permission.BODY_SENSORS,
616             Manifest.permission.READ_CELL_BROADCASTS,
617             null,
618             Manifest.permission.READ_EXTERNAL_STORAGE,
619             Manifest.permission.WRITE_EXTERNAL_STORAGE,
620             null, // no permission for turning the screen on
621             Manifest.permission.GET_ACCOUNTS
622     };
623 
624     /**
625      * Specifies whether an Op should be restricted by a user restriction.
626      * Each Op should be filled with a restriction string from UserManager or
627      * null to specify it is not affected by any user restriction.
628      */
629     private static String[] sOpRestrictions = new String[] {
630             UserManager.DISALLOW_SHARE_LOCATION, //COARSE_LOCATION
631             UserManager.DISALLOW_SHARE_LOCATION, //FINE_LOCATION
632             UserManager.DISALLOW_SHARE_LOCATION, //GPS
633             null, //VIBRATE
634             null, //READ_CONTACTS
635             null, //WRITE_CONTACTS
636             UserManager.DISALLOW_OUTGOING_CALLS, //READ_CALL_LOG
637             UserManager.DISALLOW_OUTGOING_CALLS, //WRITE_CALL_LOG
638             null, //READ_CALENDAR
639             null, //WRITE_CALENDAR
640             UserManager.DISALLOW_SHARE_LOCATION, //WIFI_SCAN
641             null, //POST_NOTIFICATION
642             null, //NEIGHBORING_CELLS
643             null, //CALL_PHONE
644             UserManager.DISALLOW_SMS, //READ_SMS
645             UserManager.DISALLOW_SMS, //WRITE_SMS
646             UserManager.DISALLOW_SMS, //RECEIVE_SMS
647             null, //RECEIVE_EMERGENCY_SMS
648             UserManager.DISALLOW_SMS, //RECEIVE_MMS
649             null, //RECEIVE_WAP_PUSH
650             UserManager.DISALLOW_SMS, //SEND_SMS
651             UserManager.DISALLOW_SMS, //READ_ICC_SMS
652             UserManager.DISALLOW_SMS, //WRITE_ICC_SMS
653             null, //WRITE_SETTINGS
654             UserManager.DISALLOW_CREATE_WINDOWS, //SYSTEM_ALERT_WINDOW
655             null, //ACCESS_NOTIFICATIONS
656             null, //CAMERA
657             UserManager.DISALLOW_RECORD_AUDIO, //RECORD_AUDIO
658             null, //PLAY_AUDIO
659             null, //READ_CLIPBOARD
660             null, //WRITE_CLIPBOARD
661             null, //TAKE_MEDIA_BUTTONS
662             null, //TAKE_AUDIO_FOCUS
663             UserManager.DISALLOW_ADJUST_VOLUME, //AUDIO_MASTER_VOLUME
664             UserManager.DISALLOW_ADJUST_VOLUME, //AUDIO_VOICE_VOLUME
665             UserManager.DISALLOW_ADJUST_VOLUME, //AUDIO_RING_VOLUME
666             UserManager.DISALLOW_ADJUST_VOLUME, //AUDIO_MEDIA_VOLUME
667             UserManager.DISALLOW_ADJUST_VOLUME, //AUDIO_ALARM_VOLUME
668             UserManager.DISALLOW_ADJUST_VOLUME, //AUDIO_NOTIFICATION_VOLUME
669             UserManager.DISALLOW_ADJUST_VOLUME, //AUDIO_BLUETOOTH_VOLUME
670             null, //WAKE_LOCK
671             UserManager.DISALLOW_SHARE_LOCATION, //MONITOR_LOCATION
672             UserManager.DISALLOW_SHARE_LOCATION, //MONITOR_HIGH_POWER_LOCATION
673             null, //GET_USAGE_STATS
674             UserManager.DISALLOW_UNMUTE_MICROPHONE, // MUTE_MICROPHONE
675             UserManager.DISALLOW_CREATE_WINDOWS, // TOAST_WINDOW
676             null, //PROJECT_MEDIA
677             UserManager.DISALLOW_CONFIG_VPN, // ACTIVATE_VPN
678             UserManager.DISALLOW_WALLPAPER, // WRITE_WALLPAPER
679             null, // ASSIST_STRUCTURE
680             null, // ASSIST_SCREENSHOT
681             null, // READ_PHONE_STATE
682             null, // ADD_VOICEMAIL
683             null, // USE_SIP
684             null, // PROCESS_OUTGOING_CALLS
685             null, // USE_FINGERPRINT
686             null, // BODY_SENSORS
687             null, // READ_CELL_BROADCASTS
688             null, // MOCK_LOCATION
689             null, // READ_EXTERNAL_STORAGE
690             null, // WRITE_EXTERNAL_STORAGE
691             null, // TURN_ON_SCREEN
692             null, // GET_ACCOUNTS
693     };
694 
695     /**
696      * This specifies whether each option should allow the system
697      * (and system ui) to bypass the user restriction when active.
698      */
699     private static boolean[] sOpAllowSystemRestrictionBypass = new boolean[] {
700             false, //COARSE_LOCATION
701             false, //FINE_LOCATION
702             false, //GPS
703             false, //VIBRATE
704             false, //READ_CONTACTS
705             false, //WRITE_CONTACTS
706             false, //READ_CALL_LOG
707             false, //WRITE_CALL_LOG
708             false, //READ_CALENDAR
709             false, //WRITE_CALENDAR
710             true, //WIFI_SCAN
711             false, //POST_NOTIFICATION
712             false, //NEIGHBORING_CELLS
713             false, //CALL_PHONE
714             false, //READ_SMS
715             false, //WRITE_SMS
716             false, //RECEIVE_SMS
717             false, //RECEIVE_EMERGECY_SMS
718             false, //RECEIVE_MMS
719             false, //RECEIVE_WAP_PUSH
720             false, //SEND_SMS
721             false, //READ_ICC_SMS
722             false, //WRITE_ICC_SMS
723             false, //WRITE_SETTINGS
724             true, //SYSTEM_ALERT_WINDOW
725             false, //ACCESS_NOTIFICATIONS
726             false, //CAMERA
727             false, //RECORD_AUDIO
728             false, //PLAY_AUDIO
729             false, //READ_CLIPBOARD
730             false, //WRITE_CLIPBOARD
731             false, //TAKE_MEDIA_BUTTONS
732             false, //TAKE_AUDIO_FOCUS
733             false, //AUDIO_MASTER_VOLUME
734             false, //AUDIO_VOICE_VOLUME
735             false, //AUDIO_RING_VOLUME
736             false, //AUDIO_MEDIA_VOLUME
737             false, //AUDIO_ALARM_VOLUME
738             false, //AUDIO_NOTIFICATION_VOLUME
739             false, //AUDIO_BLUETOOTH_VOLUME
740             false, //WAKE_LOCK
741             false, //MONITOR_LOCATION
742             false, //MONITOR_HIGH_POWER_LOCATION
743             false, //GET_USAGE_STATS
744             false, //MUTE_MICROPHONE
745             true, //TOAST_WINDOW
746             false, //PROJECT_MEDIA
747             false, //ACTIVATE_VPN
748             false, //WALLPAPER
749             false, //ASSIST_STRUCTURE
750             false, //ASSIST_SCREENSHOT
751             false, //READ_PHONE_STATE
752             false, //ADD_VOICEMAIL
753             false, // USE_SIP
754             false, // PROCESS_OUTGOING_CALLS
755             false, // USE_FINGERPRINT
756             false, // BODY_SENSORS
757             false, // READ_CELL_BROADCASTS
758             false, // MOCK_LOCATION
759             false, // READ_EXTERNAL_STORAGE
760             false, // WRITE_EXTERNAL_STORAGE
761             false, // TURN_ON_SCREEN
762             false, // GET_ACCOUNTS
763     };
764 
765     /**
766      * This specifies the default mode for each operation.
767      */
768     private static int[] sOpDefaultMode = new int[] {
769             AppOpsManager.MODE_ALLOWED,
770             AppOpsManager.MODE_ALLOWED,
771             AppOpsManager.MODE_ALLOWED,
772             AppOpsManager.MODE_ALLOWED,
773             AppOpsManager.MODE_ALLOWED,
774             AppOpsManager.MODE_ALLOWED,
775             AppOpsManager.MODE_ALLOWED,
776             AppOpsManager.MODE_ALLOWED,
777             AppOpsManager.MODE_ALLOWED,
778             AppOpsManager.MODE_ALLOWED,
779             AppOpsManager.MODE_ALLOWED,
780             AppOpsManager.MODE_ALLOWED,
781             AppOpsManager.MODE_ALLOWED,
782             AppOpsManager.MODE_ALLOWED,
783             AppOpsManager.MODE_ALLOWED,
784             AppOpsManager.MODE_IGNORED, // OP_WRITE_SMS
785             AppOpsManager.MODE_ALLOWED,
786             AppOpsManager.MODE_ALLOWED,
787             AppOpsManager.MODE_ALLOWED,
788             AppOpsManager.MODE_ALLOWED,
789             AppOpsManager.MODE_ALLOWED,
790             AppOpsManager.MODE_ALLOWED,
791             AppOpsManager.MODE_ALLOWED,
792             AppOpsManager.MODE_DEFAULT, // OP_WRITE_SETTINGS
793             AppOpsManager.MODE_DEFAULT, // OP_SYSTEM_ALERT_WINDOW
794             AppOpsManager.MODE_ALLOWED,
795             AppOpsManager.MODE_ALLOWED,
796             AppOpsManager.MODE_ALLOWED,
797             AppOpsManager.MODE_ALLOWED,
798             AppOpsManager.MODE_ALLOWED,
799             AppOpsManager.MODE_ALLOWED,
800             AppOpsManager.MODE_ALLOWED,
801             AppOpsManager.MODE_ALLOWED,
802             AppOpsManager.MODE_ALLOWED,
803             AppOpsManager.MODE_ALLOWED,
804             AppOpsManager.MODE_ALLOWED,
805             AppOpsManager.MODE_ALLOWED,
806             AppOpsManager.MODE_ALLOWED,
807             AppOpsManager.MODE_ALLOWED,
808             AppOpsManager.MODE_ALLOWED,
809             AppOpsManager.MODE_ALLOWED,
810             AppOpsManager.MODE_ALLOWED,
811             AppOpsManager.MODE_ALLOWED,
812             AppOpsManager.MODE_DEFAULT, // OP_GET_USAGE_STATS
813             AppOpsManager.MODE_ALLOWED,
814             AppOpsManager.MODE_ALLOWED,
815             AppOpsManager.MODE_IGNORED, // OP_PROJECT_MEDIA
816             AppOpsManager.MODE_IGNORED, // OP_ACTIVATE_VPN
817             AppOpsManager.MODE_ALLOWED,
818             AppOpsManager.MODE_ALLOWED,
819             AppOpsManager.MODE_ALLOWED,
820             AppOpsManager.MODE_ALLOWED,
821             AppOpsManager.MODE_ALLOWED,
822             AppOpsManager.MODE_ALLOWED,
823             AppOpsManager.MODE_ALLOWED,
824             AppOpsManager.MODE_ALLOWED,
825             AppOpsManager.MODE_ALLOWED,
826             AppOpsManager.MODE_ALLOWED,
827             AppOpsManager.MODE_ERRORED,  // OP_MOCK_LOCATION
828             AppOpsManager.MODE_ALLOWED,
829             AppOpsManager.MODE_ALLOWED,
830             AppOpsManager.MODE_ALLOWED,  // OP_TURN_ON_SCREEN
831             AppOpsManager.MODE_ALLOWED,
832     };
833 
834     /**
835      * This specifies whether each option is allowed to be reset
836      * when resetting all app preferences.  Disable reset for
837      * app ops that are under strong control of some part of the
838      * system (such as OP_WRITE_SMS, which should be allowed only
839      * for whichever app is selected as the current SMS app).
840      */
841     private static boolean[] sOpDisableReset = new boolean[] {
842             false,
843             false,
844             false,
845             false,
846             false,
847             false,
848             false,
849             false,
850             false,
851             false,
852             false,
853             false,
854             false,
855             false,
856             false,
857             true,      // OP_WRITE_SMS
858             false,
859             false,
860             false,
861             false,
862             false,
863             false,
864             false,
865             false,
866             false,
867             false,
868             false,
869             false,
870             false,
871             false,
872             false,
873             false,
874             false,
875             false,
876             false,
877             false,
878             false,
879             false,
880             false,
881             false,
882             false,
883             false,
884             false,
885             false,
886             false,
887             false,
888             false,
889             false,
890             false,
891             false,
892             false,
893             false,
894             false,
895             false,
896             false,
897             false,
898             false,
899             false,
900             false,
901             false,
902             false,
903             false,
904             false
905     };
906 
907     /**
908      * Mapping from an app op name to the app op code.
909      */
910     private static HashMap<String, Integer> sOpStrToOp = new HashMap<>();
911 
912     /**
913      * Mapping from a permission to the corresponding app op.
914      */
915     private static HashMap<String, Integer> sPermToOp = new HashMap<>();
916 
917     static {
918         if (sOpToSwitch.length != _NUM_OP) {
919             throw new IllegalStateException("sOpToSwitch length " + sOpToSwitch.length
920                     + " should be " + _NUM_OP);
921         }
922         if (sOpToString.length != _NUM_OP) {
923             throw new IllegalStateException("sOpToString length " + sOpToString.length
924                     + " should be " + _NUM_OP);
925         }
926         if (sOpNames.length != _NUM_OP) {
927             throw new IllegalStateException("sOpNames length " + sOpNames.length
928                     + " should be " + _NUM_OP);
929         }
930         if (sOpPerms.length != _NUM_OP) {
931             throw new IllegalStateException("sOpPerms length " + sOpPerms.length
932                     + " should be " + _NUM_OP);
933         }
934         if (sOpDefaultMode.length != _NUM_OP) {
935             throw new IllegalStateException("sOpDefaultMode length " + sOpDefaultMode.length
936                     + " should be " + _NUM_OP);
937         }
938         if (sOpDisableReset.length != _NUM_OP) {
939             throw new IllegalStateException("sOpDisableReset length " + sOpDisableReset.length
940                     + " should be " + _NUM_OP);
941         }
942         if (sOpRestrictions.length != _NUM_OP) {
943             throw new IllegalStateException("sOpRestrictions length " + sOpRestrictions.length
944                     + " should be " + _NUM_OP);
945         }
946         if (sOpAllowSystemRestrictionBypass.length != _NUM_OP) {
947             throw new IllegalStateException("sOpAllowSYstemRestrictionsBypass length "
948                     + sOpRestrictions.length + " should be " + _NUM_OP);
949         }
950         for (int i=0; i<_NUM_OP; i++) {
951             if (sOpToString[i] != null) {
sOpStrToOp.put(sOpToString[i], i)952                 sOpStrToOp.put(sOpToString[i], i);
953             }
954         }
955         for (int i=0; i<_NUM_OP; i++) {
956             if (sOpPerms[i] != null) {
sPermToOp.put(sOpPerms[i], i)957                 sPermToOp.put(sOpPerms[i], i);
958             }
959         }
960     }
961 
962     /**
963      * Retrieve the op switch that controls the given operation.
964      * @hide
965      */
opToSwitch(int op)966     public static int opToSwitch(int op) {
967         return sOpToSwitch[op];
968     }
969 
970     /**
971      * Retrieve a non-localized name for the operation, for debugging output.
972      * @hide
973      */
opToName(int op)974     public static String opToName(int op) {
975         if (op == OP_NONE) return "NONE";
976         return op < sOpNames.length ? sOpNames[op] : ("Unknown(" + op + ")");
977     }
978 
979     /**
980      * @hide
981      */
strDebugOpToOp(String op)982     public static int strDebugOpToOp(String op) {
983         for (int i=0; i<sOpNames.length; i++) {
984             if (sOpNames[i].equals(op)) {
985                 return i;
986             }
987         }
988         throw new IllegalArgumentException("Unknown operation string: " + op);
989     }
990 
991     /**
992      * Retrieve the permission associated with an operation, or null if there is not one.
993      * @hide
994      */
opToPermission(int op)995     public static String opToPermission(int op) {
996         return sOpPerms[op];
997     }
998 
999     /**
1000      * Retrieve the user restriction associated with an operation, or null if there is not one.
1001      * @hide
1002      */
opToRestriction(int op)1003     public static String opToRestriction(int op) {
1004         return sOpRestrictions[op];
1005     }
1006 
1007     /**
1008      * Retrieve the app op code for a permission, or null if there is not one.
1009      * @hide
1010      */
permissionToOpCode(String permission)1011     public static int permissionToOpCode(String permission) {
1012         Integer boxedOpCode = sPermToOp.get(permission);
1013         return boxedOpCode != null ? boxedOpCode : OP_NONE;
1014     }
1015 
1016     /**
1017      * Retrieve whether the op allows the system (and system ui) to
1018      * bypass the user restriction.
1019      * @hide
1020      */
opAllowSystemBypassRestriction(int op)1021     public static boolean opAllowSystemBypassRestriction(int op) {
1022         return sOpAllowSystemRestrictionBypass[op];
1023     }
1024 
1025     /**
1026      * Retrieve the default mode for the operation.
1027      * @hide
1028      */
opToDefaultMode(int op)1029     public static int opToDefaultMode(int op) {
1030         return sOpDefaultMode[op];
1031     }
1032 
1033     /**
1034      * Retrieve whether the op allows itself to be reset.
1035      * @hide
1036      */
opAllowsReset(int op)1037     public static boolean opAllowsReset(int op) {
1038         return !sOpDisableReset[op];
1039     }
1040 
1041     /**
1042      * Class holding all of the operation information associated with an app.
1043      * @hide
1044      */
1045     public static class PackageOps implements Parcelable {
1046         private final String mPackageName;
1047         private final int mUid;
1048         private final List<OpEntry> mEntries;
1049 
PackageOps(String packageName, int uid, List<OpEntry> entries)1050         public PackageOps(String packageName, int uid, List<OpEntry> entries) {
1051             mPackageName = packageName;
1052             mUid = uid;
1053             mEntries = entries;
1054         }
1055 
getPackageName()1056         public String getPackageName() {
1057             return mPackageName;
1058         }
1059 
getUid()1060         public int getUid() {
1061             return mUid;
1062         }
1063 
getOps()1064         public List<OpEntry> getOps() {
1065             return mEntries;
1066         }
1067 
1068         @Override
describeContents()1069         public int describeContents() {
1070             return 0;
1071         }
1072 
1073         @Override
writeToParcel(Parcel dest, int flags)1074         public void writeToParcel(Parcel dest, int flags) {
1075             dest.writeString(mPackageName);
1076             dest.writeInt(mUid);
1077             dest.writeInt(mEntries.size());
1078             for (int i=0; i<mEntries.size(); i++) {
1079                 mEntries.get(i).writeToParcel(dest, flags);
1080             }
1081         }
1082 
PackageOps(Parcel source)1083         PackageOps(Parcel source) {
1084             mPackageName = source.readString();
1085             mUid = source.readInt();
1086             mEntries = new ArrayList<OpEntry>();
1087             final int N = source.readInt();
1088             for (int i=0; i<N; i++) {
1089                 mEntries.add(OpEntry.CREATOR.createFromParcel(source));
1090             }
1091         }
1092 
1093         public static final Creator<PackageOps> CREATOR = new Creator<PackageOps>() {
1094             @Override public PackageOps createFromParcel(Parcel source) {
1095                 return new PackageOps(source);
1096             }
1097 
1098             @Override public PackageOps[] newArray(int size) {
1099                 return new PackageOps[size];
1100             }
1101         };
1102     }
1103 
1104     /**
1105      * Class holding the information about one unique operation of an application.
1106      * @hide
1107      */
1108     public static class OpEntry implements Parcelable {
1109         private final int mOp;
1110         private final int mMode;
1111         private final long mTime;
1112         private final long mRejectTime;
1113         private final int mDuration;
1114         private final int mProxyUid;
1115         private final String mProxyPackageName;
1116 
OpEntry(int op, int mode, long time, long rejectTime, int duration, int proxyUid, String proxyPackage)1117         public OpEntry(int op, int mode, long time, long rejectTime, int duration,
1118                 int proxyUid, String proxyPackage) {
1119             mOp = op;
1120             mMode = mode;
1121             mTime = time;
1122             mRejectTime = rejectTime;
1123             mDuration = duration;
1124             mProxyUid = proxyUid;
1125             mProxyPackageName = proxyPackage;
1126         }
1127 
getOp()1128         public int getOp() {
1129             return mOp;
1130         }
1131 
getMode()1132         public int getMode() {
1133             return mMode;
1134         }
1135 
getTime()1136         public long getTime() {
1137             return mTime;
1138         }
1139 
getRejectTime()1140         public long getRejectTime() {
1141             return mRejectTime;
1142         }
1143 
isRunning()1144         public boolean isRunning() {
1145             return mDuration == -1;
1146         }
1147 
getDuration()1148         public int getDuration() {
1149             return mDuration == -1 ? (int)(System.currentTimeMillis()-mTime) : mDuration;
1150         }
1151 
getProxyUid()1152         public int getProxyUid() {
1153             return  mProxyUid;
1154         }
1155 
getProxyPackageName()1156         public String getProxyPackageName() {
1157             return mProxyPackageName;
1158         }
1159 
1160         @Override
describeContents()1161         public int describeContents() {
1162             return 0;
1163         }
1164 
1165         @Override
writeToParcel(Parcel dest, int flags)1166         public void writeToParcel(Parcel dest, int flags) {
1167             dest.writeInt(mOp);
1168             dest.writeInt(mMode);
1169             dest.writeLong(mTime);
1170             dest.writeLong(mRejectTime);
1171             dest.writeInt(mDuration);
1172             dest.writeInt(mProxyUid);
1173             dest.writeString(mProxyPackageName);
1174         }
1175 
OpEntry(Parcel source)1176         OpEntry(Parcel source) {
1177             mOp = source.readInt();
1178             mMode = source.readInt();
1179             mTime = source.readLong();
1180             mRejectTime = source.readLong();
1181             mDuration = source.readInt();
1182             mProxyUid = source.readInt();
1183             mProxyPackageName = source.readString();
1184         }
1185 
1186         public static final Creator<OpEntry> CREATOR = new Creator<OpEntry>() {
1187             @Override public OpEntry createFromParcel(Parcel source) {
1188                 return new OpEntry(source);
1189             }
1190 
1191             @Override public OpEntry[] newArray(int size) {
1192                 return new OpEntry[size];
1193             }
1194         };
1195     }
1196 
1197     /**
1198      * Callback for notification of changes to operation state.
1199      */
1200     public interface OnOpChangedListener {
onOpChanged(String op, String packageName)1201         public void onOpChanged(String op, String packageName);
1202     }
1203 
1204     /**
1205      * Callback for notification of changes to operation state.
1206      * This allows you to see the raw op codes instead of strings.
1207      * @hide
1208      */
1209     public static class OnOpChangedInternalListener implements OnOpChangedListener {
onOpChanged(String op, String packageName)1210         public void onOpChanged(String op, String packageName) { }
onOpChanged(int op, String packageName)1211         public void onOpChanged(int op, String packageName) { }
1212     }
1213 
AppOpsManager(Context context, IAppOpsService service)1214     AppOpsManager(Context context, IAppOpsService service) {
1215         mContext = context;
1216         mService = service;
1217     }
1218 
1219     /**
1220      * Retrieve current operation state for all applications.
1221      *
1222      * @param ops The set of operations you are interested in, or null if you want all of them.
1223      * @hide
1224      */
getPackagesForOps(int[] ops)1225     public List<AppOpsManager.PackageOps> getPackagesForOps(int[] ops) {
1226         try {
1227             return mService.getPackagesForOps(ops);
1228         } catch (RemoteException e) {
1229         }
1230         return null;
1231     }
1232 
1233     /**
1234      * Retrieve current operation state for one application.
1235      *
1236      * @param uid The uid of the application of interest.
1237      * @param packageName The name of the application of interest.
1238      * @param ops The set of operations you are interested in, or null if you want all of them.
1239      * @hide
1240      */
getOpsForPackage(int uid, String packageName, int[] ops)1241     public List<AppOpsManager.PackageOps> getOpsForPackage(int uid, String packageName, int[] ops) {
1242         try {
1243             return mService.getOpsForPackage(uid, packageName, ops);
1244         } catch (RemoteException e) {
1245         }
1246         return null;
1247     }
1248 
1249     /** @hide */
setUidMode(int code, int uid, int mode)1250     public void setUidMode(int code, int uid, int mode) {
1251         try {
1252             mService.setUidMode(code, uid, mode);
1253         } catch (RemoteException e) {
1254         }
1255     }
1256 
1257     /** @hide */
setMode(int code, int uid, String packageName, int mode)1258     public void setMode(int code, int uid, String packageName, int mode) {
1259         try {
1260             mService.setMode(code, uid, packageName, mode);
1261         } catch (RemoteException e) {
1262         }
1263     }
1264 
1265     /**
1266      * Set a non-persisted restriction on an audio operation at a stream-level.
1267      * Restrictions are temporary additional constraints imposed on top of the persisted rules
1268      * defined by {@link #setMode}.
1269      *
1270      * @param code The operation to restrict.
1271      * @param usage The {@link android.media.AudioAttributes} usage value.
1272      * @param mode The restriction mode (MODE_IGNORED,MODE_ERRORED) or MODE_ALLOWED to unrestrict.
1273      * @param exceptionPackages Optional list of packages to exclude from the restriction.
1274      * @hide
1275      */
setRestriction(int code, @AttributeUsage int usage, int mode, String[] exceptionPackages)1276     public void setRestriction(int code, @AttributeUsage int usage, int mode,
1277             String[] exceptionPackages) {
1278         try {
1279             final int uid = Binder.getCallingUid();
1280             mService.setAudioRestriction(code, usage, uid, mode, exceptionPackages);
1281         } catch (RemoteException e) {
1282         }
1283     }
1284 
1285     /** @hide */
resetAllModes()1286     public void resetAllModes() {
1287         try {
1288             mService.resetAllModes(UserHandle.myUserId(), null);
1289         } catch (RemoteException e) {
1290         }
1291     }
1292 
1293     /**
1294      * Gets the app op name associated with a given permission.
1295      * The app op name is one of the public constants defined
1296      * in this class such as {@link #OPSTR_COARSE_LOCATION}.
1297      *
1298      * @param permission The permission.
1299      * @return The app op associated with the permission or null.
1300      */
permissionToOp(String permission)1301     public static String permissionToOp(String permission) {
1302         final Integer opCode = sPermToOp.get(permission);
1303         if (opCode == null) {
1304             return null;
1305         }
1306         return sOpToString[opCode];
1307     }
1308 
1309     /**
1310      * Monitor for changes to the operating mode for the given op in the given app package.
1311      * @param op The operation to monitor, one of OPSTR_*.
1312      * @param packageName The name of the application to monitor.
1313      * @param callback Where to report changes.
1314      */
startWatchingMode(String op, String packageName, final OnOpChangedListener callback)1315     public void startWatchingMode(String op, String packageName,
1316             final OnOpChangedListener callback) {
1317         startWatchingMode(strOpToOp(op), packageName, callback);
1318     }
1319 
1320     /**
1321      * Monitor for changes to the operating mode for the given op in the given app package.
1322      * @param op The operation to monitor, one of OP_*.
1323      * @param packageName The name of the application to monitor.
1324      * @param callback Where to report changes.
1325      * @hide
1326      */
startWatchingMode(int op, String packageName, final OnOpChangedListener callback)1327     public void startWatchingMode(int op, String packageName, final OnOpChangedListener callback) {
1328         synchronized (mModeWatchers) {
1329             IAppOpsCallback cb = mModeWatchers.get(callback);
1330             if (cb == null) {
1331                 cb = new IAppOpsCallback.Stub() {
1332                     public void opChanged(int op, String packageName) {
1333                         if (callback instanceof OnOpChangedInternalListener) {
1334                             ((OnOpChangedInternalListener)callback).onOpChanged(op, packageName);
1335                         }
1336                         if (sOpToString[op] != null) {
1337                             callback.onOpChanged(sOpToString[op], packageName);
1338                         }
1339                     }
1340                 };
1341                 mModeWatchers.put(callback, cb);
1342             }
1343             try {
1344                 mService.startWatchingMode(op, packageName, cb);
1345             } catch (RemoteException e) {
1346             }
1347         }
1348     }
1349 
1350     /**
1351      * Stop monitoring that was previously started with {@link #startWatchingMode}.  All
1352      * monitoring associated with this callback will be removed.
1353      */
stopWatchingMode(OnOpChangedListener callback)1354     public void stopWatchingMode(OnOpChangedListener callback) {
1355         synchronized (mModeWatchers) {
1356             IAppOpsCallback cb = mModeWatchers.get(callback);
1357             if (cb != null) {
1358                 try {
1359                     mService.stopWatchingMode(cb);
1360                 } catch (RemoteException e) {
1361                 }
1362             }
1363         }
1364     }
1365 
buildSecurityExceptionMsg(int op, int uid, String packageName)1366     private String buildSecurityExceptionMsg(int op, int uid, String packageName) {
1367         return packageName + " from uid " + uid + " not allowed to perform " + sOpNames[op];
1368     }
1369 
1370     /**
1371      * {@hide}
1372      */
strOpToOp(String op)1373     public static int strOpToOp(String op) {
1374         Integer val = sOpStrToOp.get(op);
1375         if (val == null) {
1376             throw new IllegalArgumentException("Unknown operation string: " + op);
1377         }
1378         return val;
1379     }
1380 
1381     /**
1382      * Do a quick check for whether an application might be able to perform an operation.
1383      * This is <em>not</em> a security check; you must use {@link #noteOp(String, int, String)}
1384      * or {@link #startOp(String, int, String)} for your actual security checks, which also
1385      * ensure that the given uid and package name are consistent.  This function can just be
1386      * used for a quick check to see if an operation has been disabled for the application,
1387      * as an early reject of some work.  This does not modify the time stamp or other data
1388      * about the operation.
1389      * @param op The operation to check.  One of the OPSTR_* constants.
1390      * @param uid The user id of the application attempting to perform the operation.
1391      * @param packageName The name of the application attempting to perform the operation.
1392      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1393      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1394      * causing the app to crash).
1395      * @throws SecurityException If the app has been configured to crash on this op.
1396      */
checkOp(String op, int uid, String packageName)1397     public int checkOp(String op, int uid, String packageName) {
1398         return checkOp(strOpToOp(op), uid, packageName);
1399     }
1400 
1401     /**
1402      * Like {@link #checkOp} but instead of throwing a {@link SecurityException} it
1403      * returns {@link #MODE_ERRORED}.
1404      */
checkOpNoThrow(String op, int uid, String packageName)1405     public int checkOpNoThrow(String op, int uid, String packageName) {
1406         return checkOpNoThrow(strOpToOp(op), uid, packageName);
1407     }
1408 
1409     /**
1410      * Make note of an application performing an operation.  Note that you must pass
1411      * in both the uid and name of the application to be checked; this function will verify
1412      * that these two match, and if not, return {@link #MODE_IGNORED}.  If this call
1413      * succeeds, the last execution time of the operation for this app will be updated to
1414      * the current time.
1415      * @param op The operation to note.  One of the OPSTR_* constants.
1416      * @param uid The user id of the application attempting to perform the operation.
1417      * @param packageName The name of the application attempting to perform the operation.
1418      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1419      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1420      * causing the app to crash).
1421      * @throws SecurityException If the app has been configured to crash on this op.
1422      */
noteOp(String op, int uid, String packageName)1423     public int noteOp(String op, int uid, String packageName) {
1424         return noteOp(strOpToOp(op), uid, packageName);
1425     }
1426 
1427     /**
1428      * Like {@link #noteOp} but instead of throwing a {@link SecurityException} it
1429      * returns {@link #MODE_ERRORED}.
1430      */
noteOpNoThrow(String op, int uid, String packageName)1431     public int noteOpNoThrow(String op, int uid, String packageName) {
1432         return noteOpNoThrow(strOpToOp(op), uid, packageName);
1433     }
1434 
1435     /**
1436      * Make note of an application performing an operation on behalf of another
1437      * application when handling an IPC. Note that you must pass the package name
1438      * of the application that is being proxied while its UID will be inferred from
1439      * the IPC state; this function will verify that the calling uid and proxied
1440      * package name match, and if not, return {@link #MODE_IGNORED}. If this call
1441      * succeeds, the last execution time of the operation for the proxied app and
1442      * your app will be updated to the current time.
1443      * @param op The operation to note.  One of the OPSTR_* constants.
1444      * @param proxiedPackageName The name of the application calling into the proxy application.
1445      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1446      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1447      * causing the app to crash).
1448      * @throws SecurityException If the app has been configured to crash on this op.
1449      */
noteProxyOp(String op, String proxiedPackageName)1450     public int noteProxyOp(String op, String proxiedPackageName) {
1451         return noteProxyOp(strOpToOp(op), proxiedPackageName);
1452     }
1453 
1454     /**
1455      * Like {@link #noteProxyOp(String, String)} but instead
1456      * of throwing a {@link SecurityException} it returns {@link #MODE_ERRORED}.
1457      */
noteProxyOpNoThrow(String op, String proxiedPackageName)1458     public int noteProxyOpNoThrow(String op, String proxiedPackageName) {
1459         return noteProxyOpNoThrow(strOpToOp(op), proxiedPackageName);
1460     }
1461 
1462     /**
1463      * Report that an application has started executing a long-running operation.  Note that you
1464      * must pass in both the uid and name of the application to be checked; this function will
1465      * verify that these two match, and if not, return {@link #MODE_IGNORED}.  If this call
1466      * succeeds, the last execution time of the operation for this app will be updated to
1467      * the current time and the operation will be marked as "running".  In this case you must
1468      * later call {@link #finishOp(String, int, String)} to report when the application is no
1469      * longer performing the operation.
1470      * @param op The operation to start.  One of the OPSTR_* constants.
1471      * @param uid The user id of the application attempting to perform the operation.
1472      * @param packageName The name of the application attempting to perform the operation.
1473      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1474      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1475      * causing the app to crash).
1476      * @throws SecurityException If the app has been configured to crash on this op.
1477      */
startOp(String op, int uid, String packageName)1478     public int startOp(String op, int uid, String packageName) {
1479         return startOp(strOpToOp(op), uid, packageName);
1480     }
1481 
1482     /**
1483      * Like {@link #startOp} but instead of throwing a {@link SecurityException} it
1484      * returns {@link #MODE_ERRORED}.
1485      */
startOpNoThrow(String op, int uid, String packageName)1486     public int startOpNoThrow(String op, int uid, String packageName) {
1487         return startOpNoThrow(strOpToOp(op), uid, packageName);
1488     }
1489 
1490     /**
1491      * Report that an application is no longer performing an operation that had previously
1492      * been started with {@link #startOp(String, int, String)}.  There is no validation of input
1493      * or result; the parameters supplied here must be the exact same ones previously passed
1494      * in when starting the operation.
1495      */
finishOp(String op, int uid, String packageName)1496     public void finishOp(String op, int uid, String packageName) {
1497         finishOp(strOpToOp(op), uid, packageName);
1498     }
1499 
1500     /**
1501      * Do a quick check for whether an application might be able to perform an operation.
1502      * This is <em>not</em> a security check; you must use {@link #noteOp(int, int, String)}
1503      * or {@link #startOp(int, int, String)} for your actual security checks, which also
1504      * ensure that the given uid and package name are consistent.  This function can just be
1505      * used for a quick check to see if an operation has been disabled for the application,
1506      * as an early reject of some work.  This does not modify the time stamp or other data
1507      * about the operation.
1508      * @param op The operation to check.  One of the OP_* constants.
1509      * @param uid The user id of the application attempting to perform the operation.
1510      * @param packageName The name of the application attempting to perform the operation.
1511      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1512      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1513      * causing the app to crash).
1514      * @throws SecurityException If the app has been configured to crash on this op.
1515      * @hide
1516      */
checkOp(int op, int uid, String packageName)1517     public int checkOp(int op, int uid, String packageName) {
1518         try {
1519             int mode = mService.checkOperation(op, uid, packageName);
1520             if (mode == MODE_ERRORED) {
1521                 throw new SecurityException(buildSecurityExceptionMsg(op, uid, packageName));
1522             }
1523             return mode;
1524         } catch (RemoteException e) {
1525         }
1526         return MODE_IGNORED;
1527     }
1528 
1529     /**
1530      * Like {@link #checkOp} but instead of throwing a {@link SecurityException} it
1531      * returns {@link #MODE_ERRORED}.
1532      * @hide
1533      */
checkOpNoThrow(int op, int uid, String packageName)1534     public int checkOpNoThrow(int op, int uid, String packageName) {
1535         try {
1536             return mService.checkOperation(op, uid, packageName);
1537         } catch (RemoteException e) {
1538         }
1539         return MODE_ERRORED;
1540     }
1541 
1542     /**
1543      * Do a quick check to validate if a package name belongs to a UID.
1544      *
1545      * @throws SecurityException if the package name doesn't belong to the given
1546      *             UID, or if ownership cannot be verified.
1547      */
checkPackage(int uid, String packageName)1548     public void checkPackage(int uid, String packageName) {
1549         try {
1550             if (mService.checkPackage(uid, packageName) != MODE_ALLOWED) {
1551                 throw new SecurityException(
1552                         "Package " + packageName + " does not belong to " + uid);
1553             }
1554         } catch (RemoteException e) {
1555             throw new SecurityException("Unable to verify package ownership", e);
1556         }
1557     }
1558 
1559     /**
1560      * Like {@link #checkOp} but at a stream-level for audio operations.
1561      * @hide
1562      */
checkAudioOp(int op, int stream, int uid, String packageName)1563     public int checkAudioOp(int op, int stream, int uid, String packageName) {
1564         try {
1565             final int mode = mService.checkAudioOperation(op, stream, uid, packageName);
1566             if (mode == MODE_ERRORED) {
1567                 throw new SecurityException(buildSecurityExceptionMsg(op, uid, packageName));
1568             }
1569             return mode;
1570         } catch (RemoteException e) {
1571         }
1572         return MODE_IGNORED;
1573     }
1574 
1575     /**
1576      * Like {@link #checkAudioOp} but instead of throwing a {@link SecurityException} it
1577      * returns {@link #MODE_ERRORED}.
1578      * @hide
1579      */
checkAudioOpNoThrow(int op, int stream, int uid, String packageName)1580     public int checkAudioOpNoThrow(int op, int stream, int uid, String packageName) {
1581         try {
1582             return mService.checkAudioOperation(op, stream, uid, packageName);
1583         } catch (RemoteException e) {
1584         }
1585         return MODE_ERRORED;
1586     }
1587 
1588     /**
1589      * Make note of an application performing an operation.  Note that you must pass
1590      * in both the uid and name of the application to be checked; this function will verify
1591      * that these two match, and if not, return {@link #MODE_IGNORED}.  If this call
1592      * succeeds, the last execution time of the operation for this app will be updated to
1593      * the current time.
1594      * @param op The operation to note.  One of the OP_* constants.
1595      * @param uid The user id of the application attempting to perform the operation.
1596      * @param packageName The name of the application attempting to perform the operation.
1597      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1598      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1599      * causing the app to crash).
1600      * @throws SecurityException If the app has been configured to crash on this op.
1601      * @hide
1602      */
noteOp(int op, int uid, String packageName)1603     public int noteOp(int op, int uid, String packageName) {
1604         try {
1605             int mode = mService.noteOperation(op, uid, packageName);
1606             if (mode == MODE_ERRORED) {
1607                 throw new SecurityException(buildSecurityExceptionMsg(op, uid, packageName));
1608             }
1609             return mode;
1610         } catch (RemoteException e) {
1611         }
1612         return MODE_IGNORED;
1613     }
1614 
1615     /**
1616      * Make note of an application performing an operation on behalf of another
1617      * application when handling an IPC. Note that you must pass the package name
1618      * of the application that is being proxied while its UID will be inferred from
1619      * the IPC state; this function will verify that the calling uid and proxied
1620      * package name match, and if not, return {@link #MODE_IGNORED}. If this call
1621      * succeeds, the last execution time of the operation for the proxied app and
1622      * your app will be updated to the current time.
1623      * @param op The operation to note. One of the OPSTR_* constants.
1624      * @param proxiedPackageName The name of the application calling into the proxy application.
1625      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1626      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1627      * causing the app to crash).
1628      * @throws SecurityException If the proxy or proxied app has been configured to
1629      * crash on this op.
1630      *
1631      * @hide
1632      */
noteProxyOp(int op, String proxiedPackageName)1633     public int noteProxyOp(int op, String proxiedPackageName) {
1634         int mode = noteProxyOpNoThrow(op, proxiedPackageName);
1635         if (mode == MODE_ERRORED) {
1636             throw new SecurityException("Proxy package " + mContext.getOpPackageName()
1637                     + " from uid " + Process.myUid() + " or calling package "
1638                     + proxiedPackageName + " from uid " + Binder.getCallingUid()
1639                     + " not allowed to perform " + sOpNames[op]);
1640         }
1641         return mode;
1642     }
1643 
1644     /**
1645      * Like {@link #noteProxyOp(int, String)} but instead
1646      * of throwing a {@link SecurityException} it returns {@link #MODE_ERRORED}.
1647      * @hide
1648      */
noteProxyOpNoThrow(int op, String proxiedPackageName)1649     public int noteProxyOpNoThrow(int op, String proxiedPackageName) {
1650         try {
1651             return mService.noteProxyOperation(op, mContext.getOpPackageName(),
1652                     Binder.getCallingUid(), proxiedPackageName);
1653         } catch (RemoteException e) {
1654         }
1655         return MODE_ERRORED;
1656     }
1657 
1658     /**
1659      * Like {@link #noteOp} but instead of throwing a {@link SecurityException} it
1660      * returns {@link #MODE_ERRORED}.
1661      * @hide
1662      */
noteOpNoThrow(int op, int uid, String packageName)1663     public int noteOpNoThrow(int op, int uid, String packageName) {
1664         try {
1665             return mService.noteOperation(op, uid, packageName);
1666         } catch (RemoteException e) {
1667         }
1668         return MODE_ERRORED;
1669     }
1670 
1671     /** @hide */
noteOp(int op)1672     public int noteOp(int op) {
1673         return noteOp(op, Process.myUid(), mContext.getOpPackageName());
1674     }
1675 
1676     /** @hide */
getToken(IAppOpsService service)1677     public static IBinder getToken(IAppOpsService service) {
1678         synchronized (AppOpsManager.class) {
1679             if (sToken != null) {
1680                 return sToken;
1681             }
1682             try {
1683                 sToken = service.getToken(new Binder());
1684             } catch (RemoteException e) {
1685                 // System is dead, whatevs.
1686             }
1687             return sToken;
1688         }
1689     }
1690 
1691     /**
1692      * Report that an application has started executing a long-running operation.  Note that you
1693      * must pass in both the uid and name of the application to be checked; this function will
1694      * verify that these two match, and if not, return {@link #MODE_IGNORED}.  If this call
1695      * succeeds, the last execution time of the operation for this app will be updated to
1696      * the current time and the operation will be marked as "running".  In this case you must
1697      * later call {@link #finishOp(int, int, String)} to report when the application is no
1698      * longer performing the operation.
1699      * @param op The operation to start.  One of the OP_* constants.
1700      * @param uid The user id of the application attempting to perform the operation.
1701      * @param packageName The name of the application attempting to perform the operation.
1702      * @return Returns {@link #MODE_ALLOWED} if the operation is allowed, or
1703      * {@link #MODE_IGNORED} if it is not allowed and should be silently ignored (without
1704      * causing the app to crash).
1705      * @throws SecurityException If the app has been configured to crash on this op.
1706      * @hide
1707      */
startOp(int op, int uid, String packageName)1708     public int startOp(int op, int uid, String packageName) {
1709         try {
1710             int mode = mService.startOperation(getToken(mService), op, uid, packageName);
1711             if (mode == MODE_ERRORED) {
1712                 throw new SecurityException(buildSecurityExceptionMsg(op, uid, packageName));
1713             }
1714             return mode;
1715         } catch (RemoteException e) {
1716         }
1717         return MODE_IGNORED;
1718     }
1719 
1720     /**
1721      * Like {@link #startOp} but instead of throwing a {@link SecurityException} it
1722      * returns {@link #MODE_ERRORED}.
1723      * @hide
1724      */
startOpNoThrow(int op, int uid, String packageName)1725     public int startOpNoThrow(int op, int uid, String packageName) {
1726         try {
1727             return mService.startOperation(getToken(mService), op, uid, packageName);
1728         } catch (RemoteException e) {
1729         }
1730         return MODE_ERRORED;
1731     }
1732 
1733     /** @hide */
startOp(int op)1734     public int startOp(int op) {
1735         return startOp(op, Process.myUid(), mContext.getOpPackageName());
1736     }
1737 
1738     /**
1739      * Report that an application is no longer performing an operation that had previously
1740      * been started with {@link #startOp(int, int, String)}.  There is no validation of input
1741      * or result; the parameters supplied here must be the exact same ones previously passed
1742      * in when starting the operation.
1743      * @hide
1744      */
finishOp(int op, int uid, String packageName)1745     public void finishOp(int op, int uid, String packageName) {
1746         try {
1747             mService.finishOperation(getToken(mService), op, uid, packageName);
1748         } catch (RemoteException e) {
1749         }
1750     }
1751 
1752     /** @hide */
finishOp(int op)1753     public void finishOp(int op) {
1754         finishOp(op, Process.myUid(), mContext.getOpPackageName());
1755     }
1756 }
1757