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

Commit 87b83e23 authored by Junyu Lai's avatar Junyu Lai Committed by Automerger Merge Worker
Browse files

Merge "[MS68.1] Register usage callback from NetworkPolicyManagerService" am:...

Merge "[MS68.1] Register usage callback from NetworkPolicyManagerService" am: 145b5711 am: a1472b9b

Original change: https://android-review.googlesource.com/c/platform/frameworks/base/+/1958144

Change-Id: Ic3d9854f2f293b2189f64faee2becc046f52f3b9
parents d9ee2219 a1472b9b
Loading
Loading
Loading
Loading
+2 −1
Original line number Diff line number Diff line
@@ -729,7 +729,8 @@ public class NetworkStatsManager {
     * {@link #unregisterUsageCallback} is called.
     *
     * @param template Template used to match networks. See {@link NetworkTemplate}.
     * @param thresholdBytes Threshold in bytes to be notified on.
     * @param thresholdBytes Threshold in bytes to be notified on. The provided value that lower
     *                       than 2MiB will be clamped for non-privileged callers.
     * @param executor The executor on which callback will be invoked. The provided {@link Executor}
     *                 must run callback sequentially, otherwise the order of callbacks cannot be
     *                 guaranteed.
+7 −5
Original line number Diff line number Diff line
@@ -76,7 +76,7 @@ class NetworkStatsObservers {
     */
    public DataUsageRequest register(DataUsageRequest inputRequest, IUsageCallback callback,
            int callingUid, @NetworkStatsAccess.Level int accessLevel) {
        DataUsageRequest request = buildRequest(inputRequest);
        DataUsageRequest request = buildRequest(inputRequest, callingUid);
        RequestInfo requestInfo = buildRequestInfo(request, callback, callingUid,
                accessLevel);

@@ -194,10 +194,12 @@ class NetworkStatsObservers {
        }
    }

    private DataUsageRequest buildRequest(DataUsageRequest request) {
        // Cap the minimum threshold to a safe default to avoid too many callbacks
        long thresholdInBytes = Math.max(MIN_THRESHOLD_BYTES, request.thresholdInBytes);
        if (thresholdInBytes < request.thresholdInBytes) {
    private DataUsageRequest buildRequest(DataUsageRequest request, int callingUid) {
        // For non-system uid, cap the minimum threshold to a safe default to avoid too
        // many callbacks.
        long thresholdInBytes = (callingUid == Process.SYSTEM_UID ? request.thresholdInBytes
                : Math.max(MIN_THRESHOLD_BYTES, request.thresholdInBytes));
        if (thresholdInBytes > request.thresholdInBytes) {
            Log.w(TAG, "Threshold was too low for " + request
                    + ". Overriding to a safer default of " + thresholdInBytes + " bytes");
        }
+18 −22
Original line number Diff line number Diff line
@@ -24,7 +24,6 @@ import static android.Manifest.permission.MANAGE_SUBSCRIPTION_PLANS;
import static android.Manifest.permission.NETWORK_SETTINGS;
import static android.Manifest.permission.NETWORK_STACK;
import static android.Manifest.permission.OBSERVE_NETWORK_POLICY;
import static android.Manifest.permission.READ_NETWORK_USAGE_HISTORY;
import static android.Manifest.permission.READ_PHONE_STATE;
import static android.Manifest.permission.READ_PRIVILEGED_PHONE_STATE;
import static android.app.PendingIntent.FLAG_IMMUTABLE;
@@ -130,7 +129,6 @@ import static com.android.internal.util.XmlUtils.writeIntAttribute;
import static com.android.internal.util.XmlUtils.writeLongAttribute;
import static com.android.internal.util.XmlUtils.writeStringAttribute;
import static com.android.net.module.util.NetworkStatsUtils.LIMIT_GLOBAL_ALERT;
import static com.android.server.net.NetworkStatsService.ACTION_NETWORK_STATS_UPDATED;

import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT;
import static org.xmlpull.v1.XmlPullParser.END_TAG;
@@ -1012,10 +1010,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
            userFilter.addAction(ACTION_USER_REMOVED);
            mContext.registerReceiver(mUserReceiver, userFilter, null, mHandler);

            // listen for stats update events
            final IntentFilter statsFilter = new IntentFilter(ACTION_NETWORK_STATS_UPDATED);
            mContext.registerReceiver(
                    mStatsReceiver, statsFilter, READ_NETWORK_USAGE_HISTORY, mHandler);
            // listen for stats updated callbacks for interested network types.
            mNetworkStats.registerUsageCallback(new NetworkTemplate.Builder(MATCH_MOBILE).build(),
                    0 /* thresholdBytes */, new HandlerExecutor(mHandler), mStatsCallback);
            mNetworkStats.registerUsageCallback(new NetworkTemplate.Builder(MATCH_WIFI).build(),
                    0 /* thresholdBytes */, new HandlerExecutor(mHandler), mStatsCallback);

            // listen for restrict background changes from notifications
            final IntentFilter allowFilter = new IntentFilter(ACTION_ALLOW_BACKGROUND);
@@ -1220,19 +1219,16 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
    };

    /**
     * Receiver that watches for {@link NetworkStatsManager} updates, which we
     * use to check against {@link NetworkPolicy#warningBytes}.
     * Listener that watches for {@link NetworkStatsManager} updates, which
     * NetworkPolicyManagerService uses to check against {@link NetworkPolicy#warningBytes}.
     */
    private final NetworkStatsBroadcastReceiver mStatsReceiver =
            new NetworkStatsBroadcastReceiver();
    private class NetworkStatsBroadcastReceiver extends BroadcastReceiver {
        private boolean mIsAnyIntentReceived = false;
        @Override
        public void onReceive(Context context, Intent intent) {
            // on background handler thread, and verified
            // READ_NETWORK_USAGE_HISTORY permission above.
    private final StatsCallback mStatsCallback = new StatsCallback();
    private class StatsCallback extends NetworkStatsManager.UsageCallback {
        private boolean mIsAnyCallbackReceived = false;

            mIsAnyIntentReceived = true;
        @Override
        public void onThresholdReached(int networkType, String subscriberId) {
            mIsAnyCallbackReceived = true;

            synchronized (mNetworkPoliciesSecondLock) {
                updateNetworkRulesNL();
@@ -1242,11 +1238,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
        }

        /**
         * Return whether any {@code ACTION_NETWORK_STATS_UPDATED} intent is received.
         * Return whether any callback is received.
         * Used to determine if NetworkStatsService is ready.
         */
        public boolean isAnyIntentReceived() {
            return mIsAnyIntentReceived;
        public boolean isAnyCallbackReceived() {
            return mIsAnyCallbackReceived;
        }
    };

@@ -1473,7 +1469,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {

        // Skip if not ready. NetworkStatsService will block public API calls until it is
        // ready. To prevent NPMS be blocked on that, skip and fail fast instead.
        if (!mStatsReceiver.isAnyIntentReceived()) return null;
        if (!mStatsCallback.isAnyCallbackReceived()) return null;

        final List<NetworkStats.Bucket> stats = mDeps.getNetworkUidBytes(template, start, end);
        for (final NetworkStats.Bucket entry : stats) {
@@ -5470,7 +5466,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
    private long getTotalBytes(NetworkTemplate template, long start, long end) {
        // Skip if not ready. NetworkStatsService will block public API calls until it is
        // ready. To prevent NPMS be blocked on that, skip and fail fast instead.
        if (!mStatsReceiver.isAnyIntentReceived()) return 0;
        if (!mStatsCallback.isAnyCallbackReceived()) return 0;
        return mDeps.getNetworkTotalBytes(template, start, end);
    }

+10 −3
Original line number Diff line number Diff line
@@ -51,6 +51,7 @@ import static android.net.NetworkPolicyManager.uidRulesToString;
import static android.net.NetworkStack.PERMISSION_MAINLINE_NETWORK_STACK;
import static android.net.NetworkStats.METERED_NO;
import static android.net.NetworkStats.METERED_YES;
import static android.net.NetworkTemplate.MATCH_MOBILE;
import static android.net.NetworkTemplate.buildTemplateCarrierMetered;
import static android.net.NetworkTemplate.buildTemplateWifi;
import static android.net.TrafficStats.MB_IN_BYTES;
@@ -71,7 +72,6 @@ import static com.android.server.net.NetworkPolicyManagerService.TYPE_LIMIT_SNOO
import static com.android.server.net.NetworkPolicyManagerService.TYPE_RAPID;
import static com.android.server.net.NetworkPolicyManagerService.TYPE_WARNING;
import static com.android.server.net.NetworkPolicyManagerService.UidBlockedState.getEffectiveBlockedReasons;
import static com.android.server.net.NetworkStatsService.ACTION_NETWORK_STATS_UPDATED;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
@@ -95,6 +95,7 @@ import static org.mockito.Mockito.doNothing;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.reset;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;

@@ -495,8 +496,14 @@ public class NetworkPolicyManagerServiceTest {
        verify(mNetworkManager).registerObserver(networkObserver.capture());
        mNetworkObserver = networkObserver.getValue();

        // Simulate NetworkStatsService broadcast stats updated to signal its readiness.
        mServiceContext.sendBroadcast(new Intent(ACTION_NETWORK_STATS_UPDATED));
        // Catch UsageCallback during systemReady(). Simulate NetworkStatsService triggered
        // stats updated callback to signal its readiness.
        final ArgumentCaptor<NetworkStatsManager.UsageCallback> usageObserver =
                ArgumentCaptor.forClass(NetworkStatsManager.UsageCallback.class);
        verify(mStatsManager, times(2))
                .registerUsageCallback(any(), anyLong(), any(), usageObserver.capture());
        usageObserver.getValue().onThresholdReached(
                new NetworkTemplate.Builder(MATCH_MOBILE).build());

        NetworkPolicy defaultPolicy = mService.buildDefaultCarrierPolicy(0, "");
        mDefaultWarningBytes = defaultPolicy.warningBytes;