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

Commit ae001bed authored by Kweku Adams's avatar Kweku Adams Committed by Android (Google) Code Review
Browse files

Merge "Add TARE enable constant."

parents 061857e0 739dd166
Loading
Loading
Loading
Loading
+28 −3
Original line number Diff line number Diff line
@@ -196,7 +196,6 @@ class Agent {
            final int eventId, @Nullable String tag) {
        final long now = System.currentTimeMillis();
        final Ledger ledger = getLedgerLocked(userId, pkgName);
        final boolean wasSolvent = getBalanceLocked(userId, pkgName) > 0;

        final int eventType = getEventType(eventId);
        switch (eventType) {
@@ -400,12 +399,16 @@ class Agent {
        SparseArrayMap<String, OngoingEvent> ongoingEvents =
                mCurrentOngoingEvents.get(userId, pkgName);
        if (ongoingEvents == null) {
            Slog.wtf(TAG, "No ongoing transactions :/");
            // This may occur if TARE goes from disabled to enabled while an event is already
            // occurring.
            Slog.w(TAG, "No ongoing transactions for <" + userId + ">" + pkgName);
            return;
        }
        final OngoingEvent ongoingEvent = ongoingEvents.get(eventId, tag);
        if (ongoingEvent == null) {
            Slog.wtf(TAG, "Nonexistent ongoing transaction "
            // This may occur if TARE goes from disabled to enabled while an event is already
            // occurring.
            Slog.w(TAG, "Nonexistent ongoing transaction "
                    + eventToString(eventId) + (tag == null ? "" : ":" + tag)
                    + " for <" + userId + ">" + pkgName + " ended");
            return;
@@ -768,6 +771,15 @@ class Agent {
                SystemClock.elapsedRealtime() + timeToThresholdMs);
    }

    @GuardedBy("mLock")
    void tearDownLocked() {
        mLedgers.clear();
        mCurrentNarcsInCirculation = 0;
        mCurrentOngoingEvents.clear();
        mBalanceThresholdAlarmListener.dropAllAlarmsLocked();
        mLedgerCleanupAlarmListener.dropAllAlarmsLocked();
    }

    @VisibleForTesting
    static class OngoingEvent {
        public final long startTimeElapsed;
@@ -986,6 +998,12 @@ class Agent {
            }
        }

        @GuardedBy("mLock")
        void dropAllAlarmsLocked() {
            mAlarmQueue.clear();
            setNextAlarmLocked(0);
        }

        @GuardedBy("mLock")
        protected abstract void processExpiredAlarmLocked(int userId, @NonNull String packageName);

@@ -1069,6 +1087,13 @@ class Agent {
        final ActionAffordabilityNote note =
                new ActionAffordabilityNote(bill, listener, mCompleteEconomicPolicy);
        if (actionAffordabilityNotes.add(note)) {
            if (!mIrs.isEnabled()) {
                // When TARE isn't enabled, we always say something is affordable. We also don't
                // want to silently drop affordability change listeners in case TARE becomes enabled
                // because then clients will be in an ambiguous state.
                note.setNewAffordability(true);
                return;
            }
            note.recalculateModifiedPrice(mCompleteEconomicPolicy, userId, pkgName);
            note.setNewAffordability(
                    getBalanceLocked(userId, pkgName) >= note.getCachedModifiedPrice());
+14 −1
Original line number Diff line number Diff line
@@ -40,7 +40,16 @@ class ChargingModifier extends Modifier {
        super();
        mIrs = irs;
        mChargingTracker = new ChargingTracker();
        mChargingTracker.startTracking(irs.getContext());
    }

    @Override
    public void setup() {
        mChargingTracker.startTracking(mIrs.getContext());
    }

    @Override
    public void tearDown() {
        mChargingTracker.stopTracking(mIrs.getContext());
    }

    @Override
@@ -84,6 +93,10 @@ class ChargingModifier extends Modifier {
            mCharging = batteryManager.isCharging();
        }

        public void stopTracking(@NonNull Context context) {
            context.unregisterReceiver(this);
        }

        @Override
        public void onReceive(Context context, Intent intent) {
            final String action = intent.getAction();
+14 −1
Original line number Diff line number Diff line
@@ -40,7 +40,16 @@ class DeviceIdleModifier extends Modifier {
        mIrs = irs;
        mPowerManager = irs.getContext().getSystemService(PowerManager.class);
        mDeviceIdleTracker = new DeviceIdleTracker();
        mDeviceIdleTracker.startTracking(irs.getContext());
    }

    @Override
    public void setup() {
        mDeviceIdleTracker.startTracking(mIrs.getContext());
    }

    @Override
    public void tearDown() {
        mDeviceIdleTracker.stopTracking(mIrs.getContext());
    }

    @Override
@@ -81,6 +90,10 @@ class DeviceIdleModifier extends Modifier {
            mDeviceLightIdle = mPowerManager.isLightDeviceIdleMode();
        }

        void stopTracking(@NonNull Context context) {
            context.unregisterReceiver(this);
        }

        @Override
        public void onReceive(Context context, Intent intent) {
            final String action = intent.getAction();
+12 −2
Original line number Diff line number Diff line
@@ -157,11 +157,21 @@ public abstract class EconomicPolicy {
    }

    @CallSuper
    void onSystemServicesReady() {
    void setup() {
        for (int i = 0; i < NUM_COST_MODIFIERS; ++i) {
            final Modifier modifier = COST_MODIFIER_BY_INDEX[i];
            if (modifier != null) {
                modifier.onSystemServicesReady();
                modifier.setup();
            }
        }
    }

    @CallSuper
    void tearDown() {
        for (int i = 0; i < NUM_COST_MODIFIERS; ++i) {
            final Modifier modifier = COST_MODIFIER_BY_INDEX[i];
            if (modifier != null) {
                modifier.tearDown();
            }
        }
    }
+119 −29
Original line number Diff line number Diff line
@@ -24,11 +24,13 @@ import android.annotation.Nullable;
import android.app.AlarmManager;
import android.app.tare.IEconomyManager;
import android.content.BroadcastReceiver;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.database.ContentObserver;
import android.net.Uri;
import android.os.BatteryManagerInternal;
import android.os.Binder;
@@ -38,6 +40,7 @@ import android.os.Looper;
import android.os.Message;
import android.os.SystemClock;
import android.os.UserHandle;
import android.provider.Settings;
import android.util.ArraySet;
import android.util.IndentingPrintWriter;
import android.util.Log;
@@ -81,6 +84,7 @@ public class InternalResourceService extends SystemService {

    private final Agent mAgent;
    private final CompleteEconomicPolicy mCompleteEconomicPolicy;
    private final ConfigObserver mConfigObserver;
    private final EconomyManagerStub mEconomyManagerStub;

    @NonNull
@@ -91,8 +95,8 @@ public class InternalResourceService extends SystemService {
    @GuardedBy("mLock")
    private final SparseSetArray<String> mUidToPackageCache = new SparseSetArray<>();

    @GuardedBy("mLock")
    private boolean mIsSetup;
    private volatile boolean mIsEnabled;
    private volatile int mBootPhase;
    // In the range [0,100] to represent 0% to 100% battery.
    @GuardedBy("mLock")
    private int mCurrentBatteryLevel;
@@ -185,18 +189,7 @@ public class InternalResourceService extends SystemService {
        mCompleteEconomicPolicy = new CompleteEconomicPolicy(this);
        mAgent = new Agent(this, mCompleteEconomicPolicy);

        final IntentFilter filter = new IntentFilter();
        filter.addAction(Intent.ACTION_BATTERY_LEVEL_CHANGED);
        context.registerReceiverAsUser(mBroadcastReceiver, UserHandle.ALL, filter, null, null);
        final IntentFilter pkgFilter = new IntentFilter();
        pkgFilter.addAction(Intent.ACTION_PACKAGE_FULLY_REMOVED);
        pkgFilter.addAction(Intent.ACTION_PACKAGE_ADDED);
        pkgFilter.addAction(Intent.ACTION_PACKAGE_RESTARTED);
        pkgFilter.addDataScheme("package");
        context.registerReceiverAsUser(mBroadcastReceiver, UserHandle.ALL, pkgFilter, null, null);
        final IntentFilter userFilter = new IntentFilter(Intent.ACTION_USER_REMOVED);
        userFilter.addAction(Intent.ACTION_USER_ADDED);
        context.registerReceiverAsUser(mBroadcastReceiver, UserHandle.ALL, userFilter, null, null);
        mConfigObserver = new ConfigObserver(mHandler, context);

        publishLocalService(EconomyManagerInternal.class, new LocalService());
    }
@@ -208,19 +201,11 @@ public class InternalResourceService extends SystemService {

    @Override
    public void onBootPhase(int phase) {
        mBootPhase = phase;

        if (PHASE_SYSTEM_SERVICES_READY == phase) {
            synchronized (mLock) {
                mCurrentBatteryLevel = getCurrentBatteryLevel();
                // TODO: base on if we have anything persisted
                final boolean isFirstSetup = true;
                if (isFirstSetup) {
                    mHandler.post(this::setupEconomy);
                } else {
                    mIsSetup = true;
                }
                scheduleUnusedWealthReclamationLocked();
                mCompleteEconomicPolicy.onSystemServicesReady();
            }
            mConfigObserver.start();
            setupEverything();
        }
    }

@@ -247,6 +232,10 @@ public class InternalResourceService extends SystemService {
                / 100;
    }

    boolean isEnabled() {
        return mIsEnabled;
    }

    void onBatteryLevelChanged() {
        synchronized (mLock) {
            final int newBatteryLevel = getCurrentBatteryLevel();
@@ -396,11 +385,67 @@ public class InternalResourceService extends SystemService {
        mPkgCache = mPackageManager.getInstalledPackages(0);
    }

    private void setupEconomy() {
    private void registerReceivers() {
        final IntentFilter filter = new IntentFilter();
        filter.addAction(Intent.ACTION_BATTERY_LEVEL_CHANGED);
        getContext().registerReceiverAsUser(mBroadcastReceiver, UserHandle.ALL, filter, null, null);

        final IntentFilter pkgFilter = new IntentFilter();
        pkgFilter.addAction(Intent.ACTION_PACKAGE_FULLY_REMOVED);
        pkgFilter.addAction(Intent.ACTION_PACKAGE_ADDED);
        pkgFilter.addAction(Intent.ACTION_PACKAGE_RESTARTED);
        pkgFilter.addDataScheme("package");
        getContext()
                .registerReceiverAsUser(mBroadcastReceiver, UserHandle.ALL, pkgFilter, null, null);

        final IntentFilter userFilter = new IntentFilter(Intent.ACTION_USER_REMOVED);
        userFilter.addAction(Intent.ACTION_USER_ADDED);
        getContext()
                .registerReceiverAsUser(mBroadcastReceiver, UserHandle.ALL, userFilter, null, null);
    }

    /** Perform long-running and/or heavy setup work. This should be called off the main thread. */
    private void setupHeavyWork() {
        synchronized (mLock) {
            loadInstalledPackageListLocked();
            // TODO: base on if we have anything persisted
            final boolean isFirstSetup = true;
            if (isFirstSetup) {
                mAgent.grantBirthrightsLocked();
            mIsSetup = true;
            }
        }
    }

    private void setupEverything() {
        if (mBootPhase < PHASE_SYSTEM_SERVICES_READY || !mIsEnabled) {
            return;
        }
        synchronized (mLock) {
            registerReceivers();
            mCurrentBatteryLevel = getCurrentBatteryLevel();
            mHandler.post(this::setupHeavyWork);
            scheduleUnusedWealthReclamationLocked();
            mCompleteEconomicPolicy.setup();
        }
    }

    private void tearDownEverything() {
        if (mIsEnabled) {
            return;
        }
        synchronized (mLock) {
            mAgent.tearDownLocked();
            mCompleteEconomicPolicy.tearDown();
            mHandler.post(() -> {
                // Never call out to AlarmManager with the lock held. This sits below AM.
                AlarmManager alarmManager = getContext().getSystemService(AlarmManager.class);
                if (alarmManager != null) {
                    alarmManager.cancel(mUnusedWealthReclamationListener);
                }
            });
            mPkgCache.clear();
            mUidToPackageCache.clear();
            getContext().unregisterReceiver(mBroadcastReceiver);
        }
    }

@@ -487,6 +532,9 @@ public class InternalResourceService extends SystemService {

        @Override
        public boolean canPayFor(int userId, @NonNull String pkgName, @NonNull ActionBill bill) {
            if (!mIsEnabled) {
                return true;
            }
            // TODO: take temp-allowlist into consideration
            long requiredBalance = 0;
            final List<EconomyManagerInternal.AnticipatedAction> projectedActions =
@@ -506,6 +554,9 @@ public class InternalResourceService extends SystemService {
        @Override
        public void noteInstantaneousEvent(int userId, @NonNull String pkgName, int eventId,
                @Nullable String tag) {
            if (!mIsEnabled) {
                return;
            }
            synchronized (mLock) {
                mAgent.noteInstantaneousEventLocked(userId, pkgName, eventId, tag);
            }
@@ -514,6 +565,9 @@ public class InternalResourceService extends SystemService {
        @Override
        public void noteOngoingEventStarted(int userId, @NonNull String pkgName, int eventId,
                @Nullable String tag) {
            if (!mIsEnabled) {
                return;
            }
            synchronized (mLock) {
                final long nowElapsed = SystemClock.elapsedRealtime();
                mAgent.noteOngoingEventLocked(userId, pkgName, eventId, tag, nowElapsed);
@@ -523,6 +577,9 @@ public class InternalResourceService extends SystemService {
        @Override
        public void noteOngoingEventStopped(int userId, @NonNull String pkgName, int eventId,
                @Nullable String tag) {
            if (!mIsEnabled) {
                return;
            }
            final long nowElapsed = SystemClock.elapsedRealtime();
            final long now = System.currentTimeMillis();
            synchronized (mLock) {
@@ -531,6 +588,39 @@ public class InternalResourceService extends SystemService {
        }
    }

    private class ConfigObserver extends ContentObserver {
        private final ContentResolver mContentResolver;

        ConfigObserver(Handler handler, Context context) {
            super(handler);
            mContentResolver = context.getContentResolver();
        }

        public void start() {
            mContentResolver.registerContentObserver(
                    Settings.Global.getUriFor(Settings.Global.ENABLE_TARE), false, this);
            updateConfig();
        }

        @Override
        public void onChange(boolean selfChange) {
            updateConfig();
        }

        private void updateConfig() {
            final boolean isTareEnabled = Settings.Global.getInt(mContentResolver,
                    Settings.Global.ENABLE_TARE, Settings.Global.DEFAULT_ENABLE_TARE) == 1;
            if (mIsEnabled != isTareEnabled) {
                mIsEnabled = isTareEnabled;
                if (mIsEnabled) {
                    setupEverything();
                } else {
                    tearDownEverything();
                }
            }
        }
    }

    private static void dumpHelp(PrintWriter pw) {
        pw.println("Resource Economy (economy) dump options:");
        pw.println("  [-h|--help] [package] ...");
Loading