Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a22bf1cd authored by Lei Yu's avatar Lei Yu Committed by android-build-merger
Browse files

Merge "Fix issues in battery usage accounting" into qt-dev am: 2148c1a2

am: fad8cec5

Change-Id: I9b4a73685b8091760f375b58ad58d501046386d9
parents 754416c2 fad8cec5
Loading
Loading
Loading
Loading
+3 −8
Original line number Diff line number Diff line
@@ -352,15 +352,10 @@ public class BatteryAppListPreferenceController extends AbstractPreferenceContro

    @VisibleForTesting
    boolean shouldHideSipper(BatterySipper sipper) {
        // Don't show hidden system module
        final String packageName = mBatteryUtils.getPackageName(sipper.getUid());
        if (!TextUtils.isEmpty(packageName)
                && AppUtils.isHiddenSystemModule(mContext, packageName)) {
            return true;
        }
        // Don't show over-counted and unaccounted in any condition
        // Don't show over-counted, unaccounted and hidden system module in any condition
        return sipper.drainType == BatterySipper.DrainType.OVERCOUNTED
                || sipper.drainType == BatterySipper.DrainType.UNACCOUNTED;
                || sipper.drainType == BatterySipper.DrainType.UNACCOUNTED
                || mBatteryUtils.isHiddenSystemModule(sipper);
    }

    @VisibleForTesting
+26 −3
Original line number Diff line number Diff line
@@ -47,6 +47,7 @@ import com.android.settings.fuelgauge.batterytip.AnomalyInfo;
import com.android.settings.fuelgauge.batterytip.BatteryDatabaseManager;
import com.android.settings.fuelgauge.batterytip.StatsManagerConfig;
import com.android.settings.overlay.FeatureFactory;
import com.android.settingslib.applications.AppUtils;
import com.android.settingslib.fuelgauge.Estimate;
import com.android.settingslib.fuelgauge.EstimateKt;
import com.android.settingslib.fuelgauge.PowerWhitelistBackend;
@@ -189,8 +190,10 @@ public class BatteryUtils {
                        && sipper.drainType != BatterySipper.DrainType.UNACCOUNTED
                        && sipper.drainType != BatterySipper.DrainType.BLUETOOTH
                        && sipper.drainType != BatterySipper.DrainType.WIFI
                        && sipper.drainType != BatterySipper.DrainType.IDLE) {
                    // Don't add it if it is overcounted, unaccounted, wifi, bluetooth, or screen
                        && sipper.drainType != BatterySipper.DrainType.IDLE
                        && !isHiddenSystemModule(sipper)) {
                    // Don't add it if it is overcounted, unaccounted, wifi, bluetooth, screen
                    // or hidden system modules
                    proportionalSmearPowerMah += sipper.totalPowerMah;
                }
            }
