Merge "Make BackgroundDexOpt aware of thermal state" into sc-dev
This commit is contained in:
committed by
Android (Google) Code Review
commit
043dc863be
@@ -31,6 +31,9 @@ import android.content.IntentFilter;
|
|||||||
import android.content.pm.PackageInfo;
|
import android.content.pm.PackageInfo;
|
||||||
import android.os.BatteryManagerInternal;
|
import android.os.BatteryManagerInternal;
|
||||||
import android.os.Environment;
|
import android.os.Environment;
|
||||||
|
import android.os.IThermalService;
|
||||||
|
import android.os.PowerManager;
|
||||||
|
import android.os.RemoteException;
|
||||||
import android.os.ServiceManager;
|
import android.os.ServiceManager;
|
||||||
import android.os.SystemProperties;
|
import android.os.SystemProperties;
|
||||||
import android.os.UserHandle;
|
import android.os.UserHandle;
|
||||||
@@ -82,10 +85,15 @@ public class BackgroundDexOptService extends JobService {
|
|||||||
private static final int OPTIMIZE_ABORT_BY_JOB_SCHEDULER = 2;
|
private static final int OPTIMIZE_ABORT_BY_JOB_SCHEDULER = 2;
|
||||||
// Optimizations should be aborted. No space left on device.
|
// Optimizations should be aborted. No space left on device.
|
||||||
private static final int OPTIMIZE_ABORT_NO_SPACE_LEFT = 3;
|
private static final int OPTIMIZE_ABORT_NO_SPACE_LEFT = 3;
|
||||||
|
// Optimizations should be aborted. Thermal throttling level too high.
|
||||||
|
private static final int OPTIMIZE_ABORT_THERMAL = 4;
|
||||||
|
|
||||||
// Used for calculating space threshold for downgrading unused apps.
|
// Used for calculating space threshold for downgrading unused apps.
|
||||||
private static final int LOW_THRESHOLD_MULTIPLIER_FOR_DOWNGRADE = 2;
|
private static final int LOW_THRESHOLD_MULTIPLIER_FOR_DOWNGRADE = 2;
|
||||||
|
|
||||||
|
// Thermal cutoff value used if one isn't defined by a system property.
|
||||||
|
private static final int THERMAL_CUTOFF_DEFAULT = PowerManager.THERMAL_STATUS_MODERATE;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set of failed packages remembered across job runs.
|
* Set of failed packages remembered across job runs.
|
||||||
*/
|
*/
|
||||||
@@ -107,8 +115,14 @@ public class BackgroundDexOptService extends JobService {
|
|||||||
private static final long mDowngradeUnusedAppsThresholdInMillis =
|
private static final long mDowngradeUnusedAppsThresholdInMillis =
|
||||||
getDowngradeUnusedAppsThresholdInMillis();
|
getDowngradeUnusedAppsThresholdInMillis();
|
||||||
|
|
||||||
|
private final IThermalService mThermalService =
|
||||||
|
IThermalService.Stub.asInterface(
|
||||||
|
ServiceManager.getService(Context.THERMAL_SERVICE));
|
||||||
|
|
||||||
private static List<PackagesUpdatedListener> sPackagesUpdatedListeners = new ArrayList<>();
|
private static List<PackagesUpdatedListener> sPackagesUpdatedListeners = new ArrayList<>();
|
||||||
|
|
||||||
|
private int mThermalStatusCutoff = THERMAL_CUTOFF_DEFAULT;
|
||||||
|
|
||||||
public static void schedule(Context context) {
|
public static void schedule(Context context) {
|
||||||
if (isBackgroundDexoptDisabled()) {
|
if (isBackgroundDexoptDisabled()) {
|
||||||
return;
|
return;
|
||||||
@@ -251,12 +265,18 @@ public class BackgroundDexOptService extends JobService {
|
|||||||
Slog.w(TAG, "Idle optimizations aborted because of space constraints.");
|
Slog.w(TAG, "Idle optimizations aborted because of space constraints.");
|
||||||
} else if (result == OPTIMIZE_ABORT_BY_JOB_SCHEDULER) {
|
} else if (result == OPTIMIZE_ABORT_BY_JOB_SCHEDULER) {
|
||||||
Slog.w(TAG, "Idle optimizations aborted by job scheduler.");
|
Slog.w(TAG, "Idle optimizations aborted by job scheduler.");
|
||||||
|
} else if (result == OPTIMIZE_ABORT_THERMAL) {
|
||||||
|
Slog.w(TAG, "Idle optimizations aborted by thermal throttling.");
|
||||||
} else {
|
} else {
|
||||||
Slog.w(TAG, "Idle optimizations ended with unexpected code: " + result);
|
Slog.w(TAG, "Idle optimizations ended with unexpected code: " + result);
|
||||||
}
|
}
|
||||||
if (result != OPTIMIZE_ABORT_BY_JOB_SCHEDULER) {
|
|
||||||
|
if (result == OPTIMIZE_ABORT_THERMAL) {
|
||||||
|
// Abandon our timeslice and reschedule
|
||||||
|
jobFinished(jobParams, /* wantsReschedule */ true);
|
||||||
|
} else if (result != OPTIMIZE_ABORT_BY_JOB_SCHEDULER) {
|
||||||
// Abandon our timeslice and do not reschedule.
|
// Abandon our timeslice and do not reschedule.
|
||||||
jobFinished(jobParams, /* reschedule */ false);
|
jobFinished(jobParams, /* wantsReschedule */ false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.start();
|
}.start();
|
||||||
@@ -542,6 +562,24 @@ public class BackgroundDexOptService extends JobService {
|
|||||||
// JobScheduler requested an early abort.
|
// JobScheduler requested an early abort.
|
||||||
return OPTIMIZE_ABORT_BY_JOB_SCHEDULER;
|
return OPTIMIZE_ABORT_BY_JOB_SCHEDULER;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Abort background dexopt if the device is in a moderate or stronger thermal throttling
|
||||||
|
// state.
|
||||||
|
try {
|
||||||
|
final int thermalStatus = mThermalService.getCurrentThermalStatus();
|
||||||
|
|
||||||
|
if (DEBUG) {
|
||||||
|
Log.i(TAG, "Thermal throttling status during bgdexopt: " + thermalStatus);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (thermalStatus >= mThermalStatusCutoff) {
|
||||||
|
return OPTIMIZE_ABORT_THERMAL;
|
||||||
|
}
|
||||||
|
} catch (RemoteException ex) {
|
||||||
|
// Because this is a intra-process Binder call it is impossible for a RemoteException
|
||||||
|
// to be raised.
|
||||||
|
}
|
||||||
|
|
||||||
long usableSpace = mDataDir.getUsableSpace();
|
long usableSpace = mDataDir.getUsableSpace();
|
||||||
if (usableSpace < lowStorageThreshold) {
|
if (usableSpace < lowStorageThreshold) {
|
||||||
// Rather bail than completely fill up the disk.
|
// Rather bail than completely fill up the disk.
|
||||||
@@ -603,6 +641,9 @@ public class BackgroundDexOptService extends JobService {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
mThermalStatusCutoff =
|
||||||
|
SystemProperties.getInt("dalvik.vm.dexopt.thermal-cutoff", THERMAL_CUTOFF_DEFAULT);
|
||||||
|
|
||||||
boolean result;
|
boolean result;
|
||||||
if (params.getJobId() == JOB_POST_BOOT_UPDATE) {
|
if (params.getJobId() == JOB_POST_BOOT_UPDATE) {
|
||||||
result = runPostBootUpdate(params, pm, pkgs);
|
result = runPostBootUpdate(params, pm, pkgs);
|
||||||
|
|||||||
1
tests/BackgroundDexOptServiceIntegrationTests/OWNERS
Normal file
1
tests/BackgroundDexOptServiceIntegrationTests/OWNERS
Normal file
@@ -0,0 +1 @@
|
|||||||
|
include platform/art:/OWNERS
|
||||||
@@ -20,6 +20,7 @@ import android.app.AlarmManager;
|
|||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.os.Environment;
|
import android.os.Environment;
|
||||||
import android.os.ParcelFileDescriptor;
|
import android.os.ParcelFileDescriptor;
|
||||||
|
import android.os.PowerManager;
|
||||||
import android.os.SystemProperties;
|
import android.os.SystemProperties;
|
||||||
import android.os.storage.StorageManager;
|
import android.os.storage.StorageManager;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
@@ -201,11 +202,16 @@ public final class BackgroundDexOptServiceIntegrationTests {
|
|||||||
fillUpStorage((long) (getStorageLowBytes() * LOW_STORAGE_MULTIPLIER));
|
fillUpStorage((long) (getStorageLowBytes() * LOW_STORAGE_MULTIPLIER));
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO(aeubanks): figure out how to get scheduled bg-dexopt to run
|
|
||||||
private static void runBackgroundDexOpt() throws IOException {
|
private static void runBackgroundDexOpt() throws IOException {
|
||||||
|
runBackgroundDexOpt("Success");
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO(aeubanks): figure out how to get scheduled bg-dexopt to run
|
||||||
|
private static void runBackgroundDexOpt(String expectedStatus) throws IOException {
|
||||||
String result = runShellCommand("cmd package bg-dexopt-job " + PACKAGE_NAME);
|
String result = runShellCommand("cmd package bg-dexopt-job " + PACKAGE_NAME);
|
||||||
if (!result.trim().equals("Success")) {
|
if (!result.trim().equals(expectedStatus)) {
|
||||||
throw new IllegalStateException("Expected command success, received >" + result + "<");
|
throw new IllegalStateException("Expected status: " + expectedStatus
|
||||||
|
+ "; Received: " + result.trim());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -242,6 +248,16 @@ public final class BackgroundDexOptServiceIntegrationTests {
|
|||||||
runShellCommand(String.format("cmd package compile -f -m %s %s", filter, pkg));
|
runShellCommand(String.format("cmd package compile -f -m %s %s", filter, pkg));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Override the thermal status of the device
|
||||||
|
public static void overrideThermalStatus(int status) throws IOException {
|
||||||
|
runShellCommand("cmd thermalservice override-status " + status);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Reset the thermal status of the device
|
||||||
|
public static void resetThermalStatus() throws IOException {
|
||||||
|
runShellCommand("cmd thermalservice reset");
|
||||||
|
}
|
||||||
|
|
||||||
// Test that background dexopt under normal conditions succeeds.
|
// Test that background dexopt under normal conditions succeeds.
|
||||||
@Test
|
@Test
|
||||||
public void testBackgroundDexOpt() throws IOException {
|
public void testBackgroundDexOpt() throws IOException {
|
||||||
@@ -307,4 +323,17 @@ public final class BackgroundDexOptServiceIntegrationTests {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Test that background dexopt job doesn't trigger if the device is under thermal throttling.
|
||||||
|
@Test
|
||||||
|
public void testBackgroundDexOptThermalThrottling() throws IOException {
|
||||||
|
try {
|
||||||
|
compilePackageWithFilter(PACKAGE_NAME, "verify");
|
||||||
|
overrideThermalStatus(PowerManager.THERMAL_STATUS_MODERATE);
|
||||||
|
// The bgdexopt task should fail when onStartJob is run
|
||||||
|
runBackgroundDexOpt("Failure");
|
||||||
|
Assert.assertEquals("verify", getCompilerFilter(PACKAGE_NAME));
|
||||||
|
} finally {
|
||||||
|
resetThermalStatus();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user