Loading services/core/java/com/android/server/notification/ZenModeHelper.java +86 −64 Original line number Diff line number Diff line Loading @@ -75,6 +75,7 @@ import android.util.StatsEvent; import android.util.proto.ProtoOutputStream; import com.android.internal.R; import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.config.sysui.SystemUiSystemPropertiesFlags; import com.android.internal.logging.MetricsLogger; Loading Loading @@ -108,30 +109,34 @@ public class ZenModeHelper { static final int RULE_LIMIT_PER_PACKAGE = 100; // pkg|userId => uid protected final ArrayMap<String, Integer> mRulesUidCache = new ArrayMap<>(); @VisibleForTesting protected final ArrayMap<String, Integer> mRulesUidCache = new ArrayMap<>(); private final Context mContext; private final H mHandler; private final SettingsObserver mSettingsObserver; private final AppOpsManager mAppOps; @VisibleForTesting protected final NotificationManager mNotificationManager; private final NotificationManager mNotificationManager; private final SysUiStatsEvent.BuilderFactory mStatsEventBuilderFactory; @VisibleForTesting protected ZenModeConfig mDefaultConfig; private ZenModeConfig mDefaultConfig; private final ArrayList<Callback> mCallbacks = new ArrayList<Callback>(); private final ZenModeFiltering mFiltering; protected final RingerModeDelegate mRingerModeDelegate = new private final RingerModeDelegate mRingerModeDelegate = new RingerModeDelegate(); @VisibleForTesting protected final ZenModeConditions mConditions; Object mConfigsLock = new Object(); private final Object mConfigsArrayLock = new Object(); @GuardedBy("mConfigsArrayLock") @VisibleForTesting final SparseArray<ZenModeConfig> mConfigs = new SparseArray<>(); private final Metrics mMetrics = new Metrics(); private final ConditionProviders.Config mServiceConfig; private SystemUiSystemPropertiesFlags.FlagResolver mFlagResolver; @VisibleForTesting protected ZenModeEventLogger mZenModeEventLogger; private final SystemUiSystemPropertiesFlags.FlagResolver mFlagResolver; private final ZenModeEventLogger mZenModeEventLogger; @VisibleForTesting protected int mZenMode; @VisibleForTesting protected NotificationManager.Policy mConsolidatedPolicy; private int mUser = UserHandle.USER_SYSTEM; private final Object mConfigLock = new Object(); @GuardedBy("mConfigLock") @VisibleForTesting protected ZenModeConfig mConfig; @VisibleForTesting protected AudioManagerInternal mAudioManager; protected PackageManager mPm; Loading Loading @@ -159,7 +164,7 @@ public class ZenModeHelper { mDefaultConfig = readDefaultConfig(mContext.getResources()); updateDefaultAutomaticRuleNames(); mConfig = mDefaultConfig.copy(); synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.put(UserHandle.USER_SYSTEM, mConfig); } mConsolidatedPolicy = mConfig.toNotificationPolicy(); Loading @@ -186,7 +191,7 @@ public class ZenModeHelper { public boolean matchesCallFilter(UserHandle userHandle, Bundle extras, ValidateNotificationPeople validator, int contactsTimeoutMs, float timeoutAffinity, int callingUid) { synchronized (mConfig) { synchronized (mConfigLock) { return ZenModeFiltering.matchesCallFilter(mContext, mZenMode, mConsolidatedPolicy, userHandle, extras, validator, contactsTimeoutMs, timeoutAffinity, callingUid); Loading @@ -206,7 +211,7 @@ public class ZenModeHelper { } public boolean shouldIntercept(NotificationRecord record) { synchronized (mConfig) { synchronized (mConfigLock) { return mFiltering.shouldIntercept(mZenMode, mConsolidatedPolicy, record); } } Loading @@ -221,7 +226,7 @@ public class ZenModeHelper { public void initZenMode() { if (DEBUG) Log.d(TAG, "initZenMode"); synchronized (mConfig) { synchronized (mConfigLock) { // "update" config to itself, which will have no effect in the case where a config // was read in via XML, but will initialize zen mode if nothing was read in and the // config remains the default. Loading Loading @@ -250,7 +255,7 @@ public class ZenModeHelper { public void onUserRemoved(int user) { if (user < UserHandle.USER_SYSTEM) return; if (DEBUG) Log.d(TAG, "onUserRemoved u=" + user); synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.remove(user); } } Loading @@ -268,7 +273,7 @@ public class ZenModeHelper { mUser = user; if (DEBUG) Log.d(TAG, reason + " u=" + user); ZenModeConfig config = null; synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { if (mConfigs.get(user) != null) { config = mConfigs.get(user).copy(); } Loading @@ -278,7 +283,7 @@ public class ZenModeHelper { config = mDefaultConfig.copy(); config.user = user; } synchronized (mConfig) { synchronized (mConfigLock) { setConfigLocked(config, null, reason, Process.SYSTEM_UID, true); } cleanUpZenRules(); Loading Loading @@ -314,7 +319,7 @@ public class ZenModeHelper { public List<ZenRule> getZenRules() { List<ZenRule> rules = new ArrayList<>(); synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return rules; for (ZenRule rule : mConfig.automaticRules.values()) { if (canManageAutomaticZenRule(rule)) { Loading @@ -327,7 +332,7 @@ public class ZenModeHelper { public AutomaticZenRule getAutomaticZenRule(String id) { ZenRule rule; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return null; rule = mConfig.automaticRules.get(id); } Loading Loading @@ -364,7 +369,7 @@ public class ZenModeHelper { } ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) { throw new AndroidRuntimeException("Could not create rule"); } Loading @@ -387,7 +392,7 @@ public class ZenModeHelper { public boolean updateAutomaticZenRule(String ruleId, AutomaticZenRule automaticZenRule, String reason, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return false; if (DEBUG) { Log.d(TAG, "updateAutomaticZenRule zenRule=" + automaticZenRule Loading Loading @@ -419,7 +424,7 @@ public class ZenModeHelper { public boolean removeAutomaticZenRule(String id, String reason, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return false; newConfig = mConfig.copy(); ZenRule ruleToRemove = newConfig.automaticRules.get(id); Loading Loading @@ -450,7 +455,7 @@ public class ZenModeHelper { public boolean removeAutomaticZenRules(String packageName, String reason, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return false; newConfig = mConfig.copy(); for (int i = newConfig.automaticRules.size() - 1; i >= 0; i--) { Loading @@ -467,7 +472,7 @@ public class ZenModeHelper { public void setAutomaticZenRuleState(String id, Condition condition, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return; newConfig = mConfig.copy(); Loading @@ -481,7 +486,7 @@ public class ZenModeHelper { public void setAutomaticZenRuleState(Uri ruleDefinition, Condition condition, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return; newConfig = mConfig.copy(); Loading @@ -491,6 +496,7 @@ public class ZenModeHelper { } } @GuardedBy("mConfigLock") private void setAutomaticZenRuleStateLocked(ZenModeConfig config, List<ZenRule> rules, Condition condition, int callingUid, boolean fromSystemOrSystemUi) { if (rules == null || rules.isEmpty()) return; Loading Loading @@ -538,7 +544,7 @@ public class ZenModeHelper { return 0; } int count = 0; synchronized (mConfig) { synchronized (mConfigLock) { for (ZenRule rule : mConfig.automaticRules.values()) { if (cn.equals(rule.component) || cn.equals(rule.configurationActivity)) { count++; Loading @@ -555,7 +561,7 @@ public class ZenModeHelper { return 0; } int count = 0; synchronized (mConfig) { synchronized (mConfigLock) { for (ZenRule rule : mConfig.automaticRules.values()) { if (pkg.equals(rule.getPkg())) { count++; Loading Loading @@ -588,6 +594,7 @@ public class ZenModeHelper { protected void updateDefaultZenRules(int callingUid, boolean fromSystemOrSystemUi) { updateDefaultAutomaticRuleNames(); synchronized (mConfigLock) { for (ZenRule defaultRule : mDefaultConfig.automaticRules.values()) { ZenRule currRule = mConfig.automaticRules.get(defaultRule.id); // if default rule wasn't user-modified nor enabled, use localized name Loading @@ -595,8 +602,10 @@ public class ZenModeHelper { if (currRule != null && !currRule.modified && !currRule.enabled && !defaultRule.name.equals(currRule.name)) { if (canManageAutomaticZenRule(currRule)) { if (DEBUG) Slog.d(TAG, "Locale change - updating default zen rule name " if (DEBUG) { Slog.d(TAG, "Locale change - updating default zen rule name " + "from " + currRule.name + " to " + defaultRule.name); } // update default rule (if locale changed, name of rule will change) currRule.name = defaultRule.name; updateAutomaticZenRule(defaultRule.id, createAutomaticZenRule(currRule), Loading @@ -605,6 +614,7 @@ public class ZenModeHelper { } } } } private ServiceInfo getServiceInfo(ComponentName owner) { Intent queryIntent = new Intent(); Loading Loading @@ -686,7 +696,7 @@ public class ZenModeHelper { private void setManualZenMode(int zenMode, Uri conditionId, String reason, String caller, boolean setRingerMode, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return; if (!Global.isValidZenMode(zenMode)) return; if (DEBUG) Log.d(TAG, "setManualZenMode " + Global.zenModeToString(zenMode) Loading Loading @@ -715,7 +725,7 @@ public class ZenModeHelper { void dump(ProtoOutputStream proto) { proto.write(ZenModeProto.ZEN_MODE, mZenMode); synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig.manualRule != null) { mConfig.manualRule.dumpDebug(proto, ZenModeProto.ENABLED_ACTIVE_CONDITIONS); } Loading @@ -737,14 +747,14 @@ public class ZenModeHelper { pw.println(Global.zenModeToString(mZenMode)); pw.print(prefix); pw.println("mConsolidatedPolicy=" + mConsolidatedPolicy.toString()); synchronized(mConfigsLock) { synchronized (mConfigsArrayLock) { final int N = mConfigs.size(); for (int i = 0; i < N; i++) { dump(pw, prefix, "mConfigs[u=" + mConfigs.keyAt(i) + "]", mConfigs.valueAt(i)); } } pw.print(prefix); pw.print("mUser="); pw.println(mUser); synchronized (mConfig) { synchronized (mConfigLock) { dump(pw, prefix, "mConfig", mConfig); } Loading Loading @@ -833,7 +843,7 @@ public class ZenModeHelper { Settings.Secure.ZEN_SETTINGS_UPDATED, 1, userId); } if (DEBUG) Log.d(TAG, reason); synchronized (mConfig) { synchronized (mConfigLock) { setConfigLocked(config, null, reason, Process.SYSTEM_UID, true); } } Loading @@ -841,7 +851,7 @@ public class ZenModeHelper { public void writeXml(TypedXmlSerializer out, boolean forBackup, Integer version, int userId) throws IOException { synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { final int n = mConfigs.size(); for (int i = 0; i < n; i++) { if (forBackup && mConfigs.keyAt(i) != userId) { Loading @@ -856,8 +866,10 @@ public class ZenModeHelper { * @return user-specified default notification policy for priority only do not disturb */ public Policy getNotificationPolicy() { synchronized (mConfigLock) { return getNotificationPolicy(mConfig); } } private static Policy getNotificationPolicy(ZenModeConfig config) { return config == null ? null : config.toNotificationPolicy(); Loading @@ -867,8 +879,8 @@ public class ZenModeHelper { * Sets the global notification policy used for priority only do not disturb */ public void setNotificationPolicy(Policy policy, int callingUid, boolean fromSystemOrSystemUi) { synchronized (mConfigLock) { if (policy == null || mConfig == null) return; synchronized (mConfig) { final ZenModeConfig newConfig = mConfig.copy(); newConfig.applyNotificationPolicy(policy); setConfigLocked(newConfig, null, "setNotificationPolicy", callingUid, Loading @@ -881,7 +893,7 @@ public class ZenModeHelper { */ private void cleanUpZenRules() { long currentTime = System.currentTimeMillis(); synchronized (mConfig) { synchronized (mConfigLock) { final ZenModeConfig newConfig = mConfig.copy(); if (newConfig.automaticRules != null) { for (int i = newConfig.automaticRules.size() - 1; i >= 0; i--) { Loading @@ -906,7 +918,7 @@ public class ZenModeHelper { * @return a copy of the zen mode configuration */ public ZenModeConfig getConfig() { synchronized (mConfig) { synchronized (mConfigLock) { return mConfig.copy(); } } Loading @@ -918,7 +930,8 @@ public class ZenModeHelper { return mConsolidatedPolicy.copy(); } public boolean setConfigLocked(ZenModeConfig config, ComponentName triggeringComponent, @GuardedBy("mConfigLock") private boolean setConfigLocked(ZenModeConfig config, ComponentName triggeringComponent, String reason, int callingUid, boolean fromSystemOrSystemUi) { return setConfigLocked(config, reason, triggeringComponent, true /*setRingerMode*/, callingUid, fromSystemOrSystemUi); Loading @@ -926,11 +939,12 @@ public class ZenModeHelper { public void setConfig(ZenModeConfig config, ComponentName triggeringComponent, String reason, int callingUid, boolean fromSystemOrSystemUi) { synchronized (mConfig) { synchronized (mConfigLock) { setConfigLocked(config, triggeringComponent, reason, callingUid, fromSystemOrSystemUi); } } @GuardedBy("mConfigLock") private boolean setConfigLocked(ZenModeConfig config, String reason, ComponentName triggeringComponent, boolean setRingerMode, int callingUid, boolean fromSystemOrSystemUi) { Loading @@ -942,7 +956,7 @@ public class ZenModeHelper { } if (config.user != mUser) { // simply store away for background users synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.put(config.user, config); } if (DEBUG) Log.d(TAG, "setConfigLocked: store config for user " + config.user); Loading @@ -951,7 +965,7 @@ public class ZenModeHelper { // handle CPS backed conditions - danger! may modify config mConditions.evaluateConfig(config, null, false /*processSubscriptions*/); synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.put(config.user, config); } if (DEBUG) Log.d(TAG, "setConfigLocked reason=" + reason, new Throwable()); Loading Loading @@ -979,6 +993,7 @@ public class ZenModeHelper { * Carries out a config update (if needed) and (re-)evaluates the zen mode value afterwards. * If logging is enabled, will also request logging of the outcome of this change if needed. */ @GuardedBy("mConfigLock") private void updateConfigAndZenModeLocked(ZenModeConfig config, String reason, boolean setRingerMode, int callingUid, boolean fromSystemOrSystemUi) { final boolean logZenModeEvents = mFlagResolver.isEnabled( Loading @@ -993,7 +1008,7 @@ public class ZenModeHelper { } final String val = Integer.toString(config.hashCode()); Global.putString(mContext.getContentResolver(), Global.ZEN_MODE_CONFIG_ETAG, val); evaluateZenMode(reason, setRingerMode); evaluateZenModeLocked(reason, setRingerMode); // After all changes have occurred, log if requested if (logZenModeEvents) { ZenModeEventLogger.ZenModeInfo newInfo = new ZenModeEventLogger.ZenModeInfo( Loading Loading @@ -1025,7 +1040,8 @@ public class ZenModeHelper { } @VisibleForTesting protected void evaluateZenMode(String reason, boolean setRingerMode) { @GuardedBy("mConfigLock") protected void evaluateZenModeLocked(String reason, boolean setRingerMode) { if (DEBUG) Log.d(TAG, "evaluateZenMode"); if (mConfig == null) return; final int policyHashBefore = mConsolidatedPolicy == null ? 0 Loading Loading @@ -1056,8 +1072,8 @@ public class ZenModeHelper { } private int computeZenMode() { synchronized (mConfigLock) { if (mConfig == null) return Global.ZEN_MODE_OFF; synchronized (mConfig) { if (mConfig.manualRule != null) return mConfig.manualRule.zenMode; int zen = Global.ZEN_MODE_OFF; for (ZenRule automaticRule : mConfig.automaticRules.values()) { Loading Loading @@ -1094,8 +1110,8 @@ public class ZenModeHelper { } private void updateConsolidatedPolicy(String reason) { synchronized (mConfigLock) { if (mConfig == null) return; synchronized (mConfig) { ZenPolicy policy = new ZenPolicy(); if (mConfig.manualRule != null) { applyCustomPolicy(policy, mConfig.manualRule); Loading Loading @@ -1293,7 +1309,7 @@ public class ZenModeHelper { * Generate pulled atoms about do not disturb configurations. */ public void pullRules(List<StatsEvent> events) { synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { final int numConfigs = mConfigs.size(); for (int i = 0; i < numConfigs; i++) { final int user = mConfigs.keyAt(i); Loading @@ -1319,6 +1335,7 @@ public class ZenModeHelper { } } @GuardedBy("mConfigsArrayLock") private void ruleToProtoLocked(int user, ZenRule rule, boolean isManualRule, List<StatsEvent> events) { // Make the ID safe. Loading Loading @@ -1389,7 +1406,7 @@ public class ZenModeHelper { if (mZenMode == Global.ZEN_MODE_OFF || (mZenMode == Global.ZEN_MODE_IMPORTANT_INTERRUPTIONS && !ZenModeConfig.areAllPriorityOnlyRingerSoundsMuted(mConfig))) { && !areAllPriorityOnlyRingerSoundsMuted())) { // in priority only with ringer not muted, save ringer mode changes // in dnd off, save ringer mode changes setPreviousRingerModeSetting(ringerModeNew); Loading @@ -1410,8 +1427,7 @@ public class ZenModeHelper { && (mZenMode == Global.ZEN_MODE_NO_INTERRUPTIONS || mZenMode == Global.ZEN_MODE_ALARMS || (mZenMode == Global.ZEN_MODE_IMPORTANT_INTERRUPTIONS && ZenModeConfig.areAllPriorityOnlyRingerSoundsMuted( mConfig)))) { && areAllPriorityOnlyRingerSoundsMuted()))) { newZen = Global.ZEN_MODE_OFF; } else if (mZenMode != Global.ZEN_MODE_OFF) { ringerModeExternalOut = AudioManager.RINGER_MODE_SILENT; Loading @@ -1430,6 +1446,12 @@ public class ZenModeHelper { return ringerModeExternalOut; } private boolean areAllPriorityOnlyRingerSoundsMuted() { synchronized (mConfigLock) { return ZenModeConfig.areAllPriorityOnlyRingerSoundsMuted(mConfig); } } @Override public int onSetRingerModeExternal(int ringerModeOld, int ringerModeNew, String caller, int ringerModeInternal, VolumePolicy policy) { Loading Loading @@ -1633,7 +1655,7 @@ public class ZenModeHelper { private void emitRules() { final long now = SystemClock.elapsedRealtime(); final long since = (now - mRuleCountLogTime); synchronized (mConfig) { synchronized (mConfigLock) { int numZenRules = mConfig.automaticRules.size(); if (mNumZenRules != numZenRules || since > MINIMUM_LOG_PERIOD_MS) { Loading @@ -1651,7 +1673,7 @@ public class ZenModeHelper { private void emitDndType() { final long now = SystemClock.elapsedRealtime(); final long since = (now - mTypeLogTimeMs); synchronized (mConfig) { synchronized (mConfigLock) { boolean dndOn = mZenMode != Global.ZEN_MODE_OFF; int zenType = !dndOn ? DND_OFF : (mConfig.manualRule != null) ? DND_ON_MANUAL : DND_ON_AUTOMATIC; Loading services/tests/uiservicestests/src/com/android/server/notification/ZenModeHelperTest.java +4 −4 Original line number Diff line number Diff line Loading @@ -771,7 +771,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { mZenModeHelper.mConfig = null; // will evaluate config to zen mode off for (int i = 0; i < 3; i++) { // if zen doesn't change, zen should not reapply itself to the ringer mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); } verify(mAudioManager, never()).setRingerModeInternal(AudioManager.RINGER_MODE_NORMAL, mZenModeHelper.TAG); Loading @@ -798,7 +798,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { mZenModeHelper.mZenMode = ZEN_MODE_IMPORTANT_INTERRUPTIONS; for (int i = 0; i < 3; i++) { // if zen doesn't change, zen should not reapply itself to the ringer mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); } verify(mAudioManager, never()).setRingerModeInternal(AudioManager.RINGER_MODE_NORMAL, mZenModeHelper.TAG); Loading @@ -825,7 +825,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { mZenModeHelper.mZenMode = ZEN_MODE_IMPORTANT_INTERRUPTIONS; for (int i = 0; i < 3; i++) { // if zen doesn't change, zen should not reapply itself to the ringer mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); } verify(mAudioManager, never()).setRingerModeInternal(AudioManager.RINGER_MODE_NORMAL, mZenModeHelper.TAG); Loading Loading @@ -2269,7 +2269,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { // Artificially turn zen mode "on". Re-evaluating zen mode should cause it to turn back off // given that we don't have any zen rules active. mZenModeHelper.mZenMode = ZEN_MODE_IMPORTANT_INTERRUPTIONS; mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); // Check that the change actually took: zen mode should be off now assertEquals(Global.ZEN_MODE_OFF, mZenModeHelper.mZenMode); Loading Loading
services/core/java/com/android/server/notification/ZenModeHelper.java +86 −64 Original line number Diff line number Diff line Loading @@ -75,6 +75,7 @@ import android.util.StatsEvent; import android.util.proto.ProtoOutputStream; import com.android.internal.R; import com.android.internal.annotations.GuardedBy; import com.android.internal.annotations.VisibleForTesting; import com.android.internal.config.sysui.SystemUiSystemPropertiesFlags; import com.android.internal.logging.MetricsLogger; Loading Loading @@ -108,30 +109,34 @@ public class ZenModeHelper { static final int RULE_LIMIT_PER_PACKAGE = 100; // pkg|userId => uid protected final ArrayMap<String, Integer> mRulesUidCache = new ArrayMap<>(); @VisibleForTesting protected final ArrayMap<String, Integer> mRulesUidCache = new ArrayMap<>(); private final Context mContext; private final H mHandler; private final SettingsObserver mSettingsObserver; private final AppOpsManager mAppOps; @VisibleForTesting protected final NotificationManager mNotificationManager; private final NotificationManager mNotificationManager; private final SysUiStatsEvent.BuilderFactory mStatsEventBuilderFactory; @VisibleForTesting protected ZenModeConfig mDefaultConfig; private ZenModeConfig mDefaultConfig; private final ArrayList<Callback> mCallbacks = new ArrayList<Callback>(); private final ZenModeFiltering mFiltering; protected final RingerModeDelegate mRingerModeDelegate = new private final RingerModeDelegate mRingerModeDelegate = new RingerModeDelegate(); @VisibleForTesting protected final ZenModeConditions mConditions; Object mConfigsLock = new Object(); private final Object mConfigsArrayLock = new Object(); @GuardedBy("mConfigsArrayLock") @VisibleForTesting final SparseArray<ZenModeConfig> mConfigs = new SparseArray<>(); private final Metrics mMetrics = new Metrics(); private final ConditionProviders.Config mServiceConfig; private SystemUiSystemPropertiesFlags.FlagResolver mFlagResolver; @VisibleForTesting protected ZenModeEventLogger mZenModeEventLogger; private final SystemUiSystemPropertiesFlags.FlagResolver mFlagResolver; private final ZenModeEventLogger mZenModeEventLogger; @VisibleForTesting protected int mZenMode; @VisibleForTesting protected NotificationManager.Policy mConsolidatedPolicy; private int mUser = UserHandle.USER_SYSTEM; private final Object mConfigLock = new Object(); @GuardedBy("mConfigLock") @VisibleForTesting protected ZenModeConfig mConfig; @VisibleForTesting protected AudioManagerInternal mAudioManager; protected PackageManager mPm; Loading Loading @@ -159,7 +164,7 @@ public class ZenModeHelper { mDefaultConfig = readDefaultConfig(mContext.getResources()); updateDefaultAutomaticRuleNames(); mConfig = mDefaultConfig.copy(); synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.put(UserHandle.USER_SYSTEM, mConfig); } mConsolidatedPolicy = mConfig.toNotificationPolicy(); Loading @@ -186,7 +191,7 @@ public class ZenModeHelper { public boolean matchesCallFilter(UserHandle userHandle, Bundle extras, ValidateNotificationPeople validator, int contactsTimeoutMs, float timeoutAffinity, int callingUid) { synchronized (mConfig) { synchronized (mConfigLock) { return ZenModeFiltering.matchesCallFilter(mContext, mZenMode, mConsolidatedPolicy, userHandle, extras, validator, contactsTimeoutMs, timeoutAffinity, callingUid); Loading @@ -206,7 +211,7 @@ public class ZenModeHelper { } public boolean shouldIntercept(NotificationRecord record) { synchronized (mConfig) { synchronized (mConfigLock) { return mFiltering.shouldIntercept(mZenMode, mConsolidatedPolicy, record); } } Loading @@ -221,7 +226,7 @@ public class ZenModeHelper { public void initZenMode() { if (DEBUG) Log.d(TAG, "initZenMode"); synchronized (mConfig) { synchronized (mConfigLock) { // "update" config to itself, which will have no effect in the case where a config // was read in via XML, but will initialize zen mode if nothing was read in and the // config remains the default. Loading Loading @@ -250,7 +255,7 @@ public class ZenModeHelper { public void onUserRemoved(int user) { if (user < UserHandle.USER_SYSTEM) return; if (DEBUG) Log.d(TAG, "onUserRemoved u=" + user); synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.remove(user); } } Loading @@ -268,7 +273,7 @@ public class ZenModeHelper { mUser = user; if (DEBUG) Log.d(TAG, reason + " u=" + user); ZenModeConfig config = null; synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { if (mConfigs.get(user) != null) { config = mConfigs.get(user).copy(); } Loading @@ -278,7 +283,7 @@ public class ZenModeHelper { config = mDefaultConfig.copy(); config.user = user; } synchronized (mConfig) { synchronized (mConfigLock) { setConfigLocked(config, null, reason, Process.SYSTEM_UID, true); } cleanUpZenRules(); Loading Loading @@ -314,7 +319,7 @@ public class ZenModeHelper { public List<ZenRule> getZenRules() { List<ZenRule> rules = new ArrayList<>(); synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return rules; for (ZenRule rule : mConfig.automaticRules.values()) { if (canManageAutomaticZenRule(rule)) { Loading @@ -327,7 +332,7 @@ public class ZenModeHelper { public AutomaticZenRule getAutomaticZenRule(String id) { ZenRule rule; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return null; rule = mConfig.automaticRules.get(id); } Loading Loading @@ -364,7 +369,7 @@ public class ZenModeHelper { } ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) { throw new AndroidRuntimeException("Could not create rule"); } Loading @@ -387,7 +392,7 @@ public class ZenModeHelper { public boolean updateAutomaticZenRule(String ruleId, AutomaticZenRule automaticZenRule, String reason, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return false; if (DEBUG) { Log.d(TAG, "updateAutomaticZenRule zenRule=" + automaticZenRule Loading Loading @@ -419,7 +424,7 @@ public class ZenModeHelper { public boolean removeAutomaticZenRule(String id, String reason, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return false; newConfig = mConfig.copy(); ZenRule ruleToRemove = newConfig.automaticRules.get(id); Loading Loading @@ -450,7 +455,7 @@ public class ZenModeHelper { public boolean removeAutomaticZenRules(String packageName, String reason, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return false; newConfig = mConfig.copy(); for (int i = newConfig.automaticRules.size() - 1; i >= 0; i--) { Loading @@ -467,7 +472,7 @@ public class ZenModeHelper { public void setAutomaticZenRuleState(String id, Condition condition, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return; newConfig = mConfig.copy(); Loading @@ -481,7 +486,7 @@ public class ZenModeHelper { public void setAutomaticZenRuleState(Uri ruleDefinition, Condition condition, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return; newConfig = mConfig.copy(); Loading @@ -491,6 +496,7 @@ public class ZenModeHelper { } } @GuardedBy("mConfigLock") private void setAutomaticZenRuleStateLocked(ZenModeConfig config, List<ZenRule> rules, Condition condition, int callingUid, boolean fromSystemOrSystemUi) { if (rules == null || rules.isEmpty()) return; Loading Loading @@ -538,7 +544,7 @@ public class ZenModeHelper { return 0; } int count = 0; synchronized (mConfig) { synchronized (mConfigLock) { for (ZenRule rule : mConfig.automaticRules.values()) { if (cn.equals(rule.component) || cn.equals(rule.configurationActivity)) { count++; Loading @@ -555,7 +561,7 @@ public class ZenModeHelper { return 0; } int count = 0; synchronized (mConfig) { synchronized (mConfigLock) { for (ZenRule rule : mConfig.automaticRules.values()) { if (pkg.equals(rule.getPkg())) { count++; Loading Loading @@ -588,6 +594,7 @@ public class ZenModeHelper { protected void updateDefaultZenRules(int callingUid, boolean fromSystemOrSystemUi) { updateDefaultAutomaticRuleNames(); synchronized (mConfigLock) { for (ZenRule defaultRule : mDefaultConfig.automaticRules.values()) { ZenRule currRule = mConfig.automaticRules.get(defaultRule.id); // if default rule wasn't user-modified nor enabled, use localized name Loading @@ -595,8 +602,10 @@ public class ZenModeHelper { if (currRule != null && !currRule.modified && !currRule.enabled && !defaultRule.name.equals(currRule.name)) { if (canManageAutomaticZenRule(currRule)) { if (DEBUG) Slog.d(TAG, "Locale change - updating default zen rule name " if (DEBUG) { Slog.d(TAG, "Locale change - updating default zen rule name " + "from " + currRule.name + " to " + defaultRule.name); } // update default rule (if locale changed, name of rule will change) currRule.name = defaultRule.name; updateAutomaticZenRule(defaultRule.id, createAutomaticZenRule(currRule), Loading @@ -605,6 +614,7 @@ public class ZenModeHelper { } } } } private ServiceInfo getServiceInfo(ComponentName owner) { Intent queryIntent = new Intent(); Loading Loading @@ -686,7 +696,7 @@ public class ZenModeHelper { private void setManualZenMode(int zenMode, Uri conditionId, String reason, String caller, boolean setRingerMode, int callingUid, boolean fromSystemOrSystemUi) { ZenModeConfig newConfig; synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig == null) return; if (!Global.isValidZenMode(zenMode)) return; if (DEBUG) Log.d(TAG, "setManualZenMode " + Global.zenModeToString(zenMode) Loading Loading @@ -715,7 +725,7 @@ public class ZenModeHelper { void dump(ProtoOutputStream proto) { proto.write(ZenModeProto.ZEN_MODE, mZenMode); synchronized (mConfig) { synchronized (mConfigLock) { if (mConfig.manualRule != null) { mConfig.manualRule.dumpDebug(proto, ZenModeProto.ENABLED_ACTIVE_CONDITIONS); } Loading @@ -737,14 +747,14 @@ public class ZenModeHelper { pw.println(Global.zenModeToString(mZenMode)); pw.print(prefix); pw.println("mConsolidatedPolicy=" + mConsolidatedPolicy.toString()); synchronized(mConfigsLock) { synchronized (mConfigsArrayLock) { final int N = mConfigs.size(); for (int i = 0; i < N; i++) { dump(pw, prefix, "mConfigs[u=" + mConfigs.keyAt(i) + "]", mConfigs.valueAt(i)); } } pw.print(prefix); pw.print("mUser="); pw.println(mUser); synchronized (mConfig) { synchronized (mConfigLock) { dump(pw, prefix, "mConfig", mConfig); } Loading Loading @@ -833,7 +843,7 @@ public class ZenModeHelper { Settings.Secure.ZEN_SETTINGS_UPDATED, 1, userId); } if (DEBUG) Log.d(TAG, reason); synchronized (mConfig) { synchronized (mConfigLock) { setConfigLocked(config, null, reason, Process.SYSTEM_UID, true); } } Loading @@ -841,7 +851,7 @@ public class ZenModeHelper { public void writeXml(TypedXmlSerializer out, boolean forBackup, Integer version, int userId) throws IOException { synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { final int n = mConfigs.size(); for (int i = 0; i < n; i++) { if (forBackup && mConfigs.keyAt(i) != userId) { Loading @@ -856,8 +866,10 @@ public class ZenModeHelper { * @return user-specified default notification policy for priority only do not disturb */ public Policy getNotificationPolicy() { synchronized (mConfigLock) { return getNotificationPolicy(mConfig); } } private static Policy getNotificationPolicy(ZenModeConfig config) { return config == null ? null : config.toNotificationPolicy(); Loading @@ -867,8 +879,8 @@ public class ZenModeHelper { * Sets the global notification policy used for priority only do not disturb */ public void setNotificationPolicy(Policy policy, int callingUid, boolean fromSystemOrSystemUi) { synchronized (mConfigLock) { if (policy == null || mConfig == null) return; synchronized (mConfig) { final ZenModeConfig newConfig = mConfig.copy(); newConfig.applyNotificationPolicy(policy); setConfigLocked(newConfig, null, "setNotificationPolicy", callingUid, Loading @@ -881,7 +893,7 @@ public class ZenModeHelper { */ private void cleanUpZenRules() { long currentTime = System.currentTimeMillis(); synchronized (mConfig) { synchronized (mConfigLock) { final ZenModeConfig newConfig = mConfig.copy(); if (newConfig.automaticRules != null) { for (int i = newConfig.automaticRules.size() - 1; i >= 0; i--) { Loading @@ -906,7 +918,7 @@ public class ZenModeHelper { * @return a copy of the zen mode configuration */ public ZenModeConfig getConfig() { synchronized (mConfig) { synchronized (mConfigLock) { return mConfig.copy(); } } Loading @@ -918,7 +930,8 @@ public class ZenModeHelper { return mConsolidatedPolicy.copy(); } public boolean setConfigLocked(ZenModeConfig config, ComponentName triggeringComponent, @GuardedBy("mConfigLock") private boolean setConfigLocked(ZenModeConfig config, ComponentName triggeringComponent, String reason, int callingUid, boolean fromSystemOrSystemUi) { return setConfigLocked(config, reason, triggeringComponent, true /*setRingerMode*/, callingUid, fromSystemOrSystemUi); Loading @@ -926,11 +939,12 @@ public class ZenModeHelper { public void setConfig(ZenModeConfig config, ComponentName triggeringComponent, String reason, int callingUid, boolean fromSystemOrSystemUi) { synchronized (mConfig) { synchronized (mConfigLock) { setConfigLocked(config, triggeringComponent, reason, callingUid, fromSystemOrSystemUi); } } @GuardedBy("mConfigLock") private boolean setConfigLocked(ZenModeConfig config, String reason, ComponentName triggeringComponent, boolean setRingerMode, int callingUid, boolean fromSystemOrSystemUi) { Loading @@ -942,7 +956,7 @@ public class ZenModeHelper { } if (config.user != mUser) { // simply store away for background users synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.put(config.user, config); } if (DEBUG) Log.d(TAG, "setConfigLocked: store config for user " + config.user); Loading @@ -951,7 +965,7 @@ public class ZenModeHelper { // handle CPS backed conditions - danger! may modify config mConditions.evaluateConfig(config, null, false /*processSubscriptions*/); synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { mConfigs.put(config.user, config); } if (DEBUG) Log.d(TAG, "setConfigLocked reason=" + reason, new Throwable()); Loading Loading @@ -979,6 +993,7 @@ public class ZenModeHelper { * Carries out a config update (if needed) and (re-)evaluates the zen mode value afterwards. * If logging is enabled, will also request logging of the outcome of this change if needed. */ @GuardedBy("mConfigLock") private void updateConfigAndZenModeLocked(ZenModeConfig config, String reason, boolean setRingerMode, int callingUid, boolean fromSystemOrSystemUi) { final boolean logZenModeEvents = mFlagResolver.isEnabled( Loading @@ -993,7 +1008,7 @@ public class ZenModeHelper { } final String val = Integer.toString(config.hashCode()); Global.putString(mContext.getContentResolver(), Global.ZEN_MODE_CONFIG_ETAG, val); evaluateZenMode(reason, setRingerMode); evaluateZenModeLocked(reason, setRingerMode); // After all changes have occurred, log if requested if (logZenModeEvents) { ZenModeEventLogger.ZenModeInfo newInfo = new ZenModeEventLogger.ZenModeInfo( Loading Loading @@ -1025,7 +1040,8 @@ public class ZenModeHelper { } @VisibleForTesting protected void evaluateZenMode(String reason, boolean setRingerMode) { @GuardedBy("mConfigLock") protected void evaluateZenModeLocked(String reason, boolean setRingerMode) { if (DEBUG) Log.d(TAG, "evaluateZenMode"); if (mConfig == null) return; final int policyHashBefore = mConsolidatedPolicy == null ? 0 Loading Loading @@ -1056,8 +1072,8 @@ public class ZenModeHelper { } private int computeZenMode() { synchronized (mConfigLock) { if (mConfig == null) return Global.ZEN_MODE_OFF; synchronized (mConfig) { if (mConfig.manualRule != null) return mConfig.manualRule.zenMode; int zen = Global.ZEN_MODE_OFF; for (ZenRule automaticRule : mConfig.automaticRules.values()) { Loading Loading @@ -1094,8 +1110,8 @@ public class ZenModeHelper { } private void updateConsolidatedPolicy(String reason) { synchronized (mConfigLock) { if (mConfig == null) return; synchronized (mConfig) { ZenPolicy policy = new ZenPolicy(); if (mConfig.manualRule != null) { applyCustomPolicy(policy, mConfig.manualRule); Loading Loading @@ -1293,7 +1309,7 @@ public class ZenModeHelper { * Generate pulled atoms about do not disturb configurations. */ public void pullRules(List<StatsEvent> events) { synchronized (mConfigsLock) { synchronized (mConfigsArrayLock) { final int numConfigs = mConfigs.size(); for (int i = 0; i < numConfigs; i++) { final int user = mConfigs.keyAt(i); Loading @@ -1319,6 +1335,7 @@ public class ZenModeHelper { } } @GuardedBy("mConfigsArrayLock") private void ruleToProtoLocked(int user, ZenRule rule, boolean isManualRule, List<StatsEvent> events) { // Make the ID safe. Loading Loading @@ -1389,7 +1406,7 @@ public class ZenModeHelper { if (mZenMode == Global.ZEN_MODE_OFF || (mZenMode == Global.ZEN_MODE_IMPORTANT_INTERRUPTIONS && !ZenModeConfig.areAllPriorityOnlyRingerSoundsMuted(mConfig))) { && !areAllPriorityOnlyRingerSoundsMuted())) { // in priority only with ringer not muted, save ringer mode changes // in dnd off, save ringer mode changes setPreviousRingerModeSetting(ringerModeNew); Loading @@ -1410,8 +1427,7 @@ public class ZenModeHelper { && (mZenMode == Global.ZEN_MODE_NO_INTERRUPTIONS || mZenMode == Global.ZEN_MODE_ALARMS || (mZenMode == Global.ZEN_MODE_IMPORTANT_INTERRUPTIONS && ZenModeConfig.areAllPriorityOnlyRingerSoundsMuted( mConfig)))) { && areAllPriorityOnlyRingerSoundsMuted()))) { newZen = Global.ZEN_MODE_OFF; } else if (mZenMode != Global.ZEN_MODE_OFF) { ringerModeExternalOut = AudioManager.RINGER_MODE_SILENT; Loading @@ -1430,6 +1446,12 @@ public class ZenModeHelper { return ringerModeExternalOut; } private boolean areAllPriorityOnlyRingerSoundsMuted() { synchronized (mConfigLock) { return ZenModeConfig.areAllPriorityOnlyRingerSoundsMuted(mConfig); } } @Override public int onSetRingerModeExternal(int ringerModeOld, int ringerModeNew, String caller, int ringerModeInternal, VolumePolicy policy) { Loading Loading @@ -1633,7 +1655,7 @@ public class ZenModeHelper { private void emitRules() { final long now = SystemClock.elapsedRealtime(); final long since = (now - mRuleCountLogTime); synchronized (mConfig) { synchronized (mConfigLock) { int numZenRules = mConfig.automaticRules.size(); if (mNumZenRules != numZenRules || since > MINIMUM_LOG_PERIOD_MS) { Loading @@ -1651,7 +1673,7 @@ public class ZenModeHelper { private void emitDndType() { final long now = SystemClock.elapsedRealtime(); final long since = (now - mTypeLogTimeMs); synchronized (mConfig) { synchronized (mConfigLock) { boolean dndOn = mZenMode != Global.ZEN_MODE_OFF; int zenType = !dndOn ? DND_OFF : (mConfig.manualRule != null) ? DND_ON_MANUAL : DND_ON_AUTOMATIC; Loading
services/tests/uiservicestests/src/com/android/server/notification/ZenModeHelperTest.java +4 −4 Original line number Diff line number Diff line Loading @@ -771,7 +771,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { mZenModeHelper.mConfig = null; // will evaluate config to zen mode off for (int i = 0; i < 3; i++) { // if zen doesn't change, zen should not reapply itself to the ringer mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); } verify(mAudioManager, never()).setRingerModeInternal(AudioManager.RINGER_MODE_NORMAL, mZenModeHelper.TAG); Loading @@ -798,7 +798,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { mZenModeHelper.mZenMode = ZEN_MODE_IMPORTANT_INTERRUPTIONS; for (int i = 0; i < 3; i++) { // if zen doesn't change, zen should not reapply itself to the ringer mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); } verify(mAudioManager, never()).setRingerModeInternal(AudioManager.RINGER_MODE_NORMAL, mZenModeHelper.TAG); Loading @@ -825,7 +825,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { mZenModeHelper.mZenMode = ZEN_MODE_IMPORTANT_INTERRUPTIONS; for (int i = 0; i < 3; i++) { // if zen doesn't change, zen should not reapply itself to the ringer mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); } verify(mAudioManager, never()).setRingerModeInternal(AudioManager.RINGER_MODE_NORMAL, mZenModeHelper.TAG); Loading Loading @@ -2269,7 +2269,7 @@ public class ZenModeHelperTest extends UiServiceTestCase { // Artificially turn zen mode "on". Re-evaluating zen mode should cause it to turn back off // given that we don't have any zen rules active. mZenModeHelper.mZenMode = ZEN_MODE_IMPORTANT_INTERRUPTIONS; mZenModeHelper.evaluateZenMode("test", true); mZenModeHelper.evaluateZenModeLocked("test", true); // Check that the change actually took: zen mode should be off now assertEquals(Global.ZEN_MODE_OFF, mZenModeHelper.mZenMode); Loading