diff --git a/cmds/statsd/src/atoms.proto b/cmds/statsd/src/atoms.proto index 751b3e43b9a54..6af038751acb7 100644 --- a/cmds/statsd/src/atoms.proto +++ b/cmds/statsd/src/atoms.proto @@ -292,6 +292,7 @@ message Atom { DebugFailingElapsedClock debug_failing_elapsed_clock = 10047; NumBiometricsEnrolled num_faces_enrolled = 10048; RoleHolder role_holder = 10049; + DangerousPermissionState dangerous_permission_state = 10050; } // DO NOT USE field numbers above 100,000 in AOSP. @@ -5404,3 +5405,20 @@ message ProcessStartTime { optional string hosting_name = 9; } +/** + * State of a dangerous permission requested by a package + */ +message DangerousPermissionState { + // Name of the permission + optional string permission_name = 1; + + // Uid of the package + optional int32 uid = 2 [(is_uid) = true]; + + // Package requesting the permission + optional string package_name = 3; + + // If the permission is granted to the uid + optional bool is_granted = 4; +} + diff --git a/cmds/statsd/src/external/StatsPullerManager.cpp b/cmds/statsd/src/external/StatsPullerManager.cpp index 6f3eeaa717033..c69384c7077f5 100644 --- a/cmds/statsd/src/external/StatsPullerManager.cpp +++ b/cmds/statsd/src/external/StatsPullerManager.cpp @@ -223,6 +223,9 @@ const std::map StatsPullerManager::kAllPullAtomInfo = { // RoleHolder. {android::util::ROLE_HOLDER, {.puller = new StatsCompanionServicePuller(android::util::ROLE_HOLDER)}}, + // PermissionState. + {android::util::DANGEROUS_PERMISSION_STATE, + {.puller = new StatsCompanionServicePuller(android::util::DANGEROUS_PERMISSION_STATE)}}, }; StatsPullerManager::StatsPullerManager() : mNextPullTimeNs(NO_ALARM_UPDATE) { diff --git a/services/core/java/com/android/server/stats/StatsCompanionService.java b/services/core/java/com/android/server/stats/StatsCompanionService.java index 2378c57ff8c96..48e64338262fe 100644 --- a/services/core/java/com/android/server/stats/StatsCompanionService.java +++ b/services/core/java/com/android/server/stats/StatsCompanionService.java @@ -15,6 +15,8 @@ */ package com.android.server.stats; +import static android.content.pm.PackageInfo.REQUESTED_PERMISSION_GRANTED; +import static android.content.pm.PermissionInfo.PROTECTION_DANGEROUS; import static android.os.Process.getPidsForCommands; import static android.os.Process.getUidForPid; @@ -41,6 +43,7 @@ import android.content.IntentFilter; import android.content.IntentSender; import android.content.pm.PackageInfo; import android.content.pm.PackageManager; +import android.content.pm.PermissionInfo; import android.content.pm.UserInfo; import android.hardware.fingerprint.FingerprintManager; import android.net.ConnectivityManager; @@ -1793,6 +1796,65 @@ public class StatsCompanionService extends IStatsCompanionService.Stub { pulledData.add(e); } + private void pullDangerousPermissionState(long elapsedNanos, final long wallClockNanos, + List pulledData) { + long token = Binder.clearCallingIdentity(); + try { + PackageManager pm = mContext.getPackageManager(); + + List users = mContext.getSystemService(UserManager.class).getUsers(); + + int numUsers = users.size(); + for (int userNum = 0; userNum < numUsers; userNum++) { + UserHandle user = users.get(userNum).getUserHandle(); + + List pkgs = pm.getInstalledPackagesAsUser( + PackageManager.GET_PERMISSIONS, user.getIdentifier()); + + int numPkgs = pkgs.size(); + for (int pkgNum = 0; pkgNum < numPkgs; pkgNum++) { + PackageInfo pkg = pkgs.get(pkgNum); + + if (pkg.requestedPermissions == null) { + continue; + } + + int numPerms = pkg.requestedPermissions.length; + for (int permNum = 0; permNum < numPerms; permNum++) { + String permName = pkg.requestedPermissions[permNum]; + + PermissionInfo permissionInfo; + try { + permissionInfo = pm.getPermissionInfo(permName, 0); + } catch (PackageManager.NameNotFoundException ignored) { + continue; + } + + if (permissionInfo.getProtection() != PROTECTION_DANGEROUS) { + continue; + } + + StatsLogEventWrapper e = new StatsLogEventWrapper( + StatsLog.DANGEROUS_PERMISSION_STATE, elapsedNanos, wallClockNanos); + + e.writeString(permName); + e.writeInt(pkg.applicationInfo.uid); + e.writeString(pkg.packageName); + + e.writeBoolean((pkg.requestedPermissionsFlags[permNum] + & REQUESTED_PERMISSION_GRANTED) != 0); + + pulledData.add(e); + } + } + } + } catch (Throwable t) { + Log.e(TAG, "Could not read permissions", t); + } finally { + Binder.restoreCallingIdentity(token); + } + } + /** * Add a RoleHolder atom for each package that holds a role. * @@ -2025,6 +2087,10 @@ public class StatsCompanionService extends IStatsCompanionService.Stub { pullRoleHolders(elapsedNanos, wallClockNanos, ret); break; } + case StatsLog.DANGEROUS_PERMISSION_STATE: { + pullDangerousPermissionState(elapsedNanos, wallClockNanos, ret); + break; + } default: Slog.w(TAG, "No such tagId data as " + tagId); return null;