Merge "Adding Battery saver policy to alarms"
This commit is contained in:
committed by
Android (Google) Code Review
commit
eedea4c824
@@ -274,11 +274,8 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
int uid, @NonNull String packageName) {
|
||||
updateJobsForUidPackage(uid, packageName, sender.isUidActive(uid));
|
||||
|
||||
if (!sender.areAlarmsRestricted(uid, packageName, /*allowWhileIdle=*/ false)) {
|
||||
if (!sender.areAlarmsRestricted(uid, packageName)) {
|
||||
unblockAlarmsForUidPackage(uid, packageName);
|
||||
} else if (!sender.areAlarmsRestricted(uid, packageName, /*allowWhileIdle=*/ true)) {
|
||||
// we need to deliver the allow-while-idle alarms for this uid, package
|
||||
unblockAllUnrestrictedAlarms();
|
||||
}
|
||||
|
||||
if (!sender.isRunAnyInBackgroundAppOpsAllowed(uid, packageName)) {
|
||||
@@ -302,6 +299,7 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
final boolean isActive = sender.isUidActive(uid);
|
||||
|
||||
updateJobsForUid(uid, isActive);
|
||||
updateAlarmsForUid(uid);
|
||||
|
||||
if (isActive) {
|
||||
unblockAlarmsForUid(uid);
|
||||
@@ -313,7 +311,7 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
*/
|
||||
private void onPowerSaveUnexempted(AppStateTrackerImpl sender) {
|
||||
updateAllJobs();
|
||||
unblockAllUnrestrictedAlarms();
|
||||
updateAllAlarms();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -322,6 +320,8 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
*/
|
||||
private void onPowerSaveExemptionListChanged(AppStateTrackerImpl sender) {
|
||||
updateAllJobs();
|
||||
updateAllAlarms();
|
||||
unblockAllUnrestrictedAlarms();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -344,7 +344,7 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
private void onExemptedBucketChanged(AppStateTrackerImpl sender) {
|
||||
// This doesn't happen very often, so just re-evaluate all jobs / alarms.
|
||||
updateAllJobs();
|
||||
unblockAllUnrestrictedAlarms();
|
||||
updateAllAlarms();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -352,10 +352,7 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
*/
|
||||
private void onForceAllAppsStandbyChanged(AppStateTrackerImpl sender) {
|
||||
updateAllJobs();
|
||||
|
||||
if (!sender.isForceAllAppsStandbyEnabled()) {
|
||||
unblockAllUnrestrictedAlarms();
|
||||
}
|
||||
updateAllAlarms();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -386,6 +383,19 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
public void stopForegroundServicesForUidPackage(int uid, String packageName) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when all alarms need to be re-evaluated for eligibility based on
|
||||
* {@link #areAlarmsRestrictedByBatterySaver}.
|
||||
*/
|
||||
public void updateAllAlarms() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the given uid state changes to active / idle.
|
||||
*/
|
||||
public void updateAlarmsForUid(int uid) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the job restrictions for multiple UIDs might have changed, so the alarm
|
||||
* manager should re-evaluate all restrictions for all blocked jobs.
|
||||
@@ -918,7 +928,7 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
// Feature flag for forced app standby changed.
|
||||
final boolean unblockAlarms;
|
||||
synchronized (mLock) {
|
||||
unblockAlarms = !mForcedAppStandbyEnabled && !mForceAllAppsStandby;
|
||||
unblockAlarms = !mForcedAppStandbyEnabled;
|
||||
}
|
||||
for (Listener l : cloneListeners()) {
|
||||
l.updateAllJobs();
|
||||
@@ -1109,38 +1119,11 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether alarms should be restricted for a UID package-name.
|
||||
* @return whether alarms should be restricted for a UID package-name, due to explicit
|
||||
* user-forced app standby. Use {{@link #areAlarmsRestrictedByBatterySaver} to check for
|
||||
* restrictions induced by battery saver.
|
||||
*/
|
||||
public boolean areAlarmsRestricted(int uid, @NonNull String packageName,
|
||||
boolean isExemptOnBatterySaver) {
|
||||
return isRestricted(uid, packageName, /*useTempExemptionListToo=*/ false,
|
||||
isExemptOnBatterySaver);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether jobs should be restricted for a UID package-name.
|
||||
*/
|
||||
public boolean areJobsRestricted(int uid, @NonNull String packageName,
|
||||
boolean hasForegroundExemption) {
|
||||
return isRestricted(uid, packageName, /*useTempExemptionListToo=*/ true,
|
||||
hasForegroundExemption);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether foreground services should be suppressed in the background
|
||||
* due to forced app standby for the given app
|
||||
*/
|
||||
public boolean areForegroundServicesRestricted(int uid, @NonNull String packageName) {
|
||||
synchronized (mLock) {
|
||||
return isRunAnyRestrictedLocked(uid, packageName);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether force-app-standby is effective for a UID package-name.
|
||||
*/
|
||||
private boolean isRestricted(int uid, @NonNull String packageName,
|
||||
boolean useTempExemptionListToo, boolean exemptOnBatterySaver) {
|
||||
public boolean areAlarmsRestricted(int uid, @NonNull String packageName) {
|
||||
if (isUidActive(uid)) {
|
||||
return false;
|
||||
}
|
||||
@@ -1149,13 +1132,51 @@ public class AppStateTrackerImpl implements AppStateTracker {
|
||||
if (ArrayUtils.contains(mPowerExemptAllAppIds, appId)) {
|
||||
return false;
|
||||
}
|
||||
if (useTempExemptionListToo && ArrayUtils.contains(mTempExemptAppIds, appId)) {
|
||||
return (mForcedAppStandbyEnabled && isRunAnyRestrictedLocked(uid, packageName));
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return whether alarms should be restricted when due to battery saver.
|
||||
*/
|
||||
public boolean areAlarmsRestrictedByBatterySaver(int uid, @NonNull String packageName) {
|
||||
if (isUidActive(uid)) {
|
||||
return false;
|
||||
}
|
||||
synchronized (mLock) {
|
||||
final int appId = UserHandle.getAppId(uid);
|
||||
if (ArrayUtils.contains(mPowerExemptAllAppIds, appId)) {
|
||||
return false;
|
||||
}
|
||||
final int userId = UserHandle.getUserId(uid);
|
||||
if (mAppStandbyInternal.isAppIdleEnabled() && !mAppStandbyInternal.isInParole()
|
||||
&& mExemptedBucketPackages.contains(userId, packageName)) {
|
||||
return false;
|
||||
}
|
||||
return mForceAllAppsStandby;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @return whether jobs should be restricted for a UID package-name. This could be due to
|
||||
* battery saver or user-forced app standby
|
||||
*/
|
||||
public boolean areJobsRestricted(int uid, @NonNull String packageName,
|
||||
boolean hasForegroundExemption) {
|
||||
if (isUidActive(uid)) {
|
||||
return false;
|
||||
}
|
||||
synchronized (mLock) {
|
||||
final int appId = UserHandle.getAppId(uid);
|
||||
if (ArrayUtils.contains(mPowerExemptAllAppIds, appId)
|
||||
|| ArrayUtils.contains(mTempExemptAppIds, appId)) {
|
||||
return false;
|
||||
}
|
||||
if (mForcedAppStandbyEnabled && isRunAnyRestrictedLocked(uid, packageName)) {
|
||||
return true;
|
||||
}
|
||||
if (exemptOnBatterySaver) {
|
||||
if (hasForegroundExemption) {
|
||||
return false;
|
||||
}
|
||||
final int userId = UserHandle.getUserId(uid);
|
||||
|
||||
@@ -42,7 +42,7 @@ import java.util.Date;
|
||||
*/
|
||||
class Alarm {
|
||||
@VisibleForTesting
|
||||
public static final int NUM_POLICIES = 3;
|
||||
public static final int NUM_POLICIES = 4;
|
||||
/**
|
||||
* Index used to store the time the alarm was requested to expire. To be used with
|
||||
* {@link #setPolicyElapsed(int, long)}.
|
||||
@@ -59,6 +59,12 @@ class Alarm {
|
||||
*/
|
||||
public static final int DEVICE_IDLE_POLICY_INDEX = 2;
|
||||
|
||||
/**
|
||||
* Index used to store the earliest time the alarm can expire based on battery saver policy.
|
||||
* To be used with {@link #setPolicyElapsed(int, long)}.
|
||||
*/
|
||||
public static final int BATTERY_SAVER_POLICY_INDEX = 3;
|
||||
|
||||
public final int type;
|
||||
/**
|
||||
* The original trigger time supplied by the caller. This can be in the elapsed or rtc time base
|
||||
@@ -223,6 +229,8 @@ class Alarm {
|
||||
return "app_standby";
|
||||
case DEVICE_IDLE_POLICY_INDEX:
|
||||
return "device_idle";
|
||||
case BATTERY_SAVER_POLICY_INDEX:
|
||||
return "battery_saver";
|
||||
default:
|
||||
return "--unknown--";
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@ import static android.content.pm.PackageManager.MATCH_SYSTEM_ONLY;
|
||||
import static android.os.UserHandle.USER_SYSTEM;
|
||||
|
||||
import static com.android.server.alarm.Alarm.APP_STANDBY_POLICY_INDEX;
|
||||
import static com.android.server.alarm.Alarm.BATTERY_SAVER_POLICY_INDEX;
|
||||
import static com.android.server.alarm.Alarm.DEVICE_IDLE_POLICY_INDEX;
|
||||
import static com.android.server.alarm.Alarm.REQUESTER_POLICY_INDEX;
|
||||
|
||||
@@ -156,6 +157,7 @@ public class AlarmManagerService extends SystemService {
|
||||
|
||||
static final int TICK_HISTORY_DEPTH = 10;
|
||||
static final long MILLIS_IN_DAY = 24 * 60 * 60 * 1000;
|
||||
static final long INDEFINITE_DELAY = 365 * MILLIS_IN_DAY;
|
||||
|
||||
// Indices into the KEYS_APP_STANDBY_QUOTAS array.
|
||||
static final int ACTIVE_INDEX = 0;
|
||||
@@ -964,8 +966,7 @@ public class AlarmManagerService extends SystemService {
|
||||
* Check all alarms in {@link #mPendingBackgroundAlarms} and send the ones that are not
|
||||
* restricted.
|
||||
*
|
||||
* This is only called when the global "force all apps-standby" flag changes or when the
|
||||
* power save whitelist changes, so it's okay to be slow.
|
||||
* This is only called when the power save whitelist changes, so it's okay to be slow.
|
||||
*/
|
||||
void sendAllUnrestrictedPendingBackgroundAlarmsLocked() {
|
||||
final ArrayList<Alarm> alarmsToDeliver = new ArrayList<>();
|
||||
@@ -984,7 +985,6 @@ public class AlarmManagerService extends SystemService {
|
||||
Predicate<Alarm> isBackgroundRestricted) {
|
||||
|
||||
for (int uidIndex = pendingAlarms.size() - 1; uidIndex >= 0; uidIndex--) {
|
||||
final int uid = pendingAlarms.keyAt(uidIndex);
|
||||
final ArrayList<Alarm> alarmsForUid = pendingAlarms.valueAt(uidIndex);
|
||||
|
||||
for (int alarmIndex = alarmsForUid.size() - 1; alarmIndex >= 0; alarmIndex--) {
|
||||
@@ -1619,6 +1619,44 @@ public class AlarmManagerService extends SystemService {
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Adjusts the delivery time of the alarm based on battery saver rules.
|
||||
*
|
||||
* @param alarm The alarm to adjust
|
||||
* @return {@code true} if the alarm delivery time was updated.
|
||||
*/
|
||||
private boolean adjustDeliveryTimeBasedOnBatterySaver(Alarm alarm) {
|
||||
final long nowElapsed = mInjector.getElapsedRealtime();
|
||||
if (isExemptFromBatterySaver(alarm)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!(mAppStateTracker != null && mAppStateTracker.areAlarmsRestrictedByBatterySaver(
|
||||
alarm.creatorUid, alarm.sourcePackage))) {
|
||||
return alarm.setPolicyElapsed(BATTERY_SAVER_POLICY_INDEX, nowElapsed);
|
||||
}
|
||||
|
||||
final long batterSaverPolicyElapsed;
|
||||
if ((alarm.flags & (AlarmManager.FLAG_ALLOW_WHILE_IDLE_UNRESTRICTED)) != 0) {
|
||||
// Unrestricted.
|
||||
batterSaverPolicyElapsed = nowElapsed;
|
||||
} else if ((alarm.flags & AlarmManager.FLAG_ALLOW_WHILE_IDLE) != 0) {
|
||||
// Allowed but limited.
|
||||
final long minDelay;
|
||||
if (mUseAllowWhileIdleShortTime.get(alarm.creatorUid)) {
|
||||
minDelay = mConstants.ALLOW_WHILE_IDLE_SHORT_TIME;
|
||||
} else {
|
||||
minDelay = mConstants.ALLOW_WHILE_IDLE_LONG_TIME;
|
||||
}
|
||||
final long lastDispatch = mLastAllowWhileIdleDispatch.get(alarm.creatorUid, 0);
|
||||
batterSaverPolicyElapsed = (lastDispatch == 0) ? nowElapsed : lastDispatch + minDelay;
|
||||
} else {
|
||||
// Not allowed.
|
||||
batterSaverPolicyElapsed = nowElapsed + INDEFINITE_DELAY;
|
||||
}
|
||||
return alarm.setPolicyElapsed(BATTERY_SAVER_POLICY_INDEX, batterSaverPolicyElapsed);
|
||||
}
|
||||
|
||||
/**
|
||||
* Adjusts the delivery time of the alarm based on device_idle (doze) rules.
|
||||
*
|
||||
@@ -1756,6 +1794,7 @@ public class AlarmManagerService extends SystemService {
|
||||
if (a.alarmClock != null) {
|
||||
mNextAlarmClockMayChange = true;
|
||||
}
|
||||
adjustDeliveryTimeBasedOnBatterySaver(a);
|
||||
adjustDeliveryTimeBasedOnBucketLocked(a);
|
||||
mAlarmStore.add(a);
|
||||
rescheduleKernelAlarmsLocked();
|
||||
@@ -2230,14 +2269,6 @@ public class AlarmManagerService extends SystemService {
|
||||
pw.print(": ");
|
||||
final long lastTime = mLastAllowWhileIdleDispatch.valueAt(i);
|
||||
TimeUtils.formatDuration(lastTime, nowELAPSED, pw);
|
||||
|
||||
final long minInterval = getWhileIdleMinIntervalLocked(uid);
|
||||
pw.print(" Next allowed:");
|
||||
TimeUtils.formatDuration(lastTime + minInterval, nowELAPSED, pw);
|
||||
pw.print(" (");
|
||||
TimeUtils.formatDuration(minInterval, 0, pw);
|
||||
pw.print(")");
|
||||
|
||||
pw.println();
|
||||
}
|
||||
pw.decreaseIndent();
|
||||
@@ -2511,8 +2542,6 @@ public class AlarmManagerService extends SystemService {
|
||||
proto.write(AlarmManagerServiceDumpProto.LastAllowWhileIdleDispatch.UID, uid);
|
||||
proto.write(AlarmManagerServiceDumpProto.LastAllowWhileIdleDispatch.TIME_MS,
|
||||
lastTime);
|
||||
proto.write(AlarmManagerServiceDumpProto.LastAllowWhileIdleDispatch.NEXT_ALLOWED_MS,
|
||||
lastTime + getWhileIdleMinIntervalLocked(uid));
|
||||
proto.end(token);
|
||||
}
|
||||
|
||||
@@ -3119,30 +3148,36 @@ public class AlarmManagerService extends SystemService {
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isExemptFromBatterySaver(Alarm alarm) {
|
||||
if (alarm.alarmClock != null) {
|
||||
return true;
|
||||
}
|
||||
if ((alarm.operation != null)
|
||||
&& (alarm.operation.isActivity() || alarm.operation.isForegroundService())) {
|
||||
return true;
|
||||
}
|
||||
if (UserHandle.isCore(alarm.creatorUid)) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private boolean isBackgroundRestricted(Alarm alarm) {
|
||||
boolean exemptOnBatterySaver = (alarm.flags & FLAG_ALLOW_WHILE_IDLE) != 0;
|
||||
if (alarm.alarmClock != null) {
|
||||
// Don't defer alarm clocks
|
||||
return false;
|
||||
}
|
||||
if (alarm.operation != null) {
|
||||
if (alarm.operation.isActivity()) {
|
||||
// Don't defer starting actual UI
|
||||
return false;
|
||||
}
|
||||
if (alarm.operation.isForegroundService()) {
|
||||
// FG service alarms are nearly as important; consult AST policy
|
||||
exemptOnBatterySaver = true;
|
||||
}
|
||||
if (alarm.operation != null && alarm.operation.isActivity()) {
|
||||
// Don't defer starting actual UI
|
||||
return false;
|
||||
}
|
||||
final String sourcePackage = alarm.sourcePackage;
|
||||
final int sourceUid = alarm.creatorUid;
|
||||
if (UserHandle.isCore(sourceUid)) {
|
||||
return false;
|
||||
}
|
||||
return (mAppStateTracker != null) &&
|
||||
mAppStateTracker.areAlarmsRestricted(sourceUid, sourcePackage,
|
||||
exemptOnBatterySaver);
|
||||
return (mAppStateTracker != null) && mAppStateTracker.areAlarmsRestricted(sourceUid,
|
||||
sourcePackage);
|
||||
}
|
||||
|
||||
private static native long init();
|
||||
@@ -3153,46 +3188,10 @@ public class AlarmManagerService extends SystemService {
|
||||
private static native int setKernelTimezone(long nativeData, int minuteswest);
|
||||
private static native long getNextAlarm(long nativeData, int type);
|
||||
|
||||
private long getWhileIdleMinIntervalLocked(int uid) {
|
||||
final boolean ebs = (mAppStateTracker != null)
|
||||
&& mAppStateTracker.isForceAllAppsStandbyEnabled();
|
||||
|
||||
if (!ebs || mUseAllowWhileIdleShortTime.get(uid)) {
|
||||
// if the last allow-while-idle went off while uid was fg, or the uid
|
||||
// recently came into fg, don't block the alarm for long.
|
||||
return mConstants.ALLOW_WHILE_IDLE_SHORT_TIME;
|
||||
}
|
||||
return mConstants.ALLOW_WHILE_IDLE_LONG_TIME;
|
||||
}
|
||||
|
||||
boolean triggerAlarmsLocked(ArrayList<Alarm> triggerList, final long nowELAPSED) {
|
||||
boolean hasWakeup = false;
|
||||
final ArrayList<Alarm> pendingAlarms = mAlarmStore.removePendingAlarms(nowELAPSED);
|
||||
for (final Alarm alarm : pendingAlarms) {
|
||||
if ((alarm.flags & AlarmManager.FLAG_ALLOW_WHILE_IDLE) != 0) {
|
||||
// If this is an ALLOW_WHILE_IDLE alarm, we constrain how frequently the app can
|
||||
// schedule such alarms. The first such alarm from an app is always delivered.
|
||||
final long lastTime = mLastAllowWhileIdleDispatch.get(alarm.creatorUid, -1);
|
||||
final long minTime = lastTime + getWhileIdleMinIntervalLocked(alarm.creatorUid);
|
||||
if (lastTime >= 0 && nowELAPSED < minTime) {
|
||||
// Whoops, it hasn't been long enough since the last ALLOW_WHILE_IDLE
|
||||
// alarm went off for this app. Reschedule the alarm to be in the
|
||||
// correct time period.
|
||||
alarm.setPolicyElapsed(REQUESTER_POLICY_INDEX, minTime);
|
||||
if (RECORD_DEVICE_IDLE_ALARMS) {
|
||||
IdleDispatchEntry ent = new IdleDispatchEntry();
|
||||
ent.uid = alarm.uid;
|
||||
ent.pkg = alarm.operation.getCreatorPackage();
|
||||
ent.tag = alarm.operation.getTag("");
|
||||
ent.op = "RESCHEDULE";
|
||||
ent.elapsedRealtime = nowELAPSED;
|
||||
ent.argRealtime = lastTime;
|
||||
mAllowWhileIdleDispatches.add(ent);
|
||||
}
|
||||
setImplLocked(alarm);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
if (isBackgroundRestricted(alarm)) {
|
||||
// Alarms with FLAG_WAKE_FROM_IDLE or mPendingIdleUntil alarm are not deferred
|
||||
if (DEBUG_BG_LIMIT) {
|
||||
@@ -3924,8 +3923,41 @@ public class AlarmManagerService extends SystemService {
|
||||
}
|
||||
|
||||
private final Listener mForceAppStandbyListener = new Listener() {
|
||||
|
||||
@Override
|
||||
public void updateAllAlarms() {
|
||||
// Called when:
|
||||
// 1. Power exemption list changes,
|
||||
// 2. Battery saver state is toggled,
|
||||
// 3. Any package is moved into or out of the EXEMPTED bucket.
|
||||
synchronized (mLock) {
|
||||
if (mAlarmStore.updateAlarmDeliveries(
|
||||
a -> adjustDeliveryTimeBasedOnBatterySaver(a))) {
|
||||
rescheduleKernelAlarmsLocked();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void updateAlarmsForUid(int uid) {
|
||||
// Called when the given uid's state switches b/w active and idle.
|
||||
synchronized (mLock) {
|
||||
if (mAlarmStore.updateAlarmDeliveries(a -> {
|
||||
if (a.creatorUid != uid) {
|
||||
return false;
|
||||
}
|
||||
return adjustDeliveryTimeBasedOnBatterySaver(a);
|
||||
})) {
|
||||
rescheduleKernelAlarmsLocked();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void unblockAllUnrestrictedAlarms() {
|
||||
// Called when:
|
||||
// 1. Power exemption list changes,
|
||||
// 2. User FAS feature is disabled.
|
||||
synchronized (mLock) {
|
||||
sendAllUnrestrictedPendingBackgroundAlarmsLocked();
|
||||
}
|
||||
@@ -3934,12 +3966,14 @@ public class AlarmManagerService extends SystemService {
|
||||
@Override
|
||||
public void unblockAlarmsForUid(int uid) {
|
||||
synchronized (mLock) {
|
||||
// Called when the given uid becomes active.
|
||||
sendPendingBackgroundAlarmsLocked(uid, null);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void unblockAlarmsForUidPackage(int uid, String packageName) {
|
||||
// Called when user turns off FAS for this (uid, package).
|
||||
synchronized (mLock) {
|
||||
sendPendingBackgroundAlarmsLocked(uid, packageName);
|
||||
}
|
||||
@@ -3950,9 +3984,14 @@ public class AlarmManagerService extends SystemService {
|
||||
synchronized (mLock) {
|
||||
if (foreground) {
|
||||
mUseAllowWhileIdleShortTime.put(uid, true);
|
||||
|
||||
// Note we don't have to drain the pending while-idle alarms here, because
|
||||
// this event should coincide with unblockAlarmsForUid().
|
||||
if (mAlarmStore.updateAlarmDeliveries(a -> {
|
||||
if (a.creatorUid != uid || (a.flags & FLAG_ALLOW_WHILE_IDLE) == 0) {
|
||||
return false;
|
||||
}
|
||||
return adjustDeliveryTimeBasedOnBatterySaver(a);
|
||||
})) {
|
||||
rescheduleKernelAlarmsLocked();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -4236,18 +4275,20 @@ public class AlarmManagerService extends SystemService {
|
||||
if (allowWhileIdle) {
|
||||
// Record the last time this uid handled an ALLOW_WHILE_IDLE alarm.
|
||||
mLastAllowWhileIdleDispatch.put(alarm.creatorUid, nowELAPSED);
|
||||
mAlarmStore.updateAlarmDeliveries(a -> {
|
||||
if (a.creatorUid != alarm.creatorUid) {
|
||||
return false;
|
||||
}
|
||||
return adjustDeliveryTimeBasedOnDeviceIdle(a);
|
||||
});
|
||||
if ((mAppStateTracker == null)
|
||||
|| mAppStateTracker.isUidInForeground(alarm.creatorUid)) {
|
||||
mUseAllowWhileIdleShortTime.put(alarm.creatorUid, true);
|
||||
} else {
|
||||
mUseAllowWhileIdleShortTime.put(alarm.creatorUid, false);
|
||||
}
|
||||
mAlarmStore.updateAlarmDeliveries(a -> {
|
||||
if (a.creatorUid != alarm.creatorUid
|
||||
|| (a.flags & FLAG_ALLOW_WHILE_IDLE) == 0) {
|
||||
return false;
|
||||
}
|
||||
return adjustDeliveryTimeBasedOnDeviceIdle(a)
|
||||
| adjustDeliveryTimeBasedOnBatterySaver(a);
|
||||
});
|
||||
if (RECORD_DEVICE_IDLE_ALARMS) {
|
||||
IdleDispatchEntry ent = new IdleDispatchEntry();
|
||||
ent.uid = alarm.uid;
|
||||
|
||||
@@ -313,29 +313,30 @@ public class AppStateTrackerTest {
|
||||
}
|
||||
}
|
||||
|
||||
private static final int NONE = 0;
|
||||
private static final int ALARMS_ONLY = 1 << 0;
|
||||
private static final int JOBS_ONLY = 1 << 1;
|
||||
private static final int JOBS_AND_ALARMS = ALARMS_ONLY | JOBS_ONLY;
|
||||
|
||||
private void areRestricted(AppStateTrackerTestable instance, int uid, String packageName,
|
||||
int restrictionTypes, boolean exemptFromBatterySaver) {
|
||||
assertEquals(((restrictionTypes & JOBS_ONLY) != 0),
|
||||
instance.areJobsRestricted(uid, packageName, exemptFromBatterySaver));
|
||||
assertEquals(((restrictionTypes & ALARMS_ONLY) != 0),
|
||||
instance.areAlarmsRestricted(uid, packageName, exemptFromBatterySaver));
|
||||
private void areJobsRestricted(AppStateTrackerTestable instance, int[] uids, String[] packages,
|
||||
boolean[] restricted, boolean exemption) {
|
||||
assertTrue(uids.length == packages.length && uids.length == restricted.length);
|
||||
for (int i = 0; i < uids.length; i++) {
|
||||
assertEquals(restricted[i],
|
||||
instance.areJobsRestricted(uids[i], packages[i], exemption));
|
||||
}
|
||||
}
|
||||
|
||||
private void areRestricted(AppStateTrackerTestable instance, int uid, String packageName,
|
||||
int restrictionTypes) {
|
||||
areRestricted(instance, uid, packageName, restrictionTypes,
|
||||
/*exemptFromBatterySaver=*/ false);
|
||||
private void areAlarmsRestrictedByFAS(AppStateTrackerTestable instance, int[] uids,
|
||||
String[] packages, boolean[] restricted) {
|
||||
assertTrue(uids.length == packages.length && uids.length == restricted.length);
|
||||
for (int i = 0; i < uids.length; i++) {
|
||||
assertEquals(restricted[i], instance.areAlarmsRestricted(uids[i], packages[i]));
|
||||
}
|
||||
}
|
||||
|
||||
private void areRestrictedWithExemption(AppStateTrackerTestable instance,
|
||||
int uid, String packageName, int restrictionTypes) {
|
||||
areRestricted(instance, uid, packageName, restrictionTypes,
|
||||
/*exemptFromBatterySaver=*/ true);
|
||||
private void areAlarmsRestrictedByBatterySaver(AppStateTrackerTestable instance, int[] uids,
|
||||
String[] packages, boolean[] restricted) {
|
||||
assertTrue(uids.length == packages.length && uids.length == restricted.length);
|
||||
for (int i = 0; i < uids.length; i++) {
|
||||
assertEquals(restricted[i],
|
||||
instance.areAlarmsRestrictedByBatterySaver(uids[i], packages[i]));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -344,30 +345,42 @@ public class AppStateTrackerTest {
|
||||
callStart(instance);
|
||||
|
||||
assertFalse(instance.isForceAllAppsStandbyEnabled());
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
|
||||
areRestrictedWithExemption(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestrictedWithExemption(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestrictedWithExemption(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false},
|
||||
true);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false});
|
||||
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
assertTrue(instance.isForceAllAppsStandbyEnabled());
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
|
||||
areRestrictedWithExemption(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestrictedWithExemption(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestrictedWithExemption(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false},
|
||||
true);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false});
|
||||
|
||||
// Toggle the foreground state.
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
assertFalse(instance.isUidActive(UID_1));
|
||||
assertFalse(instance.isUidActive(UID_2));
|
||||
@@ -376,34 +389,65 @@ public class AppStateTrackerTest {
|
||||
mIUidObserver.onUidActive(UID_1);
|
||||
waitUntilMainHandlerDrain();
|
||||
waitUntilMainHandlerDrain();
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, true, true, false},
|
||||
false);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, true, true, false});
|
||||
|
||||
assertTrue(instance.isUidActive(UID_1));
|
||||
assertFalse(instance.isUidActive(UID_2));
|
||||
|
||||
mIUidObserver.onUidGone(UID_1, /*disable=*/ false);
|
||||
waitUntilMainHandlerDrain();
|
||||
waitUntilMainHandlerDrain();
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false},
|
||||
false);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false});
|
||||
|
||||
assertFalse(instance.isUidActive(UID_1));
|
||||
assertFalse(instance.isUidActive(UID_2));
|
||||
|
||||
mIUidObserver.onUidActive(UID_1);
|
||||
waitUntilMainHandlerDrain();
|
||||
waitUntilMainHandlerDrain();
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, true, true, false},
|
||||
false);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, true, true, false});
|
||||
|
||||
mIUidObserver.onUidIdle(UID_1, /*disable=*/ false);
|
||||
waitUntilMainHandlerDrain();
|
||||
waitUntilMainHandlerDrain();
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false},
|
||||
false);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false});
|
||||
|
||||
assertFalse(instance.isUidActive(UID_1));
|
||||
assertFalse(instance.isUidActive(UID_2));
|
||||
|
||||
@@ -416,11 +460,19 @@ public class AppStateTrackerTest {
|
||||
assertTrue(instance.isRunAnyInBackgroundAppOpsAllowed(UID_2, PACKAGE_2));
|
||||
assertTrue(instance.isRunAnyInBackgroundAppOpsAllowed(UID_10_2, PACKAGE_2));
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_10_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, NONE);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, false},
|
||||
false);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, false});
|
||||
areAlarmsRestrictedByFAS(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, false});
|
||||
|
||||
setAppOps(UID_1, PACKAGE_1, true);
|
||||
setAppOps(UID_10_2, PACKAGE_2, true);
|
||||
@@ -429,24 +481,72 @@ public class AppStateTrackerTest {
|
||||
assertTrue(instance.isRunAnyInBackgroundAppOpsAllowed(UID_2, PACKAGE_2));
|
||||
assertFalse(instance.isRunAnyInBackgroundAppOpsAllowed(UID_10_2, PACKAGE_2));
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false},
|
||||
true);
|
||||
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, false});
|
||||
areAlarmsRestrictedByFAS(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false});
|
||||
|
||||
// Toggle power saver, should still be the same.
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false},
|
||||
true);
|
||||
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, true, false});
|
||||
areAlarmsRestrictedByFAS(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false});
|
||||
|
||||
mPowerSaveMode = false;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false},
|
||||
true);
|
||||
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, false});
|
||||
areAlarmsRestrictedByFAS(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, false, false, true, false});
|
||||
|
||||
// Clear the app ops and update the exemption list.
|
||||
setAppOps(UID_1, PACKAGE_1, false);
|
||||
@@ -455,24 +555,41 @@ public class AppStateTrackerTest {
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_3, PACKAGE_3, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_3, PACKAGE_3, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, false},
|
||||
true);
|
||||
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, true, false});
|
||||
areAlarmsRestrictedByFAS(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, false});
|
||||
|
||||
instance.setPowerSaveExemptionListAppIds(new int[] {UID_1}, new int[] {},
|
||||
new int[] {UID_2});
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_10_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, ALARMS_ONLY);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, ALARMS_ONLY);
|
||||
areRestricted(instance, UID_3, PACKAGE_3, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_3, PACKAGE_3, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, UID_3, UID_10_3, Process.SYSTEM_UID},
|
||||
new String[]{PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_3, PACKAGE_3,
|
||||
PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, true, true, false},
|
||||
false);
|
||||
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, UID_3, UID_10_3, Process.SYSTEM_UID},
|
||||
new String[]{PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_3, PACKAGE_3,
|
||||
PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, true, true, true, true, false});
|
||||
|
||||
// Again, make sure toggling the global state doesn't change it.
|
||||
mPowerSaveMode = false;
|
||||
@@ -481,13 +598,18 @@ public class AppStateTrackerTest {
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_10_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, ALARMS_ONLY);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, ALARMS_ONLY);
|
||||
areRestricted(instance, UID_3, PACKAGE_3, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_3, PACKAGE_3, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, UID_3, UID_10_3, Process.SYSTEM_UID},
|
||||
new String[]{PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_3, PACKAGE_3,
|
||||
PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false, true, true, false},
|
||||
false);
|
||||
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_10_1, UID_2, UID_10_2, UID_3, UID_10_3, Process.SYSTEM_UID},
|
||||
new String[]{PACKAGE_1, PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_3, PACKAGE_3,
|
||||
PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, true, true, true, true, false});
|
||||
|
||||
assertTrue(instance.isUidPowerSaveExempt(UID_1));
|
||||
assertTrue(instance.isUidPowerSaveExempt(UID_10_1));
|
||||
@@ -646,52 +768,98 @@ public class AppStateTrackerTest {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testExempt() throws Exception {
|
||||
public void testExemptedBucket() throws Exception {
|
||||
final AppStateTrackerTestable instance = newInstance();
|
||||
callStart(instance);
|
||||
|
||||
assertFalse(instance.isForceAllAppsStandbyEnabled());
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false},
|
||||
false);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false});
|
||||
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
assertTrue(instance.isForceAllAppsStandbyEnabled());
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, Process.SYSTEM_UID, PACKAGE_SYSTEM, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {false, false, false, false},
|
||||
true);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2, Process.SYSTEM_UID},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2, PACKAGE_SYSTEM},
|
||||
new boolean[] {true, true, true, false});
|
||||
|
||||
// Exempt package 2 on user-10.
|
||||
mAppIdleStateChangeListener.onAppIdleStateChanged(PACKAGE_2, /*user=*/ 10, false,
|
||||
UsageStatsManager.STANDBY_BUCKET_EXEMPTED, REASON_MAIN_DEFAULT);
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, NONE);
|
||||
|
||||
areRestrictedWithExemption(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestrictedWithExemption(instance, UID_2, PACKAGE_2, NONE);
|
||||
areRestrictedWithExemption(instance, UID_10_2, PACKAGE_2, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {true, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, false, false},
|
||||
true);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {true, true, false});
|
||||
|
||||
// Exempt package 1 on user-0.
|
||||
mAppIdleStateChangeListener.onAppIdleStateChanged(PACKAGE_1, /*user=*/ 0, false,
|
||||
UsageStatsManager.STANDBY_BUCKET_EXEMPTED, REASON_MAIN_DEFAULT);
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, true, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, false, false},
|
||||
true);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, true, false});
|
||||
|
||||
// Unexempt package 2 on user-10.
|
||||
mAppIdleStateChangeListener.onAppIdleStateChanged(PACKAGE_2, /*user=*/ 10, false,
|
||||
UsageStatsManager.STANDBY_BUCKET_ACTIVE, REASON_MAIN_USAGE);
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, NONE);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_10_2, PACKAGE_2, JOBS_AND_ALARMS);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, true, true},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, false, false},
|
||||
true);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, true, true});
|
||||
|
||||
// Check force-app-standby.
|
||||
// EXEMPT doesn't exempt from force-app-standby.
|
||||
@@ -703,13 +871,28 @@ public class AppStateTrackerTest {
|
||||
mAppIdleStateChangeListener.onAppIdleStateChanged(PACKAGE_2, /*user=*/ 0, false,
|
||||
UsageStatsManager.STANDBY_BUCKET_EXEMPTED, REASON_MAIN_DEFAULT);
|
||||
|
||||
// All 3 packages (u0:p1, u0:p2, u10:p2) are now in the exempted bucket.
|
||||
setAppOps(UID_1, PACKAGE_1, true);
|
||||
|
||||
areRestricted(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestricted(instance, UID_2, PACKAGE_2, NONE);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {true, false, false},
|
||||
false);
|
||||
areJobsRestricted(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {true, false, false},
|
||||
true);
|
||||
|
||||
areRestrictedWithExemption(instance, UID_1, PACKAGE_1, JOBS_AND_ALARMS);
|
||||
areRestrictedWithExemption(instance, UID_2, PACKAGE_2, NONE);
|
||||
areAlarmsRestrictedByBatterySaver(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {false, false, false});
|
||||
areAlarmsRestrictedByFAS(instance,
|
||||
new int[] {UID_1, UID_2, UID_10_2},
|
||||
new String[] {PACKAGE_1, PACKAGE_2, PACKAGE_2},
|
||||
new boolean[] {true, false, false});
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -809,6 +992,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -823,7 +1008,9 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(1)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
@@ -853,6 +1040,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(1)).updateJobsForUidPackage(eq(UID_10_2), eq(PACKAGE_2), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -865,6 +1054,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(1)).updateJobsForUidPackage(eq(UID_10_2), eq(PACKAGE_2), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(1)).unblockAlarmsForUidPackage(eq(UID_10_2), eq(PACKAGE_2));
|
||||
@@ -876,15 +1067,16 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
|
||||
// Unrestrict while battery saver is on. Shouldn't fire.
|
||||
// Test overlap with battery saver
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
// Note toggling appops while BS is on will suppress unblockAlarmsForUidPackage().
|
||||
setAppOps(UID_10_2, PACKAGE_2, true);
|
||||
|
||||
waitUntilMainHandlerDrain();
|
||||
@@ -892,6 +1084,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(1)).updateJobsForUidPackage(eq(UID_10_2), eq(PACKAGE_2), anyBoolean());
|
||||
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -906,7 +1100,9 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(1)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
@@ -922,7 +1118,9 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(1)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
@@ -934,7 +1132,9 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(1)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
@@ -948,6 +1148,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -961,12 +1163,14 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
|
||||
// Do the same thing with battery saver on. (Currently same callbacks are called.)
|
||||
// Do the same thing with battery saver on.
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
@@ -975,6 +1179,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -989,7 +1195,9 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(1)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
@@ -1001,7 +1209,9 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(1)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
@@ -1015,6 +1225,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1028,6 +1240,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(anyInt(), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1037,9 +1251,8 @@ public class AppStateTrackerTest {
|
||||
// -------------------------------------------------------------------------
|
||||
// Tests with proc state changes.
|
||||
|
||||
// With battery save.
|
||||
mPowerSaveMode = true;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
// With battery saver.
|
||||
// Battery saver is already on.
|
||||
|
||||
mIUidObserver.onUidActive(UID_10_1);
|
||||
|
||||
@@ -1049,6 +1262,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).unblockAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1062,6 +1277,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1075,6 +1292,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).unblockAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1088,12 +1307,14 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
|
||||
// Without battery save.
|
||||
// Without battery saver.
|
||||
mPowerSaveMode = false;
|
||||
mPowerSaveObserver.accept(getPowerSaveState());
|
||||
|
||||
@@ -1102,7 +1323,9 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(0)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(1)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).updateAllAlarms();
|
||||
verify(l, times(0)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
reset(l);
|
||||
@@ -1115,6 +1338,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).unblockAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1128,6 +1353,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1141,6 +1368,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(1)).unblockAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
@@ -1154,6 +1383,8 @@ public class AppStateTrackerTest {
|
||||
verify(l, times(1)).updateJobsForUid(eq(UID_10_1), anyBoolean());
|
||||
verify(l, times(0)).updateJobsForUidPackage(anyInt(), anyString(), anyBoolean());
|
||||
|
||||
verify(l, times(0)).updateAllAlarms();
|
||||
verify(l, times(1)).updateAlarmsForUid(eq(UID_10_1));
|
||||
verify(l, times(0)).unblockAllUnrestrictedAlarms();
|
||||
verify(l, times(0)).unblockAlarmsForUid(anyInt());
|
||||
verify(l, times(0)).unblockAlarmsForUidPackage(anyInt(), anyString());
|
||||
|
||||
@@ -52,6 +52,7 @@ import static com.android.server.alarm.AlarmManagerService.Constants.KEY_LISTENE
|
||||
import static com.android.server.alarm.AlarmManagerService.Constants.KEY_MAX_INTERVAL;
|
||||
import static com.android.server.alarm.AlarmManagerService.Constants.KEY_MIN_FUTURITY;
|
||||
import static com.android.server.alarm.AlarmManagerService.Constants.KEY_MIN_INTERVAL;
|
||||
import static com.android.server.alarm.AlarmManagerService.INDEFINITE_DELAY;
|
||||
import static com.android.server.alarm.AlarmManagerService.IS_WAKEUP_MASK;
|
||||
import static com.android.server.alarm.AlarmManagerService.TIME_CHANGED_MASK;
|
||||
import static com.android.server.alarm.AlarmManagerService.WORKING_INDEX;
|
||||
@@ -71,6 +72,7 @@ import static org.mockito.ArgumentMatchers.argThat;
|
||||
import static org.mockito.ArgumentMatchers.eq;
|
||||
import static org.mockito.ArgumentMatchers.isNull;
|
||||
import static org.mockito.Mockito.atLeastOnce;
|
||||
import static org.mockito.Mockito.never;
|
||||
|
||||
import android.app.ActivityManager;
|
||||
import android.app.ActivityManagerInternal;
|
||||
@@ -817,14 +819,14 @@ public class AlarmManagerServiceTest {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testAlarmRestrictedInBatterySaver() throws Exception {
|
||||
public void testAlarmRestrictedByFAS() throws Exception {
|
||||
final ArgumentCaptor<AppStateTrackerImpl.Listener> listenerArgumentCaptor =
|
||||
ArgumentCaptor.forClass(AppStateTrackerImpl.Listener.class);
|
||||
verify(mAppStateTracker).addListener(listenerArgumentCaptor.capture());
|
||||
|
||||
final PendingIntent alarmPi = getNewMockPendingIntent();
|
||||
when(mAppStateTracker.areAlarmsRestricted(TEST_CALLING_UID, TEST_CALLING_PACKAGE,
|
||||
false)).thenReturn(true);
|
||||
when(mAppStateTracker.areAlarmsRestricted(TEST_CALLING_UID,
|
||||
TEST_CALLING_PACKAGE)).thenReturn(true);
|
||||
setTestAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 2, alarmPi);
|
||||
assertEquals(mNowElapsedTest + 2, mTestTimer.getElapsed());
|
||||
|
||||
@@ -1301,7 +1303,6 @@ public class AlarmManagerServiceTest {
|
||||
|
||||
final long awiDelayForTest = 23;
|
||||
setDeviceConfigLong(KEY_ALLOW_WHILE_IDLE_LONG_TIME, awiDelayForTest);
|
||||
setDeviceConfigLong(KEY_ALLOW_WHILE_IDLE_SHORT_TIME, 0);
|
||||
|
||||
setIdleUntilAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 1000,
|
||||
getNewMockPendingIntent());
|
||||
@@ -1336,7 +1337,7 @@ public class AlarmManagerServiceTest {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void allowWhileIdleUnrestricted() throws Exception {
|
||||
public void allowWhileIdleUnrestrictedInIdle() throws Exception {
|
||||
doReturn(0).when(mService).fuzzForDuration(anyLong());
|
||||
|
||||
final long awiDelayForTest = 127;
|
||||
@@ -1361,7 +1362,7 @@ public class AlarmManagerServiceTest {
|
||||
}
|
||||
|
||||
@Test
|
||||
public void deviceIdleThrottling() throws Exception {
|
||||
public void deviceIdleDeferralOnSet() throws Exception {
|
||||
doReturn(0).when(mService).fuzzForDuration(anyLong());
|
||||
|
||||
final long deviceIdleUntil = mNowElapsedTest + 1234;
|
||||
@@ -1385,6 +1386,123 @@ public class AlarmManagerServiceTest {
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void deviceIdleStateChanges() throws Exception {
|
||||
doReturn(0).when(mService).fuzzForDuration(anyLong());
|
||||
|
||||
final int numAlarms = 10;
|
||||
final PendingIntent[] pis = new PendingIntent[numAlarms];
|
||||
for (int i = 0; i < numAlarms; i++) {
|
||||
setTestAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + i + 1,
|
||||
pis[i] = getNewMockPendingIntent());
|
||||
assertEquals(mNowElapsedTest + 1, mTestTimer.getElapsed());
|
||||
}
|
||||
|
||||
final PendingIntent idleUntil = getNewMockPendingIntent();
|
||||
setIdleUntilAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 1234, idleUntil);
|
||||
|
||||
assertEquals(mNowElapsedTest + 1234, mTestTimer.getElapsed());
|
||||
|
||||
mNowElapsedTest += 5;
|
||||
mTestTimer.expire();
|
||||
// Nothing should happen.
|
||||
verify(pis[0], never()).send(eq(mMockContext), eq(0), any(Intent.class), any(),
|
||||
any(Handler.class), isNull(), any());
|
||||
|
||||
mService.removeLocked(idleUntil, null);
|
||||
mTestTimer.expire();
|
||||
// Now, the first 5 alarms (upto i = 4) should expire.
|
||||
for (int i = 0; i < 5; i++) {
|
||||
verify(pis[i]).send(eq(mMockContext), eq(0), any(Intent.class), any(),
|
||||
any(Handler.class), isNull(), any());
|
||||
}
|
||||
// Rest should be restored, so the timer should reflect the next alarm.
|
||||
assertEquals(mNowElapsedTest + 1, mTestTimer.getElapsed());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void batterySaverThrottling() {
|
||||
final ArgumentCaptor<AppStateTrackerImpl.Listener> listenerArgumentCaptor =
|
||||
ArgumentCaptor.forClass(AppStateTrackerImpl.Listener.class);
|
||||
verify(mAppStateTracker).addListener(listenerArgumentCaptor.capture());
|
||||
final AppStateTrackerImpl.Listener listener = listenerArgumentCaptor.getValue();
|
||||
|
||||
final PendingIntent alarmPi = getNewMockPendingIntent();
|
||||
when(mAppStateTracker.areAlarmsRestrictedByBatterySaver(TEST_CALLING_UID,
|
||||
TEST_CALLING_PACKAGE)).thenReturn(true);
|
||||
setTestAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 7, alarmPi);
|
||||
assertEquals(mNowElapsedTest + INDEFINITE_DELAY, mTestTimer.getElapsed());
|
||||
|
||||
when(mAppStateTracker.areAlarmsRestrictedByBatterySaver(TEST_CALLING_UID,
|
||||
TEST_CALLING_PACKAGE)).thenReturn(false);
|
||||
listener.updateAllAlarms();
|
||||
assertEquals(mNowElapsedTest + 7, mTestTimer.getElapsed());
|
||||
|
||||
when(mAppStateTracker.areAlarmsRestrictedByBatterySaver(TEST_CALLING_UID,
|
||||
TEST_CALLING_PACKAGE)).thenReturn(true);
|
||||
listener.updateAlarmsForUid(TEST_CALLING_UID);
|
||||
assertEquals(mNowElapsedTest + INDEFINITE_DELAY, mTestTimer.getElapsed());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void allowWhileIdleAlarmsInBatterySaver() throws Exception {
|
||||
final ArgumentCaptor<AppStateTrackerImpl.Listener> listenerArgumentCaptor =
|
||||
ArgumentCaptor.forClass(AppStateTrackerImpl.Listener.class);
|
||||
verify(mAppStateTracker).addListener(listenerArgumentCaptor.capture());
|
||||
final AppStateTrackerImpl.Listener listener = listenerArgumentCaptor.getValue();
|
||||
|
||||
final long longDelay = 23;
|
||||
final long shortDelay = 7;
|
||||
setDeviceConfigLong(KEY_ALLOW_WHILE_IDLE_LONG_TIME, longDelay);
|
||||
setDeviceConfigLong(KEY_ALLOW_WHILE_IDLE_SHORT_TIME, shortDelay);
|
||||
|
||||
when(mAppStateTracker.areAlarmsRestrictedByBatterySaver(TEST_CALLING_UID,
|
||||
TEST_CALLING_PACKAGE)).thenReturn(true);
|
||||
setAllowWhileIdleAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 1,
|
||||
getNewMockPendingIntent(), false);
|
||||
setAllowWhileIdleAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 2,
|
||||
getNewMockPendingIntent(), false);
|
||||
|
||||
assertEquals(mNowElapsedTest + 1, mTestTimer.getElapsed());
|
||||
|
||||
mNowElapsedTest += 1;
|
||||
mTestTimer.expire();
|
||||
|
||||
assertEquals(mNowElapsedTest + longDelay, mTestTimer.getElapsed());
|
||||
listener.onUidForeground(TEST_CALLING_UID, true);
|
||||
// The next alarm should be deferred by shortDelay.
|
||||
assertEquals(mNowElapsedTest + shortDelay, mTestTimer.getElapsed());
|
||||
|
||||
mNowElapsedTest = mTestTimer.getElapsed();
|
||||
setAllowWhileIdleAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 1,
|
||||
getNewMockPendingIntent(), false);
|
||||
|
||||
when(mAppStateTracker.isUidInForeground(TEST_CALLING_UID)).thenReturn(true);
|
||||
mTestTimer.expire();
|
||||
// The next alarm should be deferred by shortDelay again.
|
||||
assertEquals(mNowElapsedTest + shortDelay, mTestTimer.getElapsed());
|
||||
|
||||
mNowElapsedTest = mTestTimer.getElapsed();
|
||||
setAllowWhileIdleAlarm(ELAPSED_REALTIME_WAKEUP, mNowElapsedTest + 1,
|
||||
getNewMockPendingIntent(), true);
|
||||
when(mAppStateTracker.isUidInForeground(TEST_CALLING_UID)).thenReturn(false);
|
||||
mTestTimer.expire();
|
||||
final long lastAwiDispatch = mNowElapsedTest;
|
||||
// Unrestricted, so should not be changed.
|
||||
assertEquals(mNowElapsedTest + 1, mTestTimer.getElapsed());
|
||||
|
||||
mNowElapsedTest = mTestTimer.getElapsed();
|
||||
// AWI_unrestricted should not affect normal AWI bookkeeping.
|
||||
// The next alarm is after the short delay but before the long delay.
|
||||
setAllowWhileIdleAlarm(ELAPSED_REALTIME_WAKEUP, lastAwiDispatch + shortDelay + 1,
|
||||
getNewMockPendingIntent(), false);
|
||||
mTestTimer.expire();
|
||||
assertEquals(lastAwiDispatch + longDelay, mTestTimer.getElapsed());
|
||||
|
||||
listener.onUidForeground(TEST_CALLING_UID, true);
|
||||
assertEquals(lastAwiDispatch + shortDelay + 1, mTestTimer.getElapsed());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void dispatchOrder() throws Exception {
|
||||
doReturn(0).when(mService).fuzzForDuration(anyLong());
|
||||
|
||||
Reference in New Issue
Block a user