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

Commit 1941c97b authored by Bhavya Sokke Mallikarjunappa's avatar Bhavya Sokke Mallikarjunappa Committed by Linux Build Service Account
Browse files

Enable NSRM (network socket request manager)

NSRM is a feature to synchronize app socket requests
to reduce network signalling and there by save some power.

Change-Id: Ice992713994045d0582f8cfb7b6761e2689f2555
Conflicts:
services/core/java/com/android/server/AlarmManagerService.java
parent 0792ef64
Loading
Loading
Loading
Loading
+68 −7
Original line number Diff line number Diff line
/*
 * Copyright (C) 2006 The Android Open Source Project
 * Copyright (c) 2014, The Linux Foundation. All rights reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
@@ -114,6 +115,9 @@ class AlarmManagerService extends SystemService {

    final Object mLock = new Object();

    private final ArrayList<Integer> mTriggeredUids = new ArrayList<Integer>();
    private final ArrayList<Integer> mBlockedUids = new ArrayList<Integer>();

    long mNativeData;
    private long mNextWakeup;
    private long mNextRtcWakeup;
@@ -560,9 +564,10 @@ class AlarmManagerService extends SystemService {
        final BroadcastStats mBroadcastStats;
        final FilterStats mFilterStats;
        final int mAlarmType;
        final int mUid;

        InFlight(AlarmManagerService service, PendingIntent pendingIntent, WorkSource workSource,
                int alarmType, String tag) {
                int alarmType, String tag, int uid) {
            mPendingIntent = pendingIntent;
            mWorkSource = workSource;
            mTag = tag;
@@ -574,6 +579,7 @@ class AlarmManagerService extends SystemService {
            }
            mFilterStats = fs;
            mAlarmType = alarmType;
            mUid = uid;
        }
    }

@@ -1280,6 +1286,44 @@ class AlarmManagerService extends SystemService {
        }
    }

    /* updates the blocked uids, so if a wake lock is acquired to only fire
     * alarm for it, it can be released.
     */
    void updateBlockedUids(int uid, boolean isBlocked) {
        if (localLOGV) Slog.v(TAG, "UpdateBlockedUids: uid = "+uid +" isBlocked = "+isBlocked);
        synchronized(mLock) {
            if(isBlocked) {
                mBlockedUids.add(new Integer(uid));
                if (checkReleaseWakeLock()) {
                    /* all the uids for which the alarms are triggered
                     * are either blocked or have called onSendFinished.
                     */
                    if (mWakeLock.isHeld()) {
                        mWakeLock.release();
                        if (localLOGV)
                            Slog.v(TAG, "AM WakeLock Released Internally in updateBlockedUids");
                    }
                }
            } else {
               mBlockedUids.clear();
            }
        }
    }

    boolean checkReleaseWakeLock() {
        if (mTriggeredUids.size() == 0 || mBlockedUids.size() == 0)
            return false;

        int uid;
        for (int i = 0; i <  mTriggeredUids.size(); i++) {
            uid = mTriggeredUids.get(i);
            if (!mBlockedUids.contains(uid)) {
                return false;
            }
        }
        return true;
    }

    private void removeLocked(PendingIntent operation) {
        boolean didRemove = false;
        for (int i = mAlarmBatches.size() - 1; i >= 0; i--) {
@@ -1555,6 +1599,8 @@ class AlarmManagerService extends SystemService {
        public final AlarmManager.AlarmClockInfo alarmClock;
        public final int userId;
        public PriorityClass priorityClass;
        public int uid;
        public int pid;

        public Alarm(int _type, long _when, long _whenElapsed, long _windowLength, long _maxWhen,
                long _interval, PendingIntent _op, WorkSource _ws,
@@ -1573,6 +1619,8 @@ class AlarmManagerService extends SystemService {
            workSource = _ws;
            alarmClock = _info;
            userId = _userId;
            uid = Binder.getCallingUid();
            pid = Binder.getCallingPid();
        }

        public static String makeTag(PendingIntent pi, int type) {
@@ -1680,15 +1728,16 @@ class AlarmManagerService extends SystemService {
                        mResultReceiver, mHandler);

                // we have an active broadcast so stay awake.
                if (mBroadcastRefCount == 0) {
                if (mBroadcastRefCount == 0 || !mWakeLock.isHeld()) {
                    setWakelockWorkSource(alarm.operation, alarm.workSource,
                            alarm.type, alarm.tag, true);
                    mWakeLock.acquire();
                }
                final InFlight inflight = new InFlight(AlarmManagerService.this,
                        alarm.operation, alarm.workSource, alarm.type, alarm.tag);
                        alarm.operation, alarm.workSource, alarm.type, alarm.tag, alarm.uid);
                mInFlight.add(inflight);
                mBroadcastRefCount++;
                mTriggeredUids.add(new Integer(alarm.uid));

                final BroadcastStats bs = inflight.mBroadcastStats;
                bs.count++;
@@ -1876,11 +1925,10 @@ class AlarmManagerService extends SystemService {
                mWakeLock.setWorkSource(new WorkSource(uid));
                return;
            }
        } catch (Exception e) {
        }

            // Something went wrong; fall back to attributing the lock to the OS
            mWakeLock.setWorkSource(null);
        } catch (Exception e) {
        }
    }

    private class AlarmHandler extends Handler {
@@ -2113,9 +2161,11 @@ class AlarmManagerService extends SystemService {
        public void onSendFinished(PendingIntent pi, Intent intent, int resultCode,
                String resultData, Bundle resultExtras) {
            synchronized (mLock) {
                int uid = 0;
                InFlight inflight = null;
                for (int i=0; i<mInFlight.size(); i++) {
                    if (mInFlight.get(i).mPendingIntent == pi) {
                        uid = mInFlight.get(i).mUid;
                        inflight = mInFlight.remove(i);
                        break;
                    }
@@ -2138,8 +2188,19 @@ class AlarmManagerService extends SystemService {
                    mLog.w("No in-flight alarm for " + pi + " " + intent);
                }
                mBroadcastRefCount--;
                mTriggeredUids.remove(new Integer(uid));

                if (checkReleaseWakeLock()) {
                    if (mWakeLock.isHeld()) {
                        mWakeLock.release();
                        if (localLOGV) Slog.v(TAG, "AM WakeLock Released Internally onSendFinish");
                    }
                }

                if (mBroadcastRefCount == 0) {
                    if (mWakeLock.isHeld()) {
                        mWakeLock.release();
                    }
                    if (mInFlight.size() > 0) {
                        mLog.w("Finished all broadcasts with " + mInFlight.size()
                                + " remaining inflights");
+74 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2007 The Android Open Source Project
 * Copyright (c) 2014, The Linux Foundation. All rights reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
@@ -155,6 +156,9 @@ public final class PowerManagerService extends SystemService
    private static final int POWER_HINT_INTERACTION = 2;
    private static final int POWER_HINT_LOW_POWER = 5;

    // Config value for NSRM
    private static final int DPM_CONFIG_FEATURE_MASK_NSRM = 0x00000004;

    private final Context mContext;
    private final ServiceThread mHandlerThread;
    private final PowerManagerHandler mHandler;
@@ -425,6 +429,9 @@ public final class PowerManagerService extends SystemService
    private final ArrayList<PowerManagerInternal.LowPowerModeListener> mLowPowerModeListeners
            = new ArrayList<PowerManagerInternal.LowPowerModeListener>();

    //track the blocked uids.
    private final ArrayList<Integer> mBlockedUids = new ArrayList<Integer>();

    private native void nativeInit();

    private static native void nativeAcquireSuspendBlocker(String name);
@@ -722,6 +729,15 @@ public final class PowerManagerService extends SystemService
    private void acquireWakeLockInternal(IBinder lock, int flags, String tag, String packageName,
            WorkSource ws, String historyTag, int uid, int pid) {
        synchronized (mLock) {
            if(mBlockedUids.contains(new Integer(uid)) && uid != Process.myUid()) {
                //wakelock acquisition for blocked uid, do not acquire.
                if (DEBUG_SPEW) {
                    Slog.d(TAG, "uid is blocked not acquiring wakeLock flags=0x" +
                            Integer.toHexString(flags) + " tag=" + tag + " uid=" + uid +
                            " pid =" + pid);
                }
                return;
            }
            if (DEBUG_SPEW) {
                Slog.d(TAG, "acquireWakeLockInternal: lock=" + Objects.hashCode(lock)
                        + ", flags=0x" + Integer.toHexString(flags)
@@ -848,13 +864,23 @@ public final class PowerManagerService extends SystemService
            int callingUid) {
        synchronized (mLock) {
            int index = findWakeLockIndexLocked(lock);
            int value = SystemProperties.getInt("persist.dpm.feature", 0);
            boolean isNsrmEnabled = false;

            if ((value & DPM_CONFIG_FEATURE_MASK_NSRM) == DPM_CONFIG_FEATURE_MASK_NSRM)
                isNsrmEnabled = true;

            if (index < 0) {
                if (DEBUG_SPEW) {
                    Slog.d(TAG, "updateWakeLockWorkSourceInternal: lock=" + Objects.hashCode(lock)
                            + " [not found], ws=" + ws);
                }
                if (!isNsrmEnabled) {
                throw new IllegalArgumentException("Wake lock not active: " + lock
                        + " from uid " + callingUid);
                } else {
                    return;
                }
            }

            WakeLock wakeLock = mWakeLocks.get(index);
@@ -873,6 +899,54 @@ public final class PowerManagerService extends SystemService
        }
    }

    /* updates the blocked uids, so if a wake lock is acquired for it
     * can be released.
     */
    public void updateBlockedUids(int uid, boolean isBlocked) {
        synchronized(mLock) {
            if (DEBUG_SPEW) Slog.v(TAG, "updateBlockedUids: uid = "+uid +"isBlocked = "+isBlocked);
            if(isBlocked) {
                mBlockedUids.add(new Integer(uid));
                for (int index = 0; index < mWakeLocks.size(); index++) {
                    WakeLock wl = mWakeLocks.get(index);
                    if(wl != null) {
                        if(wl.mTag.startsWith("*sync*") && wl.mOwnerUid == Process.SYSTEM_UID) {
                            releaseWakeLockInternal(wl.mLock, wl.mFlags);
                            index--;
                            if (DEBUG_SPEW) Slog.v(TAG, "Internally releasing the wakelock"
                                    + "acquired by SyncManager");
                            continue;
                        }
                        // release the wakelock for the blocked uid
                        if (wl.mOwnerUid == uid || checkWorkSourceObjectId(uid, wl)) {
                            releaseWakeLockInternal(wl.mLock, wl.mFlags);
                            index--;
                            if (DEBUG_SPEW) Slog.v(TAG, "Internally releasing it");
                        }
                    }
                }
            }
            else {
                mBlockedUids.remove(new Integer(uid));
            }
        }
    }

    private boolean checkWorkSourceObjectId(int uid, WakeLock wl) {
        try {
            for (int index = 0; index < wl.mWorkSource.size(); index++) {
                if (uid == wl.mWorkSource.get(index)) {
                    if (DEBUG_SPEW) Slog.v(TAG, "WS uid matched");
                    return true;
                }
            }
        }
        catch (Exception e) {
            return false;
        }
        return false;
    }

    private int findWakeLockIndexLocked(IBinder lock) {
        final int count = mWakeLocks.size();
        for (int i = 0; i < count; i++) {
+53 −1
Original line number Diff line number Diff line
/*
 * Copyright (C) 2006 The Android Open Source Project
 * Copyright (c) 2014, The Linux Foundation. All rights reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
@@ -99,6 +100,8 @@ import com.android.server.webkit.WebViewUpdateService;
import com.android.server.wm.WindowManagerService;

import dalvik.system.VMRuntime;
import dalvik.system.PathClassLoader;
import java.lang.reflect.Constructor;

import java.io.File;
import java.util.Timer;
@@ -152,6 +155,7 @@ public final class SystemServer {
    // TODO: remove all of these references by improving dependency resolution and boot phases
    private Installer mInstaller;
    private PowerManagerService mPowerManagerService;
    private AlarmManagerService mAlarmManagerService;
    private ActivityManagerService mActivityManagerService;
    private DisplayManagerService mDisplayManagerService;
    private PackageManagerService mPackageManagerService;
@@ -462,7 +466,7 @@ public final class SystemServer {
            consumerIr = new ConsumerIrService(context);
            ServiceManager.addService(Context.CONSUMER_IR_SERVICE, consumerIr);

            mSystemServiceManager.startService(AlarmManagerService.class);
            mAlarmManagerService = mSystemServiceManager.startService(AlarmManagerService.class);
            alarm = IAlarmManager.Stub.asInterface(
                    ServiceManager.getService(Context.ALARM_SERVICE));

@@ -695,6 +699,12 @@ public final class SystemServer {
                } catch (Throwable e) {
                    reportWtf("starting Service Discovery Service", e);
                }
                try {
                    Slog.i(TAG, "DPM Service");
                    startDpmService(context, this);
                } catch (Throwable e) {
                    reportWtf("starting DpmService", e);
                }
            }

            if (!disableNonCoreServices) {
@@ -1217,4 +1227,46 @@ public final class SystemServer {
        //Slog.d(TAG, "Starting service: " + intent);
        context.startServiceAsUser(intent, UserHandle.OWNER);
    }

    private static final void startDpmService(Context context, SystemServer systemServer) {
        try {
            Object dpmObj = null;
            int dpmFeature = SystemProperties.getInt("persist.dpm.feature", 0);
            Slog.i(TAG, "DPM configuration set to " + dpmFeature);

            if (dpmFeature > 0 && dpmFeature < 8) {
                PathClassLoader dpmClassLoader =
                    new PathClassLoader("/system/framework/com.qti.dpmframework.jar",
                            ClassLoader.getSystemClassLoader());
                Class dpmClass = dpmClassLoader.loadClass("com.qti.dpm.DpmService");
                Constructor dpmConstructor = dpmClass.getConstructor(
                        new Class[] {Context.class, SystemServer.class});
                dpmObj = dpmConstructor.newInstance(context, systemServer);
                try {
                    if(dpmObj != null && (dpmObj instanceof IBinder)) {
                        ServiceManager.addService("dpmservice", (IBinder)dpmObj);
                        Slog.i(TAG, "Created DPM Service");
                    }
                } catch (Exception e) {
                    Slog.i(TAG, "starting DPM Service", e);
                }
            }
        } catch (Throwable e) {
            Slog.i(TAG, "starting DPM Service", e);
        }
    }


    public void updateBlockedUids(int uid, boolean isBlocked) {
        try {
            mAlarmManagerService.updateBlockedUids(uid, isBlocked);
        } catch (NullPointerException e) {
            Slog.w(TAG, "Could Not Update blocked Uids with alarmManager" + e);
        }
        try {
            mPowerManagerService.updateBlockedUids(uid, isBlocked);
        } catch (NullPointerException e) {
            Slog.w(TAG, "Could Not Update blocked Uids with powerManager" + e);
        }
    }
}