@@ -403,6 +403,7 @@ public class NotificationManagerService extends SystemService {
403403 private IActivityManager mAm ;
404404 private ActivityTaskManagerInternal mAtm ;
405405 private ActivityManager mActivityManager ;
406+ private ActivityManagerInternal mAmi ;
406407 private IPackageManager mPackageManager ;
407408 private PackageManager mPackageManagerClient ;
408409 AudioManager mAudioManager ;
@@ -1876,7 +1877,7 @@ void init(WorkerHandler handler, RankingHandler rankingHandler,
18761877 DevicePolicyManagerInternal dpm , IUriGrantsManager ugm ,
18771878 UriGrantsManagerInternal ugmInternal , AppOpsManager appOps , UserManager userManager ,
18781879 NotificationHistoryManager historyManager , StatsManager statsManager ,
1879- TelephonyManager telephonyManager ) {
1880+ TelephonyManager telephonyManager , ActivityManagerInternal ami ) {
18801881 mHandler = handler ;
18811882 Resources resources = getContext ().getResources ();
18821883 mMaxPackageEnqueueRate = Settings .Global .getFloat (getContext ().getContentResolver (),
@@ -1897,6 +1898,7 @@ void init(WorkerHandler handler, RankingHandler rankingHandler,
18971898 mAlarmManager = (AlarmManager ) getContext ().getSystemService (Context .ALARM_SERVICE );
18981899 mCompanionManager = companionManager ;
18991900 mActivityManager = activityManager ;
1901+ mAmi = ami ;
19001902 mDeviceIdleController = IDeviceIdleController .Stub .asInterface (
19011903 ServiceManager .getService (Context .DEVICE_IDLE_CONTROLLER ));
19021904 mDpm = dpm ;
@@ -2119,7 +2121,8 @@ null, snoozeHelper, new NotificationUsageStats(getContext()),
21192121 new NotificationHistoryManager (getContext (), handler ),
21202122 mStatsManager = (StatsManager ) getContext ().getSystemService (
21212123 Context .STATS_MANAGER ),
2122- getContext ().getSystemService (TelephonyManager .class ));
2124+ getContext ().getSystemService (TelephonyManager .class ),
2125+ LocalServices .getService (ActivityManagerInternal .class ));
21232126
21242127 // register for various Intents
21252128 IntentFilter filter = new IntentFilter ();
@@ -3405,15 +3408,30 @@ public NotificationChannel getNotificationChannelForPackage(String pkg, int uid,
34053408 pkg , uid , channelId , conversationId , true , includeDeleted );
34063409 }
34073410
3411+ // Returns 'true' if the given channel has a notification associated
3412+ // with an active foreground service.
3413+ private void enforceDeletingChannelHasNoFgService (String pkg , int userId ,
3414+ String channelId ) {
3415+ if (mAmi .hasForegroundServiceNotification (pkg , userId , channelId )) {
3416+ Slog .w (TAG , "Package u" + userId + "/" + pkg
3417+ + " may not delete notification channel '"
3418+ + channelId + "' with fg service" );
3419+ throw new SecurityException ("Not allowed to delete channel " + channelId
3420+ + " with a foreground service" );
3421+ }
3422+ }
3423+
34083424 @ Override
34093425 public void deleteNotificationChannel (String pkg , String channelId ) {
34103426 checkCallerIsSystemOrSameApp (pkg );
34113427 final int callingUid = Binder .getCallingUid ();
3428+ final int callingUser = UserHandle .getUserId (callingUid );
34123429 if (NotificationChannel .DEFAULT_CHANNEL_ID .equals (channelId )) {
34133430 throw new IllegalArgumentException ("Cannot delete default channel" );
34143431 }
3432+ enforceDeletingChannelHasNoFgService (pkg , callingUser , channelId );
34153433 cancelAllNotificationsInt (MY_UID , MY_PID , pkg , channelId , 0 , 0 , true ,
3416- UserHandle . getUserId ( callingUid ) , REASON_CHANNEL_BANNED , null );
3434+ callingUser , REASON_CHANNEL_BANNED , null );
34173435 mPreferencesHelper .deleteNotificationChannel (pkg , callingUid , channelId );
34183436 mListeners .notifyNotificationChannelChanged (pkg ,
34193437 UserHandle .getUserHandleForUid (callingUid ),
@@ -3426,19 +3444,23 @@ public void deleteNotificationChannel(String pkg, String channelId) {
34263444 public void deleteConversationNotificationChannels (String pkg , int uid ,
34273445 String conversationId ) {
34283446 checkCallerIsSystem ();
3429- final int callingUid = Binder .getCallingUid ();
34303447 List <NotificationChannel > channels =
34313448 mPreferencesHelper .getNotificationChannelsByConversationId (
34323449 pkg , uid , conversationId );
34333450 if (!channels .isEmpty ()) {
3451+ // Preflight for fg service notifications in these channels: do nothing
3452+ // unless they're all eligible
3453+ final int appUserId = UserHandle .getUserId (uid );
34343454 for (NotificationChannel nc : channels ) {
3455+ final String channelId = nc .getId ();
3456+ mAmi .stopForegroundServicesForChannel (pkg , appUserId , channelId );
34353457 cancelAllNotificationsInt (MY_UID , MY_PID , pkg , nc .getId (), 0 , 0 , true ,
3436- UserHandle . getUserId ( callingUid ) , REASON_CHANNEL_BANNED , null );
3437- mPreferencesHelper .deleteNotificationChannel (pkg , callingUid , nc . getId () );
3458+ appUserId , REASON_CHANNEL_BANNED , null );
3459+ mPreferencesHelper .deleteNotificationChannel (pkg , uid , channelId );
34383460 mListeners .notifyNotificationChannelChanged (pkg ,
3439- UserHandle .getUserHandleForUid (callingUid ),
3461+ UserHandle .getUserHandleForUid (uid ),
34403462 mPreferencesHelper .getNotificationChannel (
3441- pkg , callingUid , nc . getId () , true ),
3463+ pkg , uid , channelId , true ),
34423464 NOTIFICATION_CHANNEL_OR_GROUP_DELETED );
34433465 }
34443466 handleSavePolicyFile ();
@@ -3469,13 +3491,20 @@ public void deleteNotificationChannelGroup(String pkg, String groupId) {
34693491 NotificationChannelGroup groupToDelete =
34703492 mPreferencesHelper .getNotificationChannelGroup (groupId , pkg , callingUid );
34713493 if (groupToDelete != null ) {
3494+ // Preflight for allowability
3495+ final int userId = UserHandle .getUserId (callingUid );
3496+ List <NotificationChannel > groupChannels = groupToDelete .getChannels ();
3497+ for (int i = 0 ; i < groupChannels .size (); i ++) {
3498+ enforceDeletingChannelHasNoFgService (pkg , userId ,
3499+ groupChannels .get (i ).getId ());
3500+ }
34723501 List <NotificationChannel > deletedChannels =
34733502 mPreferencesHelper .deleteNotificationChannelGroup (pkg , callingUid , groupId );
34743503 for (int i = 0 ; i < deletedChannels .size (); i ++) {
34753504 final NotificationChannel deletedChannel = deletedChannels .get (i );
34763505 cancelAllNotificationsInt (MY_UID , MY_PID , pkg , deletedChannel .getId (), 0 , 0 ,
34773506 true ,
3478- UserHandle . getUserId ( Binder . getCallingUid ()) , REASON_CHANNEL_BANNED ,
3507+ userId , REASON_CHANNEL_BANNED ,
34793508 null );
34803509 mListeners .notifyNotificationChannelChanged (pkg ,
34813510 UserHandle .getUserHandleForUid (callingUid ),
0 commit comments