@@ -253,7 +256,27 @@ public class BatteryUtils {
                || drainType == BatterySipper.DrainType.WIFI
                || (sipper.totalPowerMah * SECONDS_IN_HOUR) < MIN_POWER_THRESHOLD_MILLI_AMP
                || mPowerUsageFeatureProvider.isTypeService(sipper)
                || mPowerUsageFeatureProvider.isTypeSystem(sipper);
                || mPowerUsageFeatureProvider.isTypeSystem(sipper)
                || isHiddenSystemModule(sipper);
    }

    /**
     * Return {@code true} if one of packages in {@code sipper} is hidden system modules
     */
    public boolean isHiddenSystemModule(BatterySipper sipper) {
        if (sipper.uidObj == null) {
            return false;
        }
        sipper.mPackages = mPackageManager.getPackagesForUid(sipper.getUid());
        if (sipper.mPackages != null) {
            for (int i = 0, length = sipper.mPackages.length; i < length; i++) {
                if (AppUtils.isHiddenSystemModule(mContext, sipper.mPackages[i])) {
                    return true;
                }
            }
        }

        return false;
    }

    /**
+26 −20
Original line number Diff line number Diff line
@@ -20,7 +20,6 @@ import static com.android.settings.Utils.SETTINGS_PACKAGE_NAME;

import android.content.Context;
import android.os.BatteryStats;
import android.text.format.DateUtils;

import androidx.annotation.VisibleForTesting;

@@ -72,22 +71,33 @@ public class HighUsageDetector implements BatteryTipDetector {
        if (mPolicy.highUsageEnabled && mDischarging) {
            parseBatteryData();
            if (mDataParser.isDeviceHeavilyUsed() || mPolicy.testHighUsageTip) {
                final List<BatterySipper> batterySippers = mBatteryStatsHelper.getUsageList();
                for (int i = 0, size = batterySippers.size(); i < size; i++) {
                    final BatterySipper batterySipper = batterySippers.get(i);
                    if (!mBatteryUtils.shouldHideSipper(batterySipper)) {
                        final long foregroundTimeMs = mBatteryUtils.getProcessTimeMs(
                                BatteryUtils.StatusType.FOREGROUND, batterySipper.uidObj,
                                BatteryStats.STATS_SINCE_CHARGED);
                        if (foregroundTimeMs >= DateUtils.MINUTE_IN_MILLIS) {
                final BatteryStats batteryStats = mBatteryStatsHelper.getStats();
                final List<BatterySipper> batterySippers
                        = new ArrayList<>(mBatteryStatsHelper.getUsageList());
                final double totalPower = mBatteryStatsHelper.getTotalPower();
                final int dischargeAmount = batteryStats != null
                        ? batteryStats.getDischargeAmount(BatteryStats.STATS_SINCE_CHARGED)
                        : 0;

                Collections.sort(batterySippers,
                        (sipper1, sipper2) -> Double.compare(sipper2.totalSmearedPowerMah,
                                sipper1.totalSmearedPowerMah));
                for (BatterySipper batterySipper : batterySippers) {
                    final double percent = mBatteryUtils.calculateBatteryPercent(
                            batterySipper.totalSmearedPowerMah, totalPower, 0, dischargeAmount);
                    if ((percent + 0.5f < 1f) || mBatteryUtils.shouldHideSipper(batterySipper)) {
                        // Don't show it if we should hide or usage percentage is lower than 1%
                        continue;
                    }
                    mHighUsageAppList.add(new AppInfo.Builder()
                            .setUid(batterySipper.getUid())
                            .setPackageName(
                                    mBatteryUtils.getPackageName(batterySipper.getUid()))
                                    .setScreenOnTimeMs(foregroundTimeMs)
                            .build());
                    if (mHighUsageAppList.size() >= mPolicy.highUsageAppCount) {
                        break;
                    }
                    }

                }

                // When in test mode, add an app if necessary
@@ -97,10 +107,6 @@ public class HighUsageDetector implements BatteryTipDetector {
                            .setScreenOnTimeMs(TimeUnit.HOURS.toMillis(3))
                            .build());
                }

                Collections.sort(mHighUsageAppList, Collections.reverseOrder());
                mHighUsageAppList = mHighUsageAppList.subList(0,
                        Math.min(mPolicy.highUsageAppCount, mHighUsageAppList.size()));
            }
        }

+4 −9
Original line number Diff line number Diff line
@@ -20,12 +20,14 @@ import static com.google.common.truth.Truth.assertThat;

import static org.mockito.Matchers.anyInt;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;

import android.content.Context;
import android.content.pm.ModuleInfo;
import android.content.pm.PackageManager;
import android.os.BatteryStats;
import android.os.UserManager;
import android.text.TextUtils;
import android.text.format.DateUtils;
@@ -94,6 +96,7 @@ public class BatteryAppListPreferenceControllerTest {
        when(mNormalBatterySipper.getPackages()).thenReturn(PACKAGE_NAMES);
        when(mNormalBatterySipper.getUid()).thenReturn(UID);
        mNormalBatterySipper.drainType = BatterySipper.DrainType.APP;
        mNormalBatterySipper.uidObj = mock(BatteryStats.Uid.class);

        mPreferenceController = new BatteryAppListPreferenceController(mContext, KEY_APP_LIST, null,
                mSettingsActivity, mFragment);
@@ -203,15 +206,7 @@ public class BatteryAppListPreferenceControllerTest {

    @Test
    public void testShouldHideSipper_hiddenSystemModule_returnTrue() {
        ReflectionHelpers.setStaticField(ApplicationsState.class, "sInstance", null);
        final String packageName = "test.hidden.module";
        final ModuleInfo moduleInfo = new ModuleInfo();
        moduleInfo.setPackageName(packageName);
        moduleInfo.setHidden(true);
        final List<ModuleInfo> modules = new ArrayList<>();
        modules.add(moduleInfo);
        when(mBatteryUtils.getPackageName(anyInt() /* uid */)).thenReturn(packageName);
        when(mPackageManager.getInstalledModules(anyInt() /* flags */)).thenReturn(modules);
        when(mBatteryUtils.isHiddenSystemModule(mNormalBatterySipper)).thenReturn(true);

        assertThat(mPreferenceController.shouldHideSipper(mNormalBatterySipper)).isTrue();
    }
+9 −0
Original line number Diff line number Diff line
@@ -368,6 +368,15 @@ public class BatteryUtilsTest {
        assertThat(mBatteryUtils.shouldHideSipper(mNormalBatterySipper)).isTrue();
    }

    @Test
    public void testShouldHideSipper_hiddenSystemModule_ReturnTrue() {
        mNormalBatterySipper.drainType = BatterySipper.DrainType.APP;
        when(mNormalBatterySipper.getUid()).thenReturn(UID);
        when(mBatteryUtils.isHiddenSystemModule(mNormalBatterySipper)).thenReturn(true);

        assertThat(mBatteryUtils.shouldHideSipper(mNormalBatterySipper)).isTrue();
    }

    @Test
    public void testCalculateBatteryPercent() {
        assertThat(mBatteryUtils.calculateBatteryPercent(BATTERY_SYSTEM_USAGE, TOTAL_BATTERY_USAGE,
Loading