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 #include <binder/AppOpsManager.h>
18 #include <binder/IPCThreadState.h>
19 #include <binder/IServiceManager.h>
20 #include <binder/PermissionCache.h>
21 #include <private/android_filesystem_config.h>
22 #include "ServiceUtilities.h"
23 
24 /* When performing permission checks we do not use permission cache for
25  * runtime permissions (protection level dangerous) as they may change at
26  * runtime. All other permissions (protection level normal and dangerous)
27  * can be cached as they never change. Of course all permission checked
28  * here are platform defined.
29  */
30 
31 namespace android {
32 
33 // Not valid until initialized by AudioFlinger constructor.  It would have to be
34 // re-initialized if the process containing AudioFlinger service forks (which it doesn't).
35 pid_t getpid_cached;
36 
recordingAllowed(const String16 & opPackageName)37 bool recordingAllowed(const String16& opPackageName) {
38     // Note: We are getting the UID from the calling IPC thread state because all
39     // clients that perform recording create AudioRecord in their own processes
40     // and the system does not create AudioRecord objects on behalf of apps. This
41     // differs from playback where in some situations the system recreates AudioTrack
42     // instances associated with a client's MediaPlayer on behalf of this client.
43     // In the latter case we have to store the client UID and pass in along for
44     // security checks.
45 
46     if (getpid_cached == IPCThreadState::self()->getCallingPid()) return true;
47     static const String16 sRecordAudio("android.permission.RECORD_AUDIO");
48 
49     // IMPORTANT: Don't use PermissionCache - a runtime permission and may change.
50     const bool ok = checkCallingPermission(sRecordAudio);
51     if (!ok) {
52         ALOGE("Request requires android.permission.RECORD_AUDIO");
53         return false;
54     }
55 
56     const uid_t uid = IPCThreadState::self()->getCallingUid();
57 
58     // To permit command-line native tests
59     if (uid == AID_ROOT) return true;
60 
61     String16 checkedOpPackageName = opPackageName;
62 
63     // In some cases the calling code has no access to the package it runs under.
64     // For example, code using the wilhelm framework's OpenSL-ES APIs. In this
65     // case we will get the packages for the calling UID and pick the first one
66     // for attributing the app op. This will work correctly for runtime permissions
67     // as for legacy apps we will toggle the app op for all packages in the UID.
68     // The caveat is that the operation may be attributed to the wrong package and
69     // stats based on app ops may be slightly off.
70     if (checkedOpPackageName.size() <= 0) {
71         sp<IServiceManager> sm = defaultServiceManager();
72         sp<IBinder> binder = sm->getService(String16("permission"));
73         if (binder == 0) {
74             ALOGE("Cannot get permission service");
75             return false;
76         }
77 
78         sp<IPermissionController> permCtrl = interface_cast<IPermissionController>(binder);
79         Vector<String16> packages;
80 
81         permCtrl->getPackagesForUid(uid, packages);
82 
83         if (packages.isEmpty()) {
84             ALOGE("No packages for calling UID");
85             return false;
86         }
87         checkedOpPackageName = packages[0];
88     }
89 
90     AppOpsManager appOps;
91     if (appOps.noteOp(AppOpsManager::OP_RECORD_AUDIO, uid, checkedOpPackageName)
92             != AppOpsManager::MODE_ALLOWED) {
93         ALOGE("Request denied by app op OP_RECORD_AUDIO");
94         return false;
95     }
96 
97     return true;
98 }
99 
captureAudioOutputAllowed()100 bool captureAudioOutputAllowed() {
101     if (getpid_cached == IPCThreadState::self()->getCallingPid()) return true;
102     static const String16 sCaptureAudioOutput("android.permission.CAPTURE_AUDIO_OUTPUT");
103     // IMPORTANT: Use PermissionCache - not a runtime permission and may not change.
104     bool ok = PermissionCache::checkCallingPermission(sCaptureAudioOutput);
105     if (!ok) ALOGE("Request requires android.permission.CAPTURE_AUDIO_OUTPUT");
106     return ok;
107 }
108 
captureHotwordAllowed()109 bool captureHotwordAllowed() {
110     static const String16 sCaptureHotwordAllowed("android.permission.CAPTURE_AUDIO_HOTWORD");
111     // IMPORTANT: Use PermissionCache - not a runtime permission and may not change.
112     bool ok = PermissionCache::checkCallingPermission(sCaptureHotwordAllowed);
113     if (!ok) ALOGE("android.permission.CAPTURE_AUDIO_HOTWORD");
114     return ok;
115 }
116 
settingsAllowed()117 bool settingsAllowed() {
118     if (getpid_cached == IPCThreadState::self()->getCallingPid()) return true;
119     static const String16 sAudioSettings("android.permission.MODIFY_AUDIO_SETTINGS");
120     // IMPORTANT: Use PermissionCache - not a runtime permission and may not change.
121     bool ok = PermissionCache::checkCallingPermission(sAudioSettings);
122     if (!ok) ALOGE("Request requires android.permission.MODIFY_AUDIO_SETTINGS");
123     return ok;
124 }
125 
modifyAudioRoutingAllowed()126 bool modifyAudioRoutingAllowed() {
127     static const String16 sModifyAudioRoutingAllowed("android.permission.MODIFY_AUDIO_ROUTING");
128     // IMPORTANT: Use PermissionCache - not a runtime permission and may not change.
129     bool ok = PermissionCache::checkCallingPermission(sModifyAudioRoutingAllowed);
130     if (!ok) ALOGE("android.permission.MODIFY_AUDIO_ROUTING");
131     return ok;
132 }
133 
dumpAllowed()134 bool dumpAllowed() {
135     // don't optimize for same pid, since mediaserver never dumps itself
136     static const String16 sDump("android.permission.DUMP");
137     // IMPORTANT: Use PermissionCache - not a runtime permission and may not change.
138     bool ok = PermissionCache::checkCallingPermission(sDump);
139     // convention is for caller to dump an error message to fd instead of logging here
140     //if (!ok) ALOGE("Request requires android.permission.DUMP");
141     return ok;
142 }
143 
144 } // namespace android
145