Don't parse 3p recognizer metadata in safe mode Malicious apps could put large xml recognition service metadata file that could lead to crash the system. Making sure that we don't parse such metadata for 3p apps in safe mode as they are not launchable in safe mode anyway. Bug: 430284594 Test: manual by verifying device boots in safe mode normally Flag: EXEMPT CVE_FIX (cherry picked from commit a81b51b6a6e0b7fd6a417926b6abd8a162110060) Cherrypick-From: https://googleplex-android-review.googlesource.com/q/commit:a7bfe4f0a7fc994a626580a502a069b2a7326c40 Merged-In: I52435ca8da633a73fc63e07c6fea3ec9cd8cd986 Change-Id: I52435ca8da633a73fc63e07c6fea3ec9cd8cd986
diff --git a/services/voiceinteraction/java/com/android/server/voiceinteraction/RecognitionServiceInfo.java b/services/voiceinteraction/java/com/android/server/voiceinteraction/RecognitionServiceInfo.java index 05d4b93..376ba57 100644 --- a/services/voiceinteraction/java/com/android/server/voiceinteraction/RecognitionServiceInfo.java +++ b/services/voiceinteraction/java/com/android/server/voiceinteraction/RecognitionServiceInfo.java
@@ -20,6 +20,7 @@ import android.annotation.UserIdInt; import android.content.Context; import android.content.Intent; +import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; import android.content.pm.ResolveInfo; import android.content.pm.ServiceInfo; @@ -57,7 +58,7 @@ * Queries the valid recognition services available for the user. */ static List<RecognitionServiceInfo> getAvailableServices( - @NonNull Context context, @UserIdInt int user) { + @NonNull Context context, @UserIdInt int user, boolean isSafeMode) { List<RecognitionServiceInfo> services = new ArrayList<>(); List<ResolveInfo> resolveInfos = @@ -67,6 +68,19 @@ | PackageManager.MATCH_DIRECT_BOOT_UNAWARE, user); for (ResolveInfo resolveInfo : resolveInfos) { + if (isSafeMode + && (resolveInfo.serviceInfo.applicationInfo.flags + & ApplicationInfo.FLAG_SYSTEM) == 0) { + // If in safe mode, we don't parse metadata of 3p recognition services and assume + // that they are selectable as default, but they still won't be auto selected as + // we only allow preinstalled recognizers to be auto selected + // This is mainly to guard against malicious 3p apps updating their metadata + // causing boot issues if the metadata loading is causing OOM + services.add( + new RecognitionServiceInfo(resolveInfo.serviceInfo, + /*selectableAsDefault*/ true, /*parseError*/ "")); + continue; + } RecognitionServiceInfo service = parseInfo(context.getPackageManager(), resolveInfo.serviceInfo); if (!TextUtils.isEmpty(service.mParseError)) {
diff --git a/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionManagerService.java b/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionManagerService.java index 1497447..e2847f3 100644 --- a/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionManagerService.java +++ b/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionManagerService.java
@@ -818,7 +818,10 @@ | PackageManager.MATCH_DIRECT_BOOT_UNAWARE | PackageManager.GET_META_DATA, userHandle); - if (recognizerInfo != null) { + // If in safe mode, we don't parse metadata of already set recognition service + // This is mainly to guard against malicious 3p apps updating their metadata + // causing boot issues if the metadata loading is causing OOM + if (recognizerInfo != null && !mSafeMode) { RecognitionServiceInfo rsi = RecognitionServiceInfo.parseInfo( mContext.getPackageManager(), recognizerInfo); @@ -1101,7 +1104,7 @@ } List<RecognitionServiceInfo> available = - RecognitionServiceInfo.getAvailableServices(mContext, userHandle); + RecognitionServiceInfo.getAvailableServices(mContext, userHandle, mSafeMode); if (available.size() == 0) { Slog.w(TAG, "no available voice recognition services found for user " + userHandle); return null;