Merge changes from topic 'framework-net-aosp'

* changes:
  DO NOT MERGE: frameworks-test: adding missing @SmallTest
  DO NOT MERGE: Netd events: record connect() success/errno
  DO NOT MERGE: Add missing dependency.
  DO NOT MERGE: Show notification for always-on app VPN
  DO NOT MERGE: Implement metered tracking for NetworkStats summary queries.
  DO NOT MERGE: NetworkMonitor: send one DNS probe per web probe
  DO NOT MERGE: NetworkMonitor metrics: add first validation information
  DO NOT MERGE: APF: also drop any ICMPv6 RSs
  DO NOT MERGE: ConnectivityServiceTest: fix testAvoidBadWifiSettings
  DO NOT MERGE: Fix ConnectivityServiceTest testRequestBenchmark
  DO NOT MERGE: Switch over to new "time.android.com" NTP pool.
  DO NOT MERGE: Define API for metering network stats buckets.
  DO NOT MERGE: Refactored NetworkStatsServiceTest to use Mockito instead of EasyMock.
  DO NOT MERGE: Use @Ignore to explicitly disable a @Test method.
  DO NOT MERGE: Fixed NetworkStatsServiceTest and converted it to JUnit4.
  DO NOT MERGE: VPN network stat accounting changes.
  DO NOT MERGE: ConnectivityThread: use lazy holder idiom
  DO NOT MERGE: ConnectivityManager: use ConnectivityThread looper
  DO NOT MERGE: ConnectivityManager: a simpler CallbackHandler
  DO NOT MERGE: Indicate the NsdServiceInfo attributes are only filled in for a resolved service.
  DO NOT MERGE: Add a null check for the OnStartTetheringCallback.
This commit is contained in:
Lorenzo Colitti
2016-12-09 09:11:21 +00:00
committed by Gerrit Code Review
10 changed files with 818 additions and 691 deletions

View File

@@ -2079,6 +2079,8 @@ public class ConnectivityManager {
@SystemApi @SystemApi
public void startTethering(int type, boolean showProvisioningUi, public void startTethering(int type, boolean showProvisioningUi,
final OnStartTetheringCallback callback, Handler handler) { final OnStartTetheringCallback callback, Handler handler) {
checkNotNull(callback, "OnStartTetheringCallback cannot be null.");
ResultReceiver wrappedCallback = new ResultReceiver(handler) { ResultReceiver wrappedCallback = new ResultReceiver(handler) {
@Override @Override
protected void onReceiveResult(int resultCode, Bundle resultData) { protected void onReceiveResult(int resultCode, Bundle resultData) {
@@ -2089,6 +2091,7 @@ public class ConnectivityManager {
} }
} }
}; };
try { try {
mService.startTethering(type, wrappedCallback, showProvisioningUi); mService.startTethering(type, wrappedCallback, showProvisioningUi);
} catch (RemoteException e) { } catch (RemoteException e) {
@@ -2657,6 +2660,7 @@ public class ConnectivityManager {
public static final int CALLBACK_IP_CHANGED = BASE + 7; public static final int CALLBACK_IP_CHANGED = BASE + 7;
/** @hide */ /** @hide */
public static final int CALLBACK_RELEASED = BASE + 8; public static final int CALLBACK_RELEASED = BASE + 8;
// TODO: consider deleting CALLBACK_EXIT and shifting following enum codes down by 1.
/** @hide */ /** @hide */
public static final int CALLBACK_EXIT = BASE + 9; public static final int CALLBACK_EXIT = BASE + 9;
/** @hide obj = NetworkCapabilities, arg1 = seq number */ /** @hide obj = NetworkCapabilities, arg1 = seq number */
@@ -2687,24 +2691,17 @@ public class ConnectivityManager {
} }
private class CallbackHandler extends Handler { private class CallbackHandler extends Handler {
private final HashMap<NetworkRequest, NetworkCallback>mCallbackMap;
private final AtomicInteger mRefCount;
private static final String TAG = "ConnectivityManager.CallbackHandler"; private static final String TAG = "ConnectivityManager.CallbackHandler";
private final ConnectivityManager mCm;
private static final boolean DBG = false; private static final boolean DBG = false;
CallbackHandler(Looper looper, HashMap<NetworkRequest, NetworkCallback>callbackMap, CallbackHandler(Looper looper) {
AtomicInteger refCount, ConnectivityManager cm) {
super(looper); super(looper);
mCallbackMap = callbackMap;
mRefCount = refCount;
mCm = cm;
} }
@Override @Override
public void handleMessage(Message message) { public void handleMessage(Message message) {
NetworkRequest request = (NetworkRequest) getObject(message, NetworkRequest.class); NetworkRequest request = getObject(message, NetworkRequest.class);
Network network = (Network) getObject(message, Network.class); Network network = getObject(message, Network.class);
if (DBG) { if (DBG) {
Log.d(TAG, whatToString(message.what) + " for network " + network); Log.d(TAG, whatToString(message.what) + " for network " + network);
} }
@@ -2747,9 +2744,7 @@ public class ConnectivityManager {
case CALLBACK_CAP_CHANGED: { case CALLBACK_CAP_CHANGED: {
NetworkCallback callback = getCallback(request, "CAP_CHANGED"); NetworkCallback callback = getCallback(request, "CAP_CHANGED");
if (callback != null) { if (callback != null) {
NetworkCapabilities cap = (NetworkCapabilities)getObject(message, NetworkCapabilities cap = getObject(message, NetworkCapabilities.class);
NetworkCapabilities.class);
callback.onCapabilitiesChanged(network, cap); callback.onCapabilitiesChanged(network, cap);
} }
break; break;
@@ -2757,9 +2752,7 @@ public class ConnectivityManager {
case CALLBACK_IP_CHANGED: { case CALLBACK_IP_CHANGED: {
NetworkCallback callback = getCallback(request, "IP_CHANGED"); NetworkCallback callback = getCallback(request, "IP_CHANGED");
if (callback != null) { if (callback != null) {
LinkProperties lp = (LinkProperties)getObject(message, LinkProperties lp = getObject(message, LinkProperties.class);
LinkProperties.class);
callback.onLinkPropertiesChanged(network, lp); callback.onLinkPropertiesChanged(network, lp);
} }
break; break;
@@ -2779,24 +2772,16 @@ public class ConnectivityManager {
break; break;
} }
case CALLBACK_RELEASED: { case CALLBACK_RELEASED: {
NetworkCallback callback = null; final NetworkCallback callback;
synchronized(mCallbackMap) { synchronized(sCallbacks) {
callback = mCallbackMap.remove(request); callback = sCallbacks.remove(request);
} }
if (callback != null) { if (callback == null) {
synchronized(mRefCount) {
if (mRefCount.decrementAndGet() == 0) {
getLooper().quit();
}
}
} else {
Log.e(TAG, "callback not found for RELEASED message"); Log.e(TAG, "callback not found for RELEASED message");
} }
break; break;
} }
case CALLBACK_EXIT: { case CALLBACK_EXIT: {
Log.d(TAG, "Listener quitting");
getLooper().quit();
break; break;
} }
case EXPIRE_LEGACY_REQUEST: { case EXPIRE_LEGACY_REQUEST: {
@@ -2806,14 +2791,14 @@ public class ConnectivityManager {
} }
} }
private Object getObject(Message msg, Class c) { private <T> T getObject(Message msg, Class<T> c) {
return msg.getData().getParcelable(c.getSimpleName()); return (T) msg.getData().getParcelable(c.getSimpleName());
} }
private NetworkCallback getCallback(NetworkRequest req, String name) { private NetworkCallback getCallback(NetworkRequest req, String name) {
NetworkCallback callback; NetworkCallback callback;
synchronized(mCallbackMap) { synchronized(sCallbacks) {
callback = mCallbackMap.get(req); callback = sCallbacks.get(req);
} }
if (callback == null) { if (callback == null) {
Log.e(TAG, "callback not found for " + name + " message"); Log.e(TAG, "callback not found for " + name + " message");
@@ -2822,63 +2807,56 @@ public class ConnectivityManager {
} }
} }
private void incCallbackHandlerRefCount() { private CallbackHandler getHandler() {
synchronized(sCallbackRefCount) { synchronized (sCallbacks) {
if (sCallbackRefCount.incrementAndGet() == 1) { if (sCallbackHandler == null) {
// TODO: switch this to ConnectivityThread sCallbackHandler = new CallbackHandler(ConnectivityThread.getInstanceLooper());
HandlerThread callbackThread = new HandlerThread("ConnectivityManager");
callbackThread.start();
sCallbackHandler = new CallbackHandler(callbackThread.getLooper(),
sNetworkCallback, sCallbackRefCount, this);
} }
return sCallbackHandler;
} }
} }
private void decCallbackHandlerRefCount() { static final HashMap<NetworkRequest, NetworkCallback> sCallbacks = new HashMap<>();
synchronized(sCallbackRefCount) { static CallbackHandler sCallbackHandler;
if (sCallbackRefCount.decrementAndGet() == 0) {
sCallbackHandler.obtainMessage(CALLBACK_EXIT).sendToTarget();
sCallbackHandler = null;
}
}
}
static final HashMap<NetworkRequest, NetworkCallback> sNetworkCallback =
new HashMap<NetworkRequest, NetworkCallback>();
static final AtomicInteger sCallbackRefCount = new AtomicInteger(0);
static CallbackHandler sCallbackHandler = null;
private final static int LISTEN = 1; private final static int LISTEN = 1;
private final static int REQUEST = 2; private final static int REQUEST = 2;
private NetworkRequest sendRequestForNetwork(NetworkCapabilities need, private NetworkRequest sendRequestForNetwork(NetworkCapabilities need,
NetworkCallback networkCallback, int timeoutMs, int action, NetworkCallback callback, int timeoutMs, int action, int legacyType) {
int legacyType) { return sendRequestForNetwork(need, callback, getHandler(), timeoutMs, action, legacyType);
if (networkCallback == null) { }
private NetworkRequest sendRequestForNetwork(NetworkCapabilities need,
NetworkCallback callback, Handler handler, int timeoutMs, int action, int legacyType) {
if (callback == null) {
throw new IllegalArgumentException("null NetworkCallback"); throw new IllegalArgumentException("null NetworkCallback");
} }
if (need == null && action != REQUEST) { if (need == null && action != REQUEST) {
throw new IllegalArgumentException("null NetworkCapabilities"); throw new IllegalArgumentException("null NetworkCapabilities");
} }
// TODO: throw an exception if callback.networkRequest is not null.
// http://b/20701525
final NetworkRequest request;
try { try {
incCallbackHandlerRefCount(); synchronized(sCallbacks) {
synchronized(sNetworkCallback) { Messenger messenger = new Messenger(handler);
Binder binder = new Binder();
if (action == LISTEN) { if (action == LISTEN) {
networkCallback.networkRequest = mService.listenForNetwork(need, request = mService.listenForNetwork(need, messenger, binder);
new Messenger(sCallbackHandler), new Binder());
} else { } else {
networkCallback.networkRequest = mService.requestNetwork(need, request = mService.requestNetwork(
new Messenger(sCallbackHandler), timeoutMs, new Binder(), legacyType); need, messenger, timeoutMs, binder, legacyType);
} }
if (networkCallback.networkRequest != null) { if (request != null) {
sNetworkCallback.put(networkCallback.networkRequest, networkCallback); sCallbacks.put(request, callback);
} }
callback.networkRequest = request;
} }
} catch (RemoteException e) { } catch (RemoteException e) {
throw e.rethrowFromSystemServer(); throw e.rethrowFromSystemServer();
} }
if (networkCallback.networkRequest == null) decCallbackHandlerRefCount(); return request;
return networkCallback.networkRequest;
} }
/** /**

View File

@@ -27,25 +27,30 @@ import android.os.Looper;
* @hide * @hide
*/ */
public final class ConnectivityThread extends HandlerThread { public final class ConnectivityThread extends HandlerThread {
private static ConnectivityThread sInstance;
// A class implementing the lazy holder idiom: the unique static instance
// of ConnectivityThread is instantiated in a thread-safe way (guaranteed by
// the language specs) the first time that Singleton is referenced in get()
// or getInstanceLooper().
private static class Singleton {
private static final ConnectivityThread INSTANCE = createInstance();
}
private ConnectivityThread() { private ConnectivityThread() {
super("ConnectivityThread"); super("ConnectivityThread");
} }
private static synchronized ConnectivityThread getInstance() { private static ConnectivityThread createInstance() {
if (sInstance == null) { ConnectivityThread t = new ConnectivityThread();
sInstance = new ConnectivityThread(); t.start();
sInstance.start(); return t;
}
return sInstance;
} }
public static ConnectivityThread get() { public static ConnectivityThread get() {
return getInstance(); return Singleton.INSTANCE;
} }
public static Looper getInstanceLooper() { public static Looper getInstanceLooper() {
return getInstance().getLooper(); return Singleton.INSTANCE.getLooper();
} }
} }

View File

@@ -16,6 +16,9 @@
package android.net; package android.net;
import static android.net.NetworkStats.METERED_ALL;
import static android.net.NetworkStats.METERED_NO;
import static android.net.NetworkStats.METERED_YES;
import static android.net.NetworkStats.ROAMING_ALL; import static android.net.NetworkStats.ROAMING_ALL;
import static android.net.NetworkStats.ROAMING_NO; import static android.net.NetworkStats.ROAMING_NO;
import static android.net.NetworkStats.ROAMING_YES; import static android.net.NetworkStats.ROAMING_YES;
@@ -45,103 +48,124 @@ public class NetworkStatsTest extends TestCase {
private static final long TEST_START = 1194220800000L; private static final long TEST_START = 1194220800000L;
public void testFindIndex() throws Exception { public void testFindIndex() throws Exception {
final NetworkStats stats = new NetworkStats(TEST_START, 4) final NetworkStats stats = new NetworkStats(TEST_START, 5)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, 0L, .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1024L,
0L, 10) 8L, 0L, 0L, 10)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 1024L, .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 0L, 0L,
8L, 11) 1024L, 8L, 11)
.addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 0L, 0L,
1024L, 8L, 12) 1024L, 8L, 11)
.addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_YES, 1024L, 8L, .addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1024L,
1024L, 8L, 12); 8L, 1024L, 8L, 12)
.addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_YES, 1024L,
8L, 1024L, 8L, 12);
assertEquals(3, stats.findIndex(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_YES)); assertEquals(4, stats.findIndex(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, METERED_YES,
assertEquals(2, stats.findIndex(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO)); ROAMING_YES));
assertEquals(1, stats.findIndex(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO)); assertEquals(3, stats.findIndex(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, METERED_NO,
assertEquals(0, stats.findIndex(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO)); ROAMING_NO));
assertEquals(-1, stats.findIndex(TEST_IFACE, 6, SET_DEFAULT, TAG_NONE, ROAMING_NO)); assertEquals(2, stats.findIndex(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_YES,
ROAMING_NO));
assertEquals(1, stats.findIndex(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO,
ROAMING_NO));
assertEquals(0, stats.findIndex(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO,
ROAMING_NO));
assertEquals(-1, stats.findIndex(TEST_IFACE, 6, SET_DEFAULT, TAG_NONE, METERED_NO,
ROAMING_NO));
} }
public void testFindIndexHinted() { public void testFindIndexHinted() {
final NetworkStats stats = new NetworkStats(TEST_START, 3) final NetworkStats stats = new NetworkStats(TEST_START, 3)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, 0L, .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1024L,
0L, 10) 8L, 0L, 0L, 10)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 1024L, .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 0L, 0L,
8L, 11) 1024L, 8L, 11)
.addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, .addValues(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1024L,
1024L, 8L, 12) 8L, 1024L, 8L, 12)
.addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 1024L, 8L, .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO,
0L, 0L, 10) 1024L, 8L, 0L, 0L, 10)
.addValues(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 0L, 0L, 1024L, .addValues(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D, METERED_NO, ROAMING_NO, 0L, 0L,
8L, 11) 1024L, 8L, 11)
.addValues(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, .addValues(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D, METERED_YES, ROAMING_NO, 0L, 0L,
1024L, 8L, 12) 1024L, 8L, 11)
.addValues(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, ROAMING_YES, 1024L, 8L, .addValues(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1024L,
1024L, 8L, 12); 8L, 1024L, 8L, 12)
.addValues(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_YES, 1024L,
8L, 1024L, 8L, 12);
// verify that we correctly find across regardless of hinting // verify that we correctly find across regardless of hinting
for (int hint = 0; hint < stats.size(); hint++) { for (int hint = 0; hint < stats.size(); hint++) {
assertEquals(0, stats.findIndexHinted(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, assertEquals(0, stats.findIndexHinted(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE,
ROAMING_NO, hint)); METERED_NO, ROAMING_NO, hint));
assertEquals(1, stats.findIndexHinted(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, assertEquals(1, stats.findIndexHinted(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE,
ROAMING_NO, hint)); METERED_NO, ROAMING_NO, hint));
assertEquals(2, stats.findIndexHinted(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, assertEquals(2, stats.findIndexHinted(TEST_IFACE, 102, SET_DEFAULT, TAG_NONE,
ROAMING_NO, hint)); METERED_NO, ROAMING_NO, hint));
assertEquals(3, stats.findIndexHinted(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, assertEquals(3, stats.findIndexHinted(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE,
ROAMING_NO, hint)); METERED_NO, ROAMING_NO, hint));
assertEquals(4, stats.findIndexHinted(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D, assertEquals(4, stats.findIndexHinted(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D,
ROAMING_NO, hint)); METERED_NO, ROAMING_NO, hint));
assertEquals(5, stats.findIndexHinted(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, assertEquals(5, stats.findIndexHinted(TEST_IFACE2, 101, SET_DEFAULT, 0xF00D,
ROAMING_NO, hint)); METERED_YES, ROAMING_NO, hint));
assertEquals(6, stats.findIndexHinted(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE, assertEquals(6, stats.findIndexHinted(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE,
ROAMING_YES, hint)); METERED_NO, ROAMING_NO, hint));
assertEquals(7, stats.findIndexHinted(TEST_IFACE2, 102, SET_DEFAULT, TAG_NONE,
METERED_YES, ROAMING_YES, hint));
assertEquals(-1, stats.findIndexHinted(TEST_IFACE, 6, SET_DEFAULT, TAG_NONE, assertEquals(-1, stats.findIndexHinted(TEST_IFACE, 6, SET_DEFAULT, TAG_NONE,
ROAMING_NO, hint)); METERED_NO, ROAMING_NO, hint));
} }
} }
public void testAddEntryGrow() throws Exception { public void testAddEntryGrow() throws Exception {
final NetworkStats stats = new NetworkStats(TEST_START, 3); final NetworkStats stats = new NetworkStats(TEST_START, 4);
assertEquals(0, stats.size()); assertEquals(0, stats.size());
assertEquals(3, stats.internalSize()); assertEquals(4, stats.internalSize());
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L, 1L, 2L, stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1L, 1L,
2L, 3);
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 2L, 2L, 2L,
2L, 4);
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 3L, 3L, 2L,
2L, 5);
assertEquals(3, stats.size());
assertEquals(3, stats.internalSize());
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 4L, 40L, 4L,
40L, 7);
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 5L, 50L, 4L,
40L, 8);
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 6L, 60L, 5L,
50L, 10);
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 7L, 70L, 5L,
50L, 11);
assertEquals(7, stats.size());
assertTrue(stats.internalSize() >= 7);
assertValues(stats, 0, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L, 1L,
2L, 2L, 3); 2L, 2L, 3);
assertValues(stats, 1, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 2L, 2L, stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 2L, 2L,
2L, 2L, 4); 2L, 2L, 4);
assertValues(stats, 2, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 3L, 3L, stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_YES, 3L,
2L, 2L, 5); 3L, 2L, 2L, 5);
assertValues(stats, 3, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 4L, stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_YES, 3L,
3L, 2L, 2L, 5);
assertEquals(4, stats.size());
assertEquals(4, stats.internalSize());
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 4L,
40L, 4L, 40L, 7); 40L, 4L, 40L, 7);
assertValues(stats, 4, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 5L, stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 5L,
50L, 4L, 40L, 8); 50L, 4L, 40L, 8);
assertValues(stats, 5, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_NO, 6L, stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 6L,
60L, 5L, 50L, 10); 60L, 5L, 50L, 10);
assertValues(stats, 6, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, ROAMING_YES, 7L, stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_YES, 7L,
70L, 5L, 50L, 11); 70L, 5L, 50L, 11);
stats.addValues(TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_YES, 7L,
70L, 5L, 50L, 11);
assertEquals(9, stats.size());
assertTrue(stats.internalSize() >= 9);
assertValues(stats, 0, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
1L, 1L, 2L, 2L, 3);
assertValues(stats, 1, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
2L, 2L, 2L, 2L, 4);
assertValues(stats, 2, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_YES,
3L, 3L, 2L, 2L, 5);
assertValues(stats, 3, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_YES,
ROAMING_YES, 3L, 3L, 2L, 2L, 5);
assertValues(stats, 4, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
4L, 40L, 4L, 40L, 7);
assertValues(stats, 5, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
5L, 50L, 4L, 40L, 8);
assertValues(stats, 6, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
6L, 60L, 5L, 50L, 10);
assertValues(stats, 7, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_YES,
7L, 70L, 5L, 50L, 11);
assertValues(stats, 8, TEST_IFACE, TEST_UID, SET_DEFAULT, TAG_NONE, METERED_YES,
ROAMING_YES, 7L, 70L, 5L, 50L, 11);
} }
public void testCombineExisting() throws Exception { public void testCombineExisting() throws Exception {
@@ -152,20 +176,18 @@ public class NetworkStatsTest extends TestCase {
stats.combineValues(TEST_IFACE, 1001, SET_DEFAULT, TAG_NONE, -128L, -1L, stats.combineValues(TEST_IFACE, 1001, SET_DEFAULT, TAG_NONE, -128L, -1L,
-128L, -1L, -1); -128L, -1L, -1);
assertValues(stats, 0, TEST_IFACE, 1001, SET_DEFAULT, TAG_NONE, ROAMING_NO, 384L, 3L, assertValues(stats, 0, TEST_IFACE, 1001, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
128L, 1L, 9); 384L, 3L, 128L, 1L, 9);
assertValues(stats, 1, TEST_IFACE, 1001, SET_DEFAULT, 0xff, ROAMING_NO, 128L, 1L, 128L, assertValues(stats, 1, TEST_IFACE, 1001, SET_DEFAULT, 0xff, METERED_NO, ROAMING_NO, 128L,
1L, 2); 1L, 128L, 1L, 2);
// now try combining that should create row // now try combining that should create row
stats.combineValues(TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, 128L, 1L, stats.combineValues(TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, 128L, 1L, 128L, 1L, 3);
128L, 1L, 3); assertValues(stats, 2, TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
assertValues(stats, 2, TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 1L, 128L, 1L, 128L, 1L, 3);
128L, 1L, 3); stats.combineValues(TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, 128L, 1L, 128L, 1L, 3);
stats.combineValues(TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, 128L, 1L, assertValues(stats, 2, TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
128L, 1L, 3); 256L, 2L, 256L, 2L, 6);
assertValues(stats, 2, TEST_IFACE, 5005, SET_DEFAULT, TAG_NONE, ROAMING_NO, 256L, 2L,
256L, 2L, 6);
} }
public void testSubtractIdenticalData() throws Exception { public void testSubtractIdenticalData() throws Exception {
@@ -180,10 +202,10 @@ public class NetworkStatsTest extends TestCase {
final NetworkStats result = after.subtract(before); final NetworkStats result = after.subtract(before);
// identical data should result in zero delta // identical data should result in zero delta
assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L, assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 0L,
0L, 0); 0L, 0L, 0L, 0);
assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L, assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 0L,
0L, 0); 0L, 0L, 0L, 0);
} }
public void testSubtractIdenticalRows() throws Exception { public void testSubtractIdenticalRows() throws Exception {
@@ -198,10 +220,10 @@ public class NetworkStatsTest extends TestCase {
final NetworkStats result = after.subtract(before); final NetworkStats result = after.subtract(before);
// expect delta between measurements // expect delta between measurements
assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L, 1L, 2L, assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1L,
1L, 4); 1L, 2L, 1L, 4);
assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 3L, 1L, 4L, assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 3L,
1L, 8); 1L, 4L, 1L, 8);
} }
public void testSubtractNewRows() throws Exception { public void testSubtractNewRows() throws Exception {
@@ -217,12 +239,12 @@ public class NetworkStatsTest extends TestCase {
final NetworkStats result = after.subtract(before); final NetworkStats result = after.subtract(before);
// its okay to have new rows // its okay to have new rows
assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L, assertValues(result, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 0L,
0L, 0); 0L, 0L, 0L, 0);
assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 0L, 0L, 0L, assertValues(result, 1, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 0L,
0L, 0); 0L, 0L, 0L, 0);
assertValues(result, 2, TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1024L, 8L, assertValues(result, 2, TEST_IFACE, 102, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
1024L, 8L, 20); 1024L, 8L, 1024L, 8L, 20);
} }
public void testSubtractMissingRows() throws Exception { public void testSubtractMissingRows() throws Exception {
@@ -237,8 +259,8 @@ public class NetworkStatsTest extends TestCase {
// should silently drop omitted rows // should silently drop omitted rows
assertEquals(1, result.size()); assertEquals(1, result.size());
assertValues(result, 0, TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1L, assertValues(result, 0, TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, METERED_NO,
2L, 3L, 4L, 0); ROAMING_NO, 1L, 2L, 3L, 4L, 0);
assertEquals(4L, result.getTotalBytes()); assertEquals(4L, result.getTotalBytes());
} }
@@ -263,13 +285,22 @@ public class NetworkStatsTest extends TestCase {
.addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, 8L, 0L, 0L, 0L, 0L); .addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, 8L, 0L, 0L, 0L, 0L);
assertEquals(64L, uidTag.getTotalBytes()); assertEquals(64L, uidTag.getTotalBytes());
final NetworkStats uidMetered = new NetworkStats(TEST_START, 3)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 32L, 0L,
0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 32L, 0L,
0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 32L, 0L,
0L, 0L, 0L);
assertEquals(96L, uidMetered.getTotalBytes());
final NetworkStats uidRoaming = new NetworkStats(TEST_START, 3) final NetworkStats uidRoaming = new NetworkStats(TEST_START, 3)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L, .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 32L, 0L,
0L) 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L, .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 32L, 0L,
0L) 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_YES, 32L, 0L, 0L, 0L, .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_YES, 32L, 0L,
0L); 0L, 0L, 0L);
assertEquals(96L, uidRoaming.getTotalBytes()); assertEquals(96L, uidRoaming.getTotalBytes());
} }
@@ -283,95 +314,95 @@ public class NetworkStatsTest extends TestCase {
public void testGroupedByIfaceAll() throws Exception { public void testGroupedByIfaceAll() throws Exception {
final NetworkStats uidStats = new NetworkStats(TEST_START, 3) final NetworkStats uidStats = new NetworkStats(TEST_START, 3)
.addValues(IFACE_ALL, 100, SET_ALL, TAG_NONE, ROAMING_NO, 128L, 8L, 0L, 2L, .addValues(IFACE_ALL, 100, SET_ALL, TAG_NONE, METERED_NO, ROAMING_NO, 128L, 8L, 0L,
20L)
.addValues(IFACE_ALL, 101, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 128L, 8L, 0L,
2L, 20L) 2L, 20L)
.addValues(IFACE_ALL, 101, SET_ALL, TAG_NONE, ROAMING_YES, 128L, 8L, 0L, 2L, .addValues(IFACE_ALL, 101, SET_FOREGROUND, TAG_NONE, METERED_YES, ROAMING_NO, 128L,
20L); 8L, 0L, 2L, 20L)
.addValues(IFACE_ALL, 101, SET_ALL, TAG_NONE, METERED_NO, ROAMING_YES, 128L, 8L, 0L,
2L, 20L);
final NetworkStats grouped = uidStats.groupedByIface(); final NetworkStats grouped = uidStats.groupedByIface();
assertEquals(3, uidStats.size()); assertEquals(3, uidStats.size());
assertEquals(1, grouped.size()); assertEquals(1, grouped.size());
assertValues(grouped, 0, IFACE_ALL, UID_ALL, SET_ALL, TAG_NONE, ROAMING_ALL, 384L, 24L, 0L, assertValues(grouped, 0, IFACE_ALL, UID_ALL, SET_ALL, TAG_NONE, METERED_ALL, ROAMING_ALL,
6L, 0L); 384L, 24L, 0L, 6L, 0L);
} }
public void testGroupedByIface() throws Exception { public void testGroupedByIface() throws Exception {
final NetworkStats uidStats = new NetworkStats(TEST_START, 7) final NetworkStats uidStats = new NetworkStats(TEST_START, 7)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L, .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 128L, 8L,
2L, 20L) 0L, 2L, 20L)
.addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 512L, 32L, 0L, .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 512L,
0L, 0L) 32L, 0L, 0L, 0L)
.addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, ROAMING_NO, 64L, 4L, 0L, 0L, .addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, METERED_NO, ROAMING_NO, 64L, 4L,
0L)
.addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 512L, 32L,
0L, 0L, 0L) 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L, .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO, 512L,
0L, 0L) 32L, 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 128L, 8L, 0L, 0L, .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 128L, 8L,
0L) 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_YES, 128L, 8L, 0L, .addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, METERED_YES, ROAMING_NO, 128L, 8L,
0L, 0L); 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_YES, 128L,
8L, 0L, 0L, 0L);
final NetworkStats grouped = uidStats.groupedByIface(); final NetworkStats grouped = uidStats.groupedByIface();
assertEquals(7, uidStats.size()); assertEquals(7, uidStats.size());
assertEquals(2, grouped.size()); assertEquals(2, grouped.size());
assertValues(grouped, 0, TEST_IFACE, UID_ALL, SET_ALL, TAG_NONE, ROAMING_ALL, 384L, 24L, 0L, assertValues(grouped, 0, TEST_IFACE, UID_ALL, SET_ALL, TAG_NONE, METERED_ALL, ROAMING_ALL,
2L, 0L); 384L, 24L, 0L, 2L, 0L);
assertValues(grouped, 1, TEST_IFACE2, UID_ALL, SET_ALL, TAG_NONE, ROAMING_ALL, 1024L, 64L, assertValues(grouped, 1, TEST_IFACE2, UID_ALL, SET_ALL, TAG_NONE, METERED_ALL, ROAMING_ALL,
0L, 0L, 0L); 1024L, 64L, 0L, 0L, 0L);
} }
public void testAddAllValues() { public void testAddAllValues() {
final NetworkStats first = new NetworkStats(TEST_START, 5) final NetworkStats first = new NetworkStats(TEST_START, 5)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L, .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 32L, 0L,
0L) 0L, 0L, 0L)
.addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, .addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO, 32L,
0L, 0L) 0L, 0L, 0L, 0L)
.addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_YES, 32L, 0L, 0L, .addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, METERED_YES, ROAMING_YES, 32L,
0L, 0L); 0L, 0L, 0L, 0L);
final NetworkStats second = new NetworkStats(TEST_START, 2) final NetworkStats second = new NetworkStats(TEST_START, 2)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L, 0L, 0L, .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 32L, 0L,
0L)
.addValues(TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L, 0L,
0L, 0L, 0L) 0L, 0L, 0L)
.addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_YES, 32L, 0L, 0L, .addValues(TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 32L,
0L, 0L); 0L, 0L, 0L, 0L)
.addValues(TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, METERED_YES, ROAMING_YES, 32L,
0L, 0L, 0L, 0L);
first.combineAllValues(second); first.combineAllValues(second);
assertEquals(4, first.size()); assertEquals(4, first.size());
assertValues(first, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 64L, 0L, 0L, assertValues(first, 0, TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 64L,
0L, 0L);
assertValues(first, 1, TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 32L, 0L,
0L, 0L, 0L);
assertValues(first, 2, TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, ROAMING_YES, 64L, 0L,
0L, 0L, 0L);
assertValues(first, 3, TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, ROAMING_NO, 32L,
0L, 0L, 0L, 0L); 0L, 0L, 0L, 0L);
assertValues(first, 1, TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO,
32L, 0L, 0L, 0L, 0L);
assertValues(first, 2, TEST_IFACE, 100, SET_FOREGROUND, TAG_NONE, METERED_YES, ROAMING_YES,
64L, 0L, 0L, 0L, 0L);
assertValues(first, 3, TEST_IFACE2, UID_ALL, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
32L, 0L, 0L, 0L, 0L);
} }
public void testGetTotal() { public void testGetTotal() {
final NetworkStats stats = new NetworkStats(TEST_START, 7) final NetworkStats stats = new NetworkStats(TEST_START, 7)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L, .addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 128L, 8L,
2L, 20L) 0L, 2L, 20L)
.addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 512L, 32L, 0L, .addValues(TEST_IFACE2, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 512L,
0L, 0L) 32L, 0L, 0L, 0L)
.addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, ROAMING_NO, 64L, 4L, 0L, 0L, .addValues(TEST_IFACE2, 100, SET_DEFAULT, 0xF00D, METERED_NO, ROAMING_NO, 64L, 4L,
0L)
.addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 512L, 32L,
0L, 0L, 0L) 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, 0L, .addValues(TEST_IFACE2, 100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO, 512L,
0L, 0L) 32L, 0L, 0L, 0L)
.addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 128L, 8L, 0L, 0L, .addValues(TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_YES, ROAMING_NO, 128L,
0L) 8L, 0L, 0L, 0L)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, ROAMING_YES, 128L, 8L, 0L, .addValues(TEST_IFACE, 101, SET_DEFAULT, 0xF00D, METERED_NO, ROAMING_NO, 128L, 8L,
0L, 0L); 0L, 0L, 0L)
.addValues(TEST_IFACE, 100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_YES, 128L,
8L, 0L, 0L, 0L);
assertValues(stats.getTotal(null), 1408L, 88L, 0L, 2L, 20L); assertValues(stats.getTotal(null), 1408L, 88L, 0L, 2L, 20L);
assertValues(stats.getTotal(null, 100), 1280L, 80L, 0L, 2L, 20L); assertValues(stats.getTotal(null, 100), 1280L, 80L, 0L, 2L, 20L);
@@ -396,10 +427,10 @@ public class NetworkStatsTest extends TestCase {
final NetworkStats after = before.withoutUids(new int[] { 100 }); final NetworkStats after = before.withoutUids(new int[] { 100 });
assertEquals(6, before.size()); assertEquals(6, before.size());
assertEquals(2, after.size()); assertEquals(2, after.size());
assertValues(after, 0, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, ROAMING_NO, 128L, 8L, assertValues(after, 0, TEST_IFACE, 101, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
0L, 0L, 0L); 128L, 8L, 0L, 0L, 0L);
assertValues(after, 1, TEST_IFACE, 101, SET_DEFAULT, 0xF00D, ROAMING_NO, 128L, 8L, 0L, assertValues(after, 1, TEST_IFACE, 101, SET_DEFAULT, 0xF00D, METERED_NO, ROAMING_NO, 128L,
0L, 0L); 8L, 0L, 0L, 0L);
} }
public void testClone() throws Exception { public void testClone() throws Exception {
@@ -434,105 +465,175 @@ public class NetworkStatsTest extends TestCase {
final String underlyingIface = "wlan0"; final String underlyingIface = "wlan0";
final int testTag1 = 8888; final int testTag1 = 8888;
NetworkStats delta = new NetworkStats(TEST_START, 17) NetworkStats delta = new NetworkStats(TEST_START, 17)
.addValues(tunIface, 10100, SET_DEFAULT, TAG_NONE, 39605L, 46L, 12259L, 55L, 0L) .addValues(tunIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 39605L, 46L,
.addValues(tunIface, 10100, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L) 12259L, 55L, 0L)
.addValues(tunIface, 10120, SET_DEFAULT, TAG_NONE, 72667L, 197L, 43909L, 241L, 0L) .addValues(tunIface, 10100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO, 0L, 0L,
.addValues(tunIface, 10120, SET_FOREGROUND, TAG_NONE, 9297L, 17L, 4128L, 21L, 0L) 0L, 0L, 0L)
.addValues(tunIface, 10120, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 72667L, 197L,
43909L, 241L, 0L)
.addValues(tunIface, 10120, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO, 9297L,
17L, 4128L, 21L, 0L)
// VPN package also uses some traffic through unprotected network. // VPN package also uses some traffic through unprotected network.
.addValues(tunIface, tunUid, SET_DEFAULT, TAG_NONE, 4983L, 10L, 1801L, 12L, 0L) .addValues(tunIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 4983L, 10L,
.addValues(tunIface, tunUid, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L) 1801L, 12L, 0L)
.addValues(tunIface, tunUid, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO, 0L, 0L,
0L, 0L, 0L)
// Tag entries // Tag entries
.addValues(tunIface, 10120, SET_DEFAULT, testTag1, 21691L, 41L, 13820L, 51L, 0L) .addValues(tunIface, 10120, SET_DEFAULT, testTag1, METERED_NO, ROAMING_NO, 21691L, 41L,
.addValues(tunIface, 10120, SET_FOREGROUND, testTag1, 1281L, 2L, 665L, 2L, 0L) 13820L, 51L, 0L)
.addValues(tunIface, 10120, SET_FOREGROUND, testTag1, METERED_NO, ROAMING_NO, 1281L, 2L,
665L, 2L, 0L)
// Irrelevant entries // Irrelevant entries
.addValues(TEST_IFACE, 10100, SET_DEFAULT, TAG_NONE, 1685L, 5L, 2070L, 6L, 0L) .addValues(TEST_IFACE, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1685L, 5L,
2070L, 6L, 0L)
// Underlying Iface entries // Underlying Iface entries
.addValues(underlyingIface, 10100, SET_DEFAULT, TAG_NONE, 5178L, 8L, 2139L, 11L, 0L) .addValues(underlyingIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 5178L,
.addValues(underlyingIface, 10100, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L) 8L, 2139L, 11L, 0L)
.addValues(underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, 149873L, 287L, .addValues(underlyingIface, 10100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO, 0L,
59217L /* smaller than sum(tun0) */, 299L /* smaller than sum(tun0) */, 0L) 0L, 0L, 0L, 0L)
.addValues(underlyingIface, tunUid, SET_FOREGROUND, TAG_NONE, 0L, 0L, 0L, 0L, 0L); .addValues(underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
149873L, 287L, 59217L /* smaller than sum(tun0) */,
299L /* smaller than sum(tun0) */, 0L)
.addValues(underlyingIface, tunUid, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO,
0L, 0L, 0L, 0L, 0L);
assertTrue(delta.migrateTun(tunUid, tunIface, underlyingIface)); assertTrue(delta.migrateTun(tunUid, tunIface, underlyingIface));
assertEquals(21, delta.size()); assertEquals(20, delta.size());
// tunIface and TEST_IFACE entries are not changed. // tunIface and TEST_IFACE entries are not changed.
assertValues(delta, 0, tunIface, 10100, SET_DEFAULT, TAG_NONE, ROAMING_NO, assertValues(delta, 0, tunIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
39605L, 46L, 12259L, 55L, 0L); 39605L, 46L, 12259L, 55L, 0L);
assertValues(delta, 1, tunIface, 10100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 0L, 0L, assertValues(delta, 1, tunIface, 10100, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO,
0L, 0L, 0L); 0L, 0L, 0L, 0L, 0L);
assertValues(delta, 2, tunIface, 10120, SET_DEFAULT, TAG_NONE, ROAMING_NO, assertValues(delta, 2, tunIface, 10120, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
72667L, 197L, 43909L, 241L, 0L); 72667L, 197L, 43909L, 241L, 0L);
assertValues(delta, 3, tunIface, 10120, SET_FOREGROUND, TAG_NONE, ROAMING_NO, assertValues(delta, 3, tunIface, 10120, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO,
9297L, 17L, 4128L, 21L, 0L); 9297L, 17L, 4128L, 21L, 0L);
assertValues(delta, 4, tunIface, tunUid, SET_DEFAULT, TAG_NONE, ROAMING_NO, assertValues(delta, 4, tunIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
4983L, 10L, 1801L, 12L, 0L); 4983L, 10L, 1801L, 12L, 0L);
assertValues(delta, 5, tunIface, tunUid, SET_FOREGROUND, TAG_NONE, ROAMING_NO, 0L, 0L, assertValues(delta, 5, tunIface, tunUid, SET_FOREGROUND, TAG_NONE, METERED_NO, ROAMING_NO,
0L, 0L, 0L); 0L, 0L, 0L, 0L, 0L);
assertValues(delta, 6, tunIface, 10120, SET_DEFAULT, testTag1, ROAMING_NO, assertValues(delta, 6, tunIface, 10120, SET_DEFAULT, testTag1, METERED_NO, ROAMING_NO,
21691L, 41L, 13820L, 51L, 0L); 21691L, 41L, 13820L, 51L, 0L);
assertValues(delta, 7, tunIface, 10120, SET_FOREGROUND, testTag1, ROAMING_NO, 1281L, assertValues(delta, 7, tunIface, 10120, SET_FOREGROUND, testTag1, METERED_NO, ROAMING_NO,
2L, 665L, 2L, 0L); 1281L, 2L, 665L, 2L, 0L);
assertValues(delta, 8, TEST_IFACE, 10100, SET_DEFAULT, TAG_NONE, ROAMING_NO, 1685L, 5L, assertValues(delta, 8, TEST_IFACE, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
2070L, 6L, 0L); 1685L, 5L, 2070L, 6L, 0L);
// Existing underlying Iface entries are updated // Existing underlying Iface entries are updated
assertValues(delta, 9, underlyingIface, 10100, SET_DEFAULT, TAG_NONE, ROAMING_NO, assertValues(delta, 9, underlyingIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO,
44783L, 54L, 13829L, 60L, 0L); ROAMING_NO, 44783L, 54L, 14178L, 62L, 0L);
assertValues(delta, 10, underlyingIface, 10100, SET_FOREGROUND, TAG_NONE, ROAMING_NO, assertValues(delta, 10, underlyingIface, 10100, SET_FOREGROUND, TAG_NONE, METERED_NO,
0L, 0L, 0L, 0L, 0L); ROAMING_NO, 0L, 0L, 0L, 0L, 0L);
// VPN underlying Iface entries are updated // VPN underlying Iface entries are updated
assertValues(delta, 11, underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, ROAMING_NO, assertValues(delta, 11, underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO,
28304L, 27L, 1719L, 12L, 0L); ROAMING_NO, 28304L, 27L, 1L, 2L, 0L);
assertValues(delta, 12, underlyingIface, tunUid, SET_FOREGROUND, TAG_NONE, ROAMING_NO, assertValues(delta, 12, underlyingIface, tunUid, SET_FOREGROUND, TAG_NONE, METERED_NO,
0L, 0L, 0L, 0L, 0L); ROAMING_NO, 0L, 0L, 0L, 0L, 0L);
// New entries are added for new application's underlying Iface traffic // New entries are added for new application's underlying Iface traffic
assertContains(delta, underlyingIface, 10120, SET_DEFAULT, TAG_NONE, ROAMING_NO, assertContains(delta, underlyingIface, 10120, SET_DEFAULT, TAG_NONE, METERED_NO,
72667L, 197L, 41872L, 219L, 0L); ROAMING_NO, 72667L, 197L, 43123L, 227L, 0L);
assertContains(delta, underlyingIface, 10120, SET_FOREGROUND, TAG_NONE, ROAMING_NO, assertContains(delta, underlyingIface, 10120, SET_FOREGROUND, TAG_NONE, METERED_NO,
9297L, 17L, 3936, 19L, 0L); ROAMING_NO, 9297L, 17L, 4054, 19L, 0L);
assertContains(delta, underlyingIface, 10120, SET_DEFAULT, testTag1, ROAMING_NO, assertContains(delta, underlyingIface, 10120, SET_DEFAULT, testTag1, METERED_NO,
21691L, 41L, 13179L, 46L, 0L); ROAMING_NO, 21691L, 41L, 13572L, 48L, 0L);
assertContains(delta, underlyingIface, 10120, SET_FOREGROUND, testTag1, ROAMING_NO, assertContains(delta, underlyingIface, 10120, SET_FOREGROUND, testTag1, METERED_NO,
1281L, 2L, 634L, 1L, 0L); ROAMING_NO, 1281L, 2L, 653L, 1L, 0L);
// New entries are added for debug purpose // New entries are added for debug purpose
assertContains(delta, underlyingIface, 10100, SET_DBG_VPN_IN, TAG_NONE, ROAMING_NO, assertContains(delta, underlyingIface, 10100, SET_DBG_VPN_IN, TAG_NONE, METERED_NO,
39605L, 46L, 11690, 49, 0); ROAMING_NO, 39605L, 46L, 12039, 51, 0);
assertContains(delta, underlyingIface, 10120, SET_DBG_VPN_IN, TAG_NONE, ROAMING_NO, assertContains(delta, underlyingIface, 10120, SET_DBG_VPN_IN, TAG_NONE, METERED_NO,
81964, 214, 45808, 238, 0); ROAMING_NO, 81964, 214, 47177, 246, 0);
assertContains(delta, underlyingIface, tunUid, SET_DBG_VPN_IN, TAG_NONE, ROAMING_NO, assertContains(delta, underlyingIface, tunUid, SET_DBG_VPN_OUT, TAG_NONE, METERED_ALL,
4983, 10, 1717, 10, 0); ROAMING_ALL, 121569, 260, 59216, 297, 0);
assertContains(delta, underlyingIface, tunUid, SET_DBG_VPN_OUT, TAG_NONE, ROAMING_ALL,
126552, 270, 59215, 297, 0);
} }
// Tests a case where all of the data received by the tun0 interface is echo back into the tun0
// interface by the vpn app before it's sent out of the underlying interface. The VPN app should
// not be charged for the echoed data but it should still be charged for any extra data it sends
// via the underlying interface.
public void testMigrateTun_VpnAsLoopback() {
final int tunUid = 10030;
final String tunIface = "tun0";
final String underlyingIface = "wlan0";
NetworkStats delta = new NetworkStats(TEST_START, 9)
// 2 different apps sent/receive data via tun0.
.addValues(tunIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 50000L, 25L,
100000L, 50L, 0L)
.addValues(tunIface, 20100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 500L, 2L,
200L, 5L, 0L)
// VPN package resends data through the tunnel (with exaggerated overhead)
.addValues(tunIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 240000,
100L, 120000L, 60L, 0L)
// 1 app already has some traffic on the underlying interface, the other doesn't yet
.addValues(underlyingIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO, 1000L,
10L, 2000L, 20L, 0L)
// Traffic through the underlying interface via the vpn app.
// This test should redistribute this data correctly.
.addValues(underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
75500L, 37L, 130000L, 70L, 0L);
assertTrue(delta.migrateTun(tunUid, tunIface, underlyingIface));
assertEquals(9, delta.size());
// tunIface entries should not be changed.
assertValues(delta, 0, tunIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
50000L, 25L, 100000L, 50L, 0L);
assertValues(delta, 1, tunIface, 20100, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
500L, 2L, 200L, 5L, 0L);
assertValues(delta, 2, tunIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
240000L, 100L, 120000L, 60L, 0L);
// Existing underlying Iface entries are updated
assertValues(delta, 3, underlyingIface, 10100, SET_DEFAULT, TAG_NONE, METERED_NO,
ROAMING_NO, 51000L, 35L, 102000L, 70L, 0L);
// VPN underlying Iface entries are updated
assertValues(delta, 4, underlyingIface, tunUid, SET_DEFAULT, TAG_NONE, METERED_NO,
ROAMING_NO, 25000L, 10L, 29800L, 15L, 0L);
// New entries are added for new application's underlying Iface traffic
assertContains(delta, underlyingIface, 20100, SET_DEFAULT, TAG_NONE, METERED_NO,
ROAMING_NO, 500L, 2L, 200L, 5L, 0L);
// New entries are added for debug purpose
assertContains(delta, underlyingIface, 10100, SET_DBG_VPN_IN, TAG_NONE, METERED_NO,
ROAMING_NO, 50000L, 25L, 100000L, 50L, 0L);
assertContains(delta, underlyingIface, 20100, SET_DBG_VPN_IN, TAG_NONE, METERED_NO,
ROAMING_NO, 500, 2L, 200L, 5L, 0L);
assertContains(delta, underlyingIface, tunUid, SET_DBG_VPN_OUT, TAG_NONE, METERED_ALL,
ROAMING_ALL, 50500L, 27L, 100200L, 55, 0);
}
private static void assertContains(NetworkStats stats, String iface, int uid, int set, private static void assertContains(NetworkStats stats, String iface, int uid, int set,
int tag, int roaming, long rxBytes, long rxPackets, long txBytes, long txPackets, int tag, int metered, int roaming, long rxBytes, long rxPackets, long txBytes,
long operations) { long txPackets, long operations) {
int index = stats.findIndex(iface, uid, set, tag, roaming); int index = stats.findIndex(iface, uid, set, tag, metered, roaming);
assertTrue(index != -1); assertTrue(index != -1);
assertValues(stats, index, iface, uid, set, tag, roaming, assertValues(stats, index, iface, uid, set, tag, metered, roaming,
rxBytes, rxPackets, txBytes, txPackets, operations); rxBytes, rxPackets, txBytes, txPackets, operations);
} }
private static void assertValues(NetworkStats stats, int index, String iface, int uid, int set, private static void assertValues(NetworkStats stats, int index, String iface, int uid, int set,
int tag, int roaming, long rxBytes, long rxPackets, long txBytes, long txPackets, int tag, int metered, int roaming, long rxBytes, long rxPackets, long txBytes,
long operations) { long txPackets, long operations) {
final NetworkStats.Entry entry = stats.getValues(index, null); final NetworkStats.Entry entry = stats.getValues(index, null);
assertValues(entry, iface, uid, set, tag, roaming); assertValues(entry, iface, uid, set, tag, metered, roaming);
assertValues(entry, rxBytes, rxPackets, txBytes, txPackets, operations); assertValues(entry, rxBytes, rxPackets, txBytes, txPackets, operations);
} }
private static void assertValues( private static void assertValues(
NetworkStats.Entry entry, String iface, int uid, int set, int tag, int roaming) { NetworkStats.Entry entry, String iface, int uid, int set, int tag, int metered,
int roaming) {
assertEquals(iface, entry.iface); assertEquals(iface, entry.iface);
assertEquals(uid, entry.uid); assertEquals(uid, entry.uid);
assertEquals(set, entry.set); assertEquals(set, entry.set);
assertEquals(tag, entry.tag); assertEquals(tag, entry.tag);
assertEquals(metered, entry.metered);
assertEquals(roaming, entry.roaming); assertEquals(roaming, entry.roaming);
} }

View File

@@ -16,6 +16,7 @@
package com.android.internal.net; package com.android.internal.net;
import static android.net.NetworkStats.METERED_NO;
import static android.net.NetworkStats.ROAMING_NO; import static android.net.NetworkStats.ROAMING_NO;
import static android.net.NetworkStats.SET_ALL; import static android.net.NetworkStats.SET_ALL;
import static android.net.NetworkStats.SET_DEFAULT; import static android.net.NetworkStats.SET_DEFAULT;
@@ -101,12 +102,14 @@ public class NetworkStatsFactoryTest extends AndroidTestCase {
final NetworkStats stats = mFactory.readNetworkStatsDetail(); final NetworkStats stats = mFactory.readNetworkStatsDetail();
assertEquals(70, stats.size()); assertEquals(70, stats.size());
assertStatsEntry(stats, "rmnet1", 10021, SET_DEFAULT, 0x30100000, 219110L, 578L, 227423L, 676L); assertStatsEntry(stats, "rmnet1", 10021, SET_DEFAULT, 0x30100000, 219110L, 578L, 227423L,
676L);
assertStatsEntry(stats, "rmnet1", 10021, SET_FOREGROUND, 0x30100000, 742L, 3L, 1265L, 3L); assertStatsEntry(stats, "rmnet1", 10021, SET_FOREGROUND, 0x30100000, 742L, 3L, 1265L, 3L);
} }
public void testNetworkStatsSingle() throws Exception { public void testNetworkStatsSingle() throws Exception {
stageFile(R.raw.xt_qtaguid_iface_typical, new File(mTestProc, "net/xt_qtaguid/iface_stat_all")); stageFile(R.raw.xt_qtaguid_iface_typical,
new File(mTestProc, "net/xt_qtaguid/iface_stat_all"));
final NetworkStats stats = mFactory.readNetworkStatsSummaryDev(); final NetworkStats stats = mFactory.readNetworkStatsSummaryDev();
assertEquals(6, stats.size()); assertEquals(6, stats.size());
@@ -122,7 +125,8 @@ public class NetworkStatsFactoryTest extends AndroidTestCase {
final NetworkStats stats = mFactory.readNetworkStatsSummaryXt(); final NetworkStats stats = mFactory.readNetworkStatsSummaryXt();
assertEquals(3, stats.size()); assertEquals(3, stats.size());
assertStatsEntry(stats, "rmnet0", UID_ALL, SET_ALL, TAG_NONE, 6824L, 16L, 5692L, 10L); assertStatsEntry(stats, "rmnet0", UID_ALL, SET_ALL, TAG_NONE, 6824L, 16L, 5692L, 10L);
assertStatsEntry(stats, "rmnet1", UID_ALL, SET_ALL, TAG_NONE, 11153922L, 8051L, 190226L, 2468L); assertStatsEntry(stats, "rmnet1", UID_ALL, SET_ALL, TAG_NONE, 11153922L, 8051L, 190226L,
2468L);
assertStatsEntry(stats, "rmnet2", UID_ALL, SET_ALL, TAG_NONE, 4968L, 35L, 3081L, 39L); assertStatsEntry(stats, "rmnet2", UID_ALL, SET_ALL, TAG_NONE, 4968L, 35L, 3081L, 39L);
} }
@@ -157,7 +161,7 @@ public class NetworkStatsFactoryTest extends AndroidTestCase {
private static void assertStatsEntry(NetworkStats stats, String iface, int uid, int set, private static void assertStatsEntry(NetworkStats stats, String iface, int uid, int set,
int tag, long rxBytes, long txBytes) { int tag, long rxBytes, long txBytes) {
final int i = stats.findIndex(iface, uid, set, tag, ROAMING_NO); final int i = stats.findIndex(iface, uid, set, tag, METERED_NO, ROAMING_NO);
final NetworkStats.Entry entry = stats.getValues(i, null); final NetworkStats.Entry entry = stats.getValues(i, null);
assertEquals("unexpected rxBytes", rxBytes, entry.rxBytes); assertEquals("unexpected rxBytes", rxBytes, entry.rxBytes);
assertEquals("unexpected txBytes", txBytes, entry.txBytes); assertEquals("unexpected txBytes", txBytes, entry.txBytes);
@@ -165,7 +169,7 @@ public class NetworkStatsFactoryTest extends AndroidTestCase {
private static void assertStatsEntry(NetworkStats stats, String iface, int uid, int set, private static void assertStatsEntry(NetworkStats stats, String iface, int uid, int set,
int tag, long rxBytes, long rxPackets, long txBytes, long txPackets) { int tag, long rxBytes, long rxPackets, long txBytes, long txPackets) {
final int i = stats.findIndex(iface, uid, set, tag, ROAMING_NO); final int i = stats.findIndex(iface, uid, set, tag, METERED_NO, ROAMING_NO);
final NetworkStats.Entry entry = stats.getValues(i, null); final NetworkStats.Entry entry = stats.getValues(i, null);
assertEquals("unexpected rxBytes", rxBytes, entry.rxBytes); assertEquals("unexpected rxBytes", rxBytes, entry.rxBytes);
assertEquals("unexpected rxPackets", rxPackets, entry.rxPackets); assertEquals("unexpected rxPackets", rxPackets, entry.rxPackets);

View File

@@ -25,6 +25,7 @@ import static org.mockito.Matchers.isA;
import static org.mockito.Mockito.when; import static org.mockito.Mockito.when;
import static android.net.NetworkStats.SET_DEFAULT; import static android.net.NetworkStats.SET_DEFAULT;
import static android.net.NetworkStats.METERED_NO;
import static android.net.NetworkStats.ROAMING_NO; import static android.net.NetworkStats.ROAMING_NO;
import static android.net.NetworkStats.TAG_NONE; import static android.net.NetworkStats.TAG_NONE;
import static android.net.NetworkTemplate.buildTemplateMobileAll; import static android.net.NetworkTemplate.buildTemplateMobileAll;
@@ -336,7 +337,7 @@ public class NetworkStatsObserversTest extends TestCase {
// Baseline // Baseline
NetworkStats xtSnapshot = null; NetworkStats xtSnapshot = null;
NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */) NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
BASE_BYTES, 2L, BASE_BYTES, 2L, 0L); BASE_BYTES, 2L, BASE_BYTES, 2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
@@ -344,7 +345,7 @@ public class NetworkStatsObserversTest extends TestCase {
// Delta // Delta
uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */) uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES, 2L, 0L); BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES, 2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
@@ -374,7 +375,7 @@ public class NetworkStatsObserversTest extends TestCase {
// Baseline // Baseline
NetworkStats xtSnapshot = null; NetworkStats xtSnapshot = null;
NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */) NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
BASE_BYTES, 2L, BASE_BYTES, 2L, 0L); BASE_BYTES, 2L, BASE_BYTES, 2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
@@ -382,7 +383,7 @@ public class NetworkStatsObserversTest extends TestCase {
// Delta // Delta
uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */) uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES, 2L, 0L); BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES, 2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
@@ -412,7 +413,7 @@ public class NetworkStatsObserversTest extends TestCase {
// Baseline // Baseline
NetworkStats xtSnapshot = null; NetworkStats xtSnapshot = null;
NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */) NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
BASE_BYTES, 2L, BASE_BYTES, 2L, 0L); BASE_BYTES, 2L, BASE_BYTES, 2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
@@ -420,7 +421,7 @@ public class NetworkStatsObserversTest extends TestCase {
// Delta // Delta
uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */) uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_RED, SET_DEFAULT, TAG_NONE, METERED_NO, ROAMING_NO,
BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES, 2L, 0L); BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES, 2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
@@ -450,16 +451,17 @@ public class NetworkStatsObserversTest extends TestCase {
// Baseline // Baseline
NetworkStats xtSnapshot = null; NetworkStats xtSnapshot = null;
NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */) NetworkStats uidSnapshot = new NetworkStats(TEST_START, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_ANOTHER_USER, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_ANOTHER_USER, SET_DEFAULT, TAG_NONE, METERED_NO,
BASE_BYTES, 2L, BASE_BYTES, 2L, 0L); ROAMING_NO, BASE_BYTES, 2L, BASE_BYTES, 2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
VPN_INFO, TEST_START); VPN_INFO, TEST_START);
// Delta // Delta
uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */) uidSnapshot = new NetworkStats(TEST_START + 2 * MINUTE_IN_MILLIS, 2 /* initialSize */)
.addValues(TEST_IFACE, UID_ANOTHER_USER, SET_DEFAULT, TAG_NONE, ROAMING_NO, .addValues(TEST_IFACE, UID_ANOTHER_USER, SET_DEFAULT, TAG_NONE, METERED_NO,
BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES, 2L, 0L); ROAMING_NO, BASE_BYTES + THRESHOLD_BYTES, 2L, BASE_BYTES + THRESHOLD_BYTES,
2L, 0L);
mStatsObservers.updateStats( mStatsObservers.updateStats(
xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces, xtSnapshot, uidSnapshot, mActiveIfaces, mActiveUidIfaces,
VPN_INFO, TEST_START); VPN_INFO, TEST_START);

View File

@@ -70,7 +70,6 @@ import android.provider.Settings;
import android.test.AndroidTestCase; import android.test.AndroidTestCase;
import android.test.FlakyTest; import android.test.FlakyTest;
import android.test.mock.MockContentResolver; import android.test.mock.MockContentResolver;
import android.test.suitebuilder.annotation.LargeTest;
import android.test.suitebuilder.annotation.SmallTest; import android.test.suitebuilder.annotation.SmallTest;
import android.util.Log; import android.util.Log;
import android.util.LogPrinter; import android.util.LogPrinter;
@@ -91,6 +90,7 @@ import java.util.concurrent.CountDownLatch;
import java.util.concurrent.LinkedBlockingQueue; import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicBoolean; import java.util.concurrent.atomic.AtomicBoolean;
import java.util.function.BooleanSupplier;
/** /**
* Tests for {@link ConnectivityService}. * Tests for {@link ConnectivityService}.
@@ -195,6 +195,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
} }
// Tests that IdleableHandlerThread works as expected. // Tests that IdleableHandlerThread works as expected.
@SmallTest
public void testIdleableHandlerThread() { public void testIdleableHandlerThread() {
final int attempts = 50; // Causes the test to take about 200ms on bullhead-eng. final int attempts = 50; // Causes the test to take about 200ms on bullhead-eng.
@@ -219,6 +220,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
} }
} }
@SmallTest
@FlakyTest(tolerance = 3) @FlakyTest(tolerance = 3)
public void testNotWaitingForIdleCausesRaceConditions() { public void testNotWaitingForIdleCausesRaceConditions() {
// Bring up a network that we can use to send messages to ConnectivityService. // Bring up a network that we can use to send messages to ConnectivityService.
@@ -622,7 +624,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
} }
private class WrappedAvoidBadWifiTracker extends AvoidBadWifiTracker { private class WrappedAvoidBadWifiTracker extends AvoidBadWifiTracker {
public boolean configRestrictsAvoidBadWifi; public volatile boolean configRestrictsAvoidBadWifi;
public WrappedAvoidBadWifiTracker(Context c, Handler h, Runnable r) { public WrappedAvoidBadWifiTracker(Context c, Handler h, Runnable r) {
super(c, h, r); super(c, h, r);
@@ -839,7 +841,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
return cv; return cv;
} }
@LargeTest @SmallTest
public void testLingering() throws Exception { public void testLingering() throws Exception {
verifyNoNetwork(); verifyNoNetwork();
mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR); mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR);
@@ -879,7 +881,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
verifyNoNetwork(); verifyNoNetwork();
} }
@LargeTest @SmallTest
public void testValidatedCellularOutscoresUnvalidatedWiFi() throws Exception { public void testValidatedCellularOutscoresUnvalidatedWiFi() throws Exception {
// Test bringing up unvalidated WiFi // Test bringing up unvalidated WiFi
mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI); mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI);
@@ -914,7 +916,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
verifyNoNetwork(); verifyNoNetwork();
} }
@LargeTest @SmallTest
public void testUnvalidatedWifiOutscoresUnvalidatedCellular() throws Exception { public void testUnvalidatedWifiOutscoresUnvalidatedCellular() throws Exception {
// Test bringing up unvalidated cellular. // Test bringing up unvalidated cellular.
mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR); mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR);
@@ -940,7 +942,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
verifyNoNetwork(); verifyNoNetwork();
} }
@LargeTest @SmallTest
public void testUnlingeringDoesNotValidate() throws Exception { public void testUnlingeringDoesNotValidate() throws Exception {
// Test bringing up unvalidated WiFi. // Test bringing up unvalidated WiFi.
mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI); mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI);
@@ -968,7 +970,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
NET_CAPABILITY_VALIDATED)); NET_CAPABILITY_VALIDATED));
} }
@LargeTest @SmallTest
public void testCellularOutscoresWeakWifi() throws Exception { public void testCellularOutscoresWeakWifi() throws Exception {
// Test bringing up validated cellular. // Test bringing up validated cellular.
mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR); mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR);
@@ -994,7 +996,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
verifyActiveNetwork(TRANSPORT_WIFI); verifyActiveNetwork(TRANSPORT_WIFI);
} }
@LargeTest @SmallTest
public void testReapingNetwork() throws Exception { public void testReapingNetwork() throws Exception {
// Test bringing up WiFi without NET_CAPABILITY_INTERNET. // Test bringing up WiFi without NET_CAPABILITY_INTERNET.
// Expect it to be torn down immediately because it satisfies no requests. // Expect it to be torn down immediately because it satisfies no requests.
@@ -1027,7 +1029,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
waitFor(cv); waitFor(cv);
} }
@LargeTest @SmallTest
public void testCellularFallback() throws Exception { public void testCellularFallback() throws Exception {
// Test bringing up validated cellular. // Test bringing up validated cellular.
mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR); mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR);
@@ -1065,7 +1067,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
verifyActiveNetwork(TRANSPORT_WIFI); verifyActiveNetwork(TRANSPORT_WIFI);
} }
@LargeTest @SmallTest
public void testWiFiFallback() throws Exception { public void testWiFiFallback() throws Exception {
// Test bringing up unvalidated WiFi. // Test bringing up unvalidated WiFi.
mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI); mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI);
@@ -1192,7 +1194,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
} }
} }
@LargeTest @SmallTest
public void testStateChangeNetworkCallbacks() throws Exception { public void testStateChangeNetworkCallbacks() throws Exception {
final TestNetworkCallback genericNetworkCallback = new TestNetworkCallback(); final TestNetworkCallback genericNetworkCallback = new TestNetworkCallback();
final TestNetworkCallback wifiNetworkCallback = new TestNetworkCallback(); final TestNetworkCallback wifiNetworkCallback = new TestNetworkCallback();
@@ -1575,7 +1577,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
handlerThread.quit(); handlerThread.quit();
} }
@LargeTest @SmallTest
public void testNetworkFactoryRequests() throws Exception { public void testNetworkFactoryRequests() throws Exception {
tryNetworkFactoryRequests(NET_CAPABILITY_MMS); tryNetworkFactoryRequests(NET_CAPABILITY_MMS);
tryNetworkFactoryRequests(NET_CAPABILITY_SUPL); tryNetworkFactoryRequests(NET_CAPABILITY_SUPL);
@@ -1595,7 +1597,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
// Skipping VALIDATED and CAPTIVE_PORTAL as they're disallowed. // Skipping VALIDATED and CAPTIVE_PORTAL as they're disallowed.
} }
@LargeTest @SmallTest
public void testNoMutableNetworkRequests() throws Exception { public void testNoMutableNetworkRequests() throws Exception {
PendingIntent pendingIntent = PendingIntent.getBroadcast(mContext, 0, new Intent("a"), 0); PendingIntent pendingIntent = PendingIntent.getBroadcast(mContext, 0, new Intent("a"), 0);
NetworkRequest.Builder builder = new NetworkRequest.Builder(); NetworkRequest.Builder builder = new NetworkRequest.Builder();
@@ -1620,7 +1622,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
} catch (IllegalArgumentException expected) {} } catch (IllegalArgumentException expected) {}
} }
@LargeTest @SmallTest
public void testMMSonWiFi() throws Exception { public void testMMSonWiFi() throws Exception {
// Test bringing up cellular without MMS NetworkRequest gets reaped // Test bringing up cellular without MMS NetworkRequest gets reaped
mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR); mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR);
@@ -1655,7 +1657,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
verifyActiveNetwork(TRANSPORT_WIFI); verifyActiveNetwork(TRANSPORT_WIFI);
} }
@LargeTest @SmallTest
public void testMMSonCell() throws Exception { public void testMMSonCell() throws Exception {
// Test bringing up cellular without MMS // Test bringing up cellular without MMS
mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR); mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR);
@@ -1681,7 +1683,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
verifyActiveNetwork(TRANSPORT_CELLULAR); verifyActiveNetwork(TRANSPORT_CELLULAR);
} }
@LargeTest @SmallTest
public void testCaptivePortal() { public void testCaptivePortal() {
final TestNetworkCallback captivePortalCallback = new TestNetworkCallback(); final TestNetworkCallback captivePortalCallback = new TestNetworkCallback();
final NetworkRequest captivePortalRequest = new NetworkRequest.Builder() final NetworkRequest captivePortalRequest = new NetworkRequest.Builder()
@@ -1730,7 +1732,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
validatedCallback.expectCallback(CallbackState.LOST, mWiFiNetworkAgent); validatedCallback.expectCallback(CallbackState.LOST, mWiFiNetworkAgent);
} }
@LargeTest @SmallTest
public void testAvoidOrIgnoreCaptivePortals() { public void testAvoidOrIgnoreCaptivePortals() {
final TestNetworkCallback captivePortalCallback = new TestNetworkCallback(); final TestNetworkCallback captivePortalCallback = new TestNetworkCallback();
final NetworkRequest captivePortalRequest = new NetworkRequest.Builder() final NetworkRequest captivePortalRequest = new NetworkRequest.Builder()
@@ -1801,7 +1803,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
execptionCalled); execptionCalled);
} }
@LargeTest @SmallTest
public void testRegisterDefaultNetworkCallback() throws Exception { public void testRegisterDefaultNetworkCallback() throws Exception {
final TestNetworkCallback defaultNetworkCallback = new TestNetworkCallback(); final TestNetworkCallback defaultNetworkCallback = new TestNetworkCallback();
mCm.registerDefaultNetworkCallback(defaultNetworkCallback); mCm.registerDefaultNetworkCallback(defaultNetworkCallback);
@@ -1862,7 +1864,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
} }
} }
@LargeTest @SmallTest
public void testRequestCallbackUpdates() throws Exception { public void testRequestCallbackUpdates() throws Exception {
// File a network request for mobile. // File a network request for mobile.
final TestNetworkCallback cellNetworkCallback = new TestRequestUpdateCallback(); final TestNetworkCallback cellNetworkCallback = new TestRequestUpdateCallback();
@@ -1997,6 +1999,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
@SmallTest @SmallTest
public void testRequestBenchmark() throws Exception { public void testRequestBenchmark() throws Exception {
// TODO: turn this unit test into a real benchmarking test.
// Benchmarks connecting and switching performance in the presence of a large number of // Benchmarks connecting and switching performance in the presence of a large number of
// NetworkRequests. // NetworkRequests.
// 1. File NUM_REQUESTS requests. // 1. File NUM_REQUESTS requests.
@@ -2010,61 +2013,80 @@ public class ConnectivityServiceTest extends AndroidTestCase {
final CountDownLatch availableLatch = new CountDownLatch(NUM_REQUESTS); final CountDownLatch availableLatch = new CountDownLatch(NUM_REQUESTS);
final CountDownLatch losingLatch = new CountDownLatch(NUM_REQUESTS); final CountDownLatch losingLatch = new CountDownLatch(NUM_REQUESTS);
final int REGISTER_TIME_LIMIT_MS = 100;
long startTime = System.currentTimeMillis();
for (int i = 0; i < NUM_REQUESTS; i++) { for (int i = 0; i < NUM_REQUESTS; i++) {
callbacks[i] = new NetworkCallback() { callbacks[i] = new NetworkCallback() {
@Override public void onAvailable(Network n) { availableLatch.countDown(); } @Override public void onAvailable(Network n) { availableLatch.countDown(); }
@Override public void onLosing(Network n, int t) { losingLatch.countDown(); } @Override public void onLosing(Network n, int t) { losingLatch.countDown(); }
}; };
mCm.registerNetworkCallback(request, callbacks[i]);
} }
long timeTaken = System.currentTimeMillis() - startTime;
String msg = String.format("Register %d callbacks: %dms, acceptable %dms",
NUM_REQUESTS, timeTaken, REGISTER_TIME_LIMIT_MS);
Log.d(TAG, msg);
assertTrue(msg, timeTaken < REGISTER_TIME_LIMIT_MS);
final int CONNECT_TIME_LIMIT_MS = 30; final int REGISTER_TIME_LIMIT_MS = 180;
assertTimeLimit("Registering callbacks", REGISTER_TIME_LIMIT_MS, () -> {
for (NetworkCallback cb : callbacks) {
mCm.registerNetworkCallback(request, cb);
}
});
final int CONNECT_TIME_LIMIT_MS = 40;
mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR); mCellNetworkAgent = new MockNetworkAgent(TRANSPORT_CELLULAR);
// Don't request that the network validate, because otherwise connect() will block until // Don't request that the network validate, because otherwise connect() will block until
// the network gets NET_CAPABILITY_VALIDATED, after all the callbacks below have fired, // the network gets NET_CAPABILITY_VALIDATED, after all the callbacks below have fired,
// and we won't actually measure anything. // and we won't actually measure anything.
mCellNetworkAgent.connect(false); mCellNetworkAgent.connect(false);
startTime = System.currentTimeMillis();
if (!availableLatch.await(CONNECT_TIME_LIMIT_MS, TimeUnit.MILLISECONDS)) {
fail(String.format("Only dispatched %d/%d onAvailable callbacks in %dms",
NUM_REQUESTS - availableLatch.getCount(), NUM_REQUESTS,
CONNECT_TIME_LIMIT_MS));
}
timeTaken = System.currentTimeMillis() - startTime;
Log.d(TAG, String.format("Connect, %d callbacks: %dms, acceptable %dms",
NUM_REQUESTS, timeTaken, CONNECT_TIME_LIMIT_MS));
final int SWITCH_TIME_LIMIT_MS = 30; long onAvailableDispatchingDuration = durationOf(() -> {
if (!awaitLatch(availableLatch, CONNECT_TIME_LIMIT_MS)) {
fail(String.format("Only dispatched %d/%d onAvailable callbacks in %dms",
NUM_REQUESTS - availableLatch.getCount(), NUM_REQUESTS,
CONNECT_TIME_LIMIT_MS));
}
});
Log.d(TAG, String.format("Connect, %d callbacks: %dms, acceptable %dms",
NUM_REQUESTS, onAvailableDispatchingDuration, CONNECT_TIME_LIMIT_MS));
final int SWITCH_TIME_LIMIT_MS = 40;
mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI); mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI);
// Give wifi a high enough score that we'll linger cell when wifi comes up. // Give wifi a high enough score that we'll linger cell when wifi comes up.
mWiFiNetworkAgent.adjustScore(40); mWiFiNetworkAgent.adjustScore(40);
mWiFiNetworkAgent.connect(false); mWiFiNetworkAgent.connect(false);
startTime = System.currentTimeMillis();
if (!losingLatch.await(SWITCH_TIME_LIMIT_MS, TimeUnit.MILLISECONDS)) { long onLostDispatchingDuration = durationOf(() -> {
fail(String.format("Only dispatched %d/%d onLosing callbacks in %dms", if (!awaitLatch(losingLatch, SWITCH_TIME_LIMIT_MS)) {
NUM_REQUESTS - losingLatch.getCount(), NUM_REQUESTS, SWITCH_TIME_LIMIT_MS)); fail(String.format("Only dispatched %d/%d onLosing callbacks in %dms",
} NUM_REQUESTS - losingLatch.getCount(), NUM_REQUESTS, SWITCH_TIME_LIMIT_MS));
timeTaken = System.currentTimeMillis() - startTime; }
});
Log.d(TAG, String.format("Linger, %d callbacks: %dms, acceptable %dms", Log.d(TAG, String.format("Linger, %d callbacks: %dms, acceptable %dms",
NUM_REQUESTS, timeTaken, SWITCH_TIME_LIMIT_MS)); NUM_REQUESTS, onLostDispatchingDuration, SWITCH_TIME_LIMIT_MS));
final int UNREGISTER_TIME_LIMIT_MS = 10; final int UNREGISTER_TIME_LIMIT_MS = 10;
startTime = System.currentTimeMillis(); assertTimeLimit("Unregistering callbacks", UNREGISTER_TIME_LIMIT_MS, () -> {
for (int i = 0; i < NUM_REQUESTS; i++) { for (NetworkCallback cb : callbacks) {
mCm.unregisterNetworkCallback(callbacks[i]); mCm.unregisterNetworkCallback(cb);
} }
timeTaken = System.currentTimeMillis() - startTime; });
msg = String.format("Unregister %d callbacks: %dms, acceptable %dms", }
NUM_REQUESTS, timeTaken, UNREGISTER_TIME_LIMIT_MS);
private long durationOf(Runnable fn) {
long startTime = SystemClock.elapsedRealtime();
fn.run();
return SystemClock.elapsedRealtime() - startTime;
}
private void assertTimeLimit(String descr, long timeLimit, Runnable fn) {
long timeTaken = durationOf(fn);
String msg = String.format("%s: took %dms, limit was %dms", descr, timeTaken, timeLimit);
Log.d(TAG, msg); Log.d(TAG, msg);
assertTrue(msg, timeTaken < UNREGISTER_TIME_LIMIT_MS); assertTrue(msg, timeTaken <= timeLimit);
}
private boolean awaitLatch(CountDownLatch l, long timeoutMs) {
try {
if (l.await(timeoutMs, TimeUnit.MILLISECONDS)) {
return true;
}
} catch (InterruptedException e) {}
return false;
} }
@SmallTest @SmallTest
@@ -2145,7 +2167,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
tracker.reevaluate(); tracker.reevaluate();
mService.waitForIdle(); mService.waitForIdle();
String msg = String.format("config=false, setting=%s", values[i]); String msg = String.format("config=false, setting=%s", values[i]);
assertTrue(msg, mService.avoidBadWifi()); assertEventuallyTrue(() -> mService.avoidBadWifi(), 50);
assertFalse(msg, tracker.shouldNotifyWifiUnvalidated()); assertFalse(msg, tracker.shouldNotifyWifiUnvalidated());
} }
@@ -2154,19 +2176,19 @@ public class ConnectivityServiceTest extends AndroidTestCase {
Settings.Global.putInt(cr, settingName, 0); Settings.Global.putInt(cr, settingName, 0);
tracker.reevaluate(); tracker.reevaluate();
mService.waitForIdle(); mService.waitForIdle();
assertFalse(mService.avoidBadWifi()); assertEventuallyTrue(() -> !mService.avoidBadWifi(), 50);
assertFalse(tracker.shouldNotifyWifiUnvalidated()); assertFalse(tracker.shouldNotifyWifiUnvalidated());
Settings.Global.putInt(cr, settingName, 1); Settings.Global.putInt(cr, settingName, 1);
tracker.reevaluate(); tracker.reevaluate();
mService.waitForIdle(); mService.waitForIdle();
assertTrue(mService.avoidBadWifi()); assertEventuallyTrue(() -> mService.avoidBadWifi(), 50);
assertFalse(tracker.shouldNotifyWifiUnvalidated()); assertFalse(tracker.shouldNotifyWifiUnvalidated());
Settings.Global.putString(cr, settingName, null); Settings.Global.putString(cr, settingName, null);
tracker.reevaluate(); tracker.reevaluate();
mService.waitForIdle(); mService.waitForIdle();
assertFalse(mService.avoidBadWifi()); assertEventuallyTrue(() -> !mService.avoidBadWifi(), 50);
assertTrue(tracker.shouldNotifyWifiUnvalidated()); assertTrue(tracker.shouldNotifyWifiUnvalidated());
} }
@@ -2383,6 +2405,17 @@ public class ConnectivityServiceTest extends AndroidTestCase {
networkCallback.assertNoCallback(); networkCallback.assertNoCallback();
} }
public void assertEventuallyTrue(BooleanSupplier fn, long maxWaitingTimeMs) throws Exception {
long start = SystemClock.elapsedRealtime();
while (SystemClock.elapsedRealtime() <= start + maxWaitingTimeMs) {
if (fn.getAsBoolean()) {
return;
}
Thread.sleep(10);
}
assertTrue(fn.getAsBoolean());
}
private static class TestKeepaliveCallback extends PacketKeepaliveCallback { private static class TestKeepaliveCallback extends PacketKeepaliveCallback {
public static enum CallbackType { ON_STARTED, ON_STOPPED, ON_ERROR }; public static enum CallbackType { ON_STARTED, ON_STOPPED, ON_ERROR };
@@ -2472,6 +2505,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
return mWiFiNetworkAgent.getNetwork(); return mWiFiNetworkAgent.getNetwork();
} }
@SmallTest
public void testPacketKeepalives() throws Exception { public void testPacketKeepalives() throws Exception {
InetAddress myIPv4 = InetAddress.getByName("192.0.2.129"); InetAddress myIPv4 = InetAddress.getByName("192.0.2.129");
InetAddress notMyIPv4 = InetAddress.getByName("192.0.2.35"); InetAddress notMyIPv4 = InetAddress.getByName("192.0.2.35");

View File

@@ -24,6 +24,7 @@ import android.net.Network;
import android.net.NetworkCapabilities; import android.net.NetworkCapabilities;
import android.net.NetworkInfo; import android.net.NetworkInfo;
import android.net.NetworkMisc; import android.net.NetworkMisc;
import android.test.suitebuilder.annotation.SmallTest;
import android.text.format.DateUtils; import android.text.format.DateUtils;
import com.android.internal.R; import com.android.internal.R;
import com.android.server.ConnectivityService; import com.android.server.ConnectivityService;
@@ -70,6 +71,7 @@ public class LingerMonitorTest extends TestCase {
mMonitor = new TestableLingerMonitor(mCtx, mNotifier, HIGH_DAILY_LIMIT, HIGH_RATE_LIMIT); mMonitor = new TestableLingerMonitor(mCtx, mNotifier, HIGH_DAILY_LIMIT, HIGH_RATE_LIMIT);
} }
@SmallTest
public void testTransitions() { public void testTransitions() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
NetworkAgentInfo nai1 = wifiNai(100); NetworkAgentInfo nai1 = wifiNai(100);
@@ -79,6 +81,7 @@ public class LingerMonitorTest extends TestCase {
assertFalse(mMonitor.isNotificationEnabled(nai2, nai1)); assertFalse(mMonitor.isNotificationEnabled(nai2, nai1));
} }
@SmallTest
public void testNotificationOnLinger() { public void testNotificationOnLinger() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION); setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION);
@@ -89,6 +92,7 @@ public class LingerMonitorTest extends TestCase {
verifyNotification(from, to); verifyNotification(from, to);
} }
@SmallTest
public void testToastOnLinger() { public void testToastOnLinger() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST); setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST);
@@ -99,6 +103,7 @@ public class LingerMonitorTest extends TestCase {
verifyToast(from, to); verifyToast(from, to);
} }
@SmallTest
public void testNotificationClearedAfterDisconnect() { public void testNotificationClearedAfterDisconnect() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION); setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION);
@@ -112,6 +117,7 @@ public class LingerMonitorTest extends TestCase {
verify(mNotifier, times(1)).clearNotification(100); verify(mNotifier, times(1)).clearNotification(100);
} }
@SmallTest
public void testNotificationClearedAfterSwitchingBack() { public void testNotificationClearedAfterSwitchingBack() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION); setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION);
@@ -125,6 +131,7 @@ public class LingerMonitorTest extends TestCase {
verify(mNotifier, times(1)).clearNotification(100); verify(mNotifier, times(1)).clearNotification(100);
} }
@SmallTest
public void testUniqueToast() { public void testUniqueToast() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST); setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST);
@@ -142,6 +149,7 @@ public class LingerMonitorTest extends TestCase {
verifyNoNotifications(); verifyNoNotifications();
} }
@SmallTest
public void testMultipleNotifications() { public void testMultipleNotifications() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION); setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION);
@@ -160,6 +168,7 @@ public class LingerMonitorTest extends TestCase {
verifyNotification(wifi2, cell); verifyNotification(wifi2, cell);
} }
@SmallTest
public void testRateLimiting() throws InterruptedException { public void testRateLimiting() throws InterruptedException {
mMonitor = new TestableLingerMonitor(mCtx, mNotifier, HIGH_DAILY_LIMIT, LOW_RATE_LIMIT); mMonitor = new TestableLingerMonitor(mCtx, mNotifier, HIGH_DAILY_LIMIT, LOW_RATE_LIMIT);
@@ -185,6 +194,7 @@ public class LingerMonitorTest extends TestCase {
verifyNoNotifications(); verifyNoNotifications();
} }
@SmallTest
public void testDailyLimiting() throws InterruptedException { public void testDailyLimiting() throws InterruptedException {
mMonitor = new TestableLingerMonitor(mCtx, mNotifier, LOW_DAILY_LIMIT, HIGH_RATE_LIMIT); mMonitor = new TestableLingerMonitor(mCtx, mNotifier, LOW_DAILY_LIMIT, HIGH_RATE_LIMIT);
@@ -211,6 +221,7 @@ public class LingerMonitorTest extends TestCase {
verifyNoNotifications(); verifyNoNotifications();
} }
@SmallTest
public void testUniqueNotification() { public void testUniqueNotification() {
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION); setNotificationType(LingerMonitor.NOTIFY_TYPE_NOTIFICATION);
@@ -227,6 +238,7 @@ public class LingerMonitorTest extends TestCase {
verifyNotification(from, to); verifyNotification(from, to);
} }
@SmallTest
public void testIgnoreNeverValidatedNetworks() { public void testIgnoreNeverValidatedNetworks() {
setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST); setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST);
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
@@ -238,6 +250,7 @@ public class LingerMonitorTest extends TestCase {
verifyNoNotifications(); verifyNoNotifications();
} }
@SmallTest
public void testIgnoreCurrentlyValidatedNetworks() { public void testIgnoreCurrentlyValidatedNetworks() {
setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST); setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST);
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
@@ -249,6 +262,7 @@ public class LingerMonitorTest extends TestCase {
verifyNoNotifications(); verifyNoNotifications();
} }
@SmallTest
public void testNoNotificationType() { public void testNoNotificationType() {
setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST); setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST);
setNotificationSwitch(); setNotificationSwitch();
@@ -259,6 +273,7 @@ public class LingerMonitorTest extends TestCase {
verifyNoNotifications(); verifyNoNotifications();
} }
@SmallTest
public void testNoTransitionToNotify() { public void testNoTransitionToNotify() {
setNotificationType(LingerMonitor.NOTIFY_TYPE_NONE); setNotificationType(LingerMonitor.NOTIFY_TYPE_NONE);
setNotificationSwitch(transition(WIFI, CELLULAR)); setNotificationSwitch(transition(WIFI, CELLULAR));
@@ -269,6 +284,7 @@ public class LingerMonitorTest extends TestCase {
verifyNoNotifications(); verifyNoNotifications();
} }
@SmallTest
public void testDifferentTransitionToNotify() { public void testDifferentTransitionToNotify() {
setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST); setNotificationType(LingerMonitor.NOTIFY_TYPE_TOAST);
setNotificationSwitch(transition(CELLULAR, WIFI)); setNotificationSwitch(transition(CELLULAR, WIFI));

View File

@@ -22,6 +22,8 @@ import android.net.Network;
import android.net.metrics.DnsEvent; import android.net.metrics.DnsEvent;
import android.net.metrics.INetdEventListener; import android.net.metrics.INetdEventListener;
import android.net.metrics.IpConnectivityLog; import android.net.metrics.IpConnectivityLog;
import android.os.RemoteException;
import android.test.suitebuilder.annotation.SmallTest;
import junit.framework.TestCase; import junit.framework.TestCase;
import org.junit.Before; import org.junit.Before;
@@ -82,6 +84,7 @@ public class NetdEventListenerServiceTest extends TestCase {
verify(mCm, times(1)).registerNetworkCallback(any(), mCallbackCaptor.capture()); verify(mCm, times(1)).registerNetworkCallback(any(), mCallbackCaptor.capture());
} }
@SmallTest
public void testOneBatch() throws Exception { public void testOneBatch() throws Exception {
log(105, LATENCIES); log(105, LATENCIES);
log(106, Arrays.copyOf(LATENCIES, BATCH_SIZE - 1)); // one lookup short of a batch event log(106, Arrays.copyOf(LATENCIES, BATCH_SIZE - 1)); // one lookup short of a batch event
@@ -96,6 +99,7 @@ public class NetdEventListenerServiceTest extends TestCase {
new DnsEvent(106, EVENT_TYPES, RETURN_CODES, LATENCIES)); new DnsEvent(106, EVENT_TYPES, RETURN_CODES, LATENCIES));
} }
@SmallTest
public void testSeveralBatches() throws Exception { public void testSeveralBatches() throws Exception {
log(105, LATENCIES); log(105, LATENCIES);
log(106, LATENCIES); log(106, LATENCIES);
@@ -109,6 +113,7 @@ public class NetdEventListenerServiceTest extends TestCase {
new DnsEvent(107, EVENT_TYPES, RETURN_CODES, LATENCIES)); new DnsEvent(107, EVENT_TYPES, RETURN_CODES, LATENCIES));
} }
@SmallTest
public void testBatchAndNetworkLost() throws Exception { public void testBatchAndNetworkLost() throws Exception {
byte[] eventTypes = Arrays.copyOf(EVENT_TYPES, 20); byte[] eventTypes = Arrays.copyOf(EVENT_TYPES, 20);
byte[] returnCodes = Arrays.copyOf(RETURN_CODES, 20); byte[] returnCodes = Arrays.copyOf(RETURN_CODES, 20);
@@ -125,6 +130,7 @@ public class NetdEventListenerServiceTest extends TestCase {
new DnsEvent(105, EVENT_TYPES, RETURN_CODES, LATENCIES)); new DnsEvent(105, EVENT_TYPES, RETURN_CODES, LATENCIES));
} }
@SmallTest
public void testConcurrentBatchesAndDumps() throws Exception { public void testConcurrentBatchesAndDumps() throws Exception {
final long stop = System.currentTimeMillis() + 100; final long stop = System.currentTimeMillis() + 100;
final PrintWriter pw = new PrintWriter(new FileOutputStream("/dev/null")); final PrintWriter pw = new PrintWriter(new FileOutputStream("/dev/null"));
@@ -146,6 +152,7 @@ public class NetdEventListenerServiceTest extends TestCase {
new DnsEvent(107, EVENT_TYPES, RETURN_CODES, LATENCIES)); new DnsEvent(107, EVENT_TYPES, RETURN_CODES, LATENCIES));
} }
@SmallTest
public void testConcurrentBatchesAndNetworkLoss() throws Exception { public void testConcurrentBatchesAndNetworkLoss() throws Exception {
logAsync(105, LATENCIES); logAsync(105, LATENCIES);
Thread.sleep(10L); Thread.sleep(10L);
@@ -157,9 +164,13 @@ public class NetdEventListenerServiceTest extends TestCase {
} }
void log(int netId, int[] latencies) { void log(int netId, int[] latencies) {
for (int l : latencies) { try {
mNetdEventListenerService.onDnsEvent(netId, EVENT_TYPE, RETURN_CODE, l, null, null, 0, for (int l : latencies) {
0); mNetdEventListenerService.onDnsEvent(netId, EVENT_TYPE, RETURN_CODE, l, null, null,
0, 0);
}
} catch (RemoteException re) {
throw re.rethrowFromSystemServer();
} }
} }

View File

@@ -25,9 +25,11 @@ import static org.mockito.Mockito.*;
import android.annotation.UserIdInt; import android.annotation.UserIdInt;
import android.app.AppOpsManager; import android.app.AppOpsManager;
import android.app.NotificationManager;
import android.content.Context; import android.content.Context;
import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import android.content.pm.UserInfo; import android.content.pm.UserInfo;
import android.net.NetworkInfo.DetailedState;
import android.net.UidRange; import android.net.UidRange;
import android.os.INetworkManagementService; import android.os.INetworkManagementService;
import android.os.Looper; import android.os.Looper;
@@ -43,6 +45,8 @@ import java.util.Arrays;
import java.util.Map; import java.util.Map;
import java.util.Set; import java.util.Set;
import org.mockito.ArgumentCaptor;
import org.mockito.InOrder;
import org.mockito.Mock; import org.mockito.Mock;
import org.mockito.MockitoAnnotations; import org.mockito.MockitoAnnotations;
@@ -88,14 +92,18 @@ public class VpnTest extends AndroidTestCase {
@Mock private PackageManager mPackageManager; @Mock private PackageManager mPackageManager;
@Mock private INetworkManagementService mNetService; @Mock private INetworkManagementService mNetService;
@Mock private AppOpsManager mAppOps; @Mock private AppOpsManager mAppOps;
@Mock private NotificationManager mNotificationManager;
@Override @Override
public void setUp() throws Exception { public void setUp() throws Exception {
MockitoAnnotations.initMocks(this); MockitoAnnotations.initMocks(this);
when(mContext.getPackageManager()).thenReturn(mPackageManager); when(mContext.getPackageManager()).thenReturn(mPackageManager);
setMockedPackages(mPackages); setMockedPackages(mPackages);
when(mContext.getPackageName()).thenReturn(Vpn.class.getPackage().getName());
when(mContext.getSystemService(eq(Context.USER_SERVICE))).thenReturn(mUserManager); when(mContext.getSystemService(eq(Context.USER_SERVICE))).thenReturn(mUserManager);
when(mContext.getSystemService(eq(Context.APP_OPS_SERVICE))).thenReturn(mAppOps); when(mContext.getSystemService(eq(Context.APP_OPS_SERVICE))).thenReturn(mAppOps);
when(mContext.getSystemService(eq(Context.NOTIFICATION_SERVICE)))
.thenReturn(mNotificationManager);
doNothing().when(mNetService).registerObserver(any()); doNothing().when(mNetService).registerObserver(any());
} }
@@ -103,7 +111,7 @@ public class VpnTest extends AndroidTestCase {
public void testRestrictedProfilesAreAddedToVpn() { public void testRestrictedProfilesAreAddedToVpn() {
setMockedUsers(primaryUser, secondaryUser, restrictedProfileA, restrictedProfileB); setMockedUsers(primaryUser, secondaryUser, restrictedProfileA, restrictedProfileB);
final Vpn vpn = new MockVpn(primaryUser.id); final Vpn vpn = spyVpn(primaryUser.id);
final Set<UidRange> ranges = vpn.createUserAndRestrictedProfilesRanges(primaryUser.id, final Set<UidRange> ranges = vpn.createUserAndRestrictedProfilesRanges(primaryUser.id,
null, null); null, null);
@@ -117,7 +125,7 @@ public class VpnTest extends AndroidTestCase {
public void testManagedProfilesAreNotAddedToVpn() { public void testManagedProfilesAreNotAddedToVpn() {
setMockedUsers(primaryUser, managedProfileA); setMockedUsers(primaryUser, managedProfileA);
final Vpn vpn = new MockVpn(primaryUser.id); final Vpn vpn = spyVpn(primaryUser.id);
final Set<UidRange> ranges = vpn.createUserAndRestrictedProfilesRanges(primaryUser.id, final Set<UidRange> ranges = vpn.createUserAndRestrictedProfilesRanges(primaryUser.id,
null, null); null, null);
@@ -130,7 +138,7 @@ public class VpnTest extends AndroidTestCase {
public void testAddUserToVpnOnlyAddsOneUser() { public void testAddUserToVpnOnlyAddsOneUser() {
setMockedUsers(primaryUser, restrictedProfileA, managedProfileA); setMockedUsers(primaryUser, restrictedProfileA, managedProfileA);
final Vpn vpn = new MockVpn(primaryUser.id); final Vpn vpn = spyVpn(primaryUser.id);
final Set<UidRange> ranges = new ArraySet<>(); final Set<UidRange> ranges = new ArraySet<>();
vpn.addUserToRanges(ranges, primaryUser.id, null, null); vpn.addUserToRanges(ranges, primaryUser.id, null, null);
@@ -141,7 +149,7 @@ public class VpnTest extends AndroidTestCase {
@SmallTest @SmallTest
public void testUidWhiteAndBlacklist() throws Exception { public void testUidWhiteAndBlacklist() throws Exception {
final Vpn vpn = new MockVpn(primaryUser.id); final Vpn vpn = spyVpn(primaryUser.id);
final UidRange user = UidRange.createForUser(primaryUser.id); final UidRange user = UidRange.createForUser(primaryUser.id);
final String[] packages = {PKGS[0], PKGS[1], PKGS[2]}; final String[] packages = {PKGS[0], PKGS[1], PKGS[2]};
@@ -166,15 +174,15 @@ public class VpnTest extends AndroidTestCase {
@SmallTest @SmallTest
public void testLockdownChangingPackage() throws Exception { public void testLockdownChangingPackage() throws Exception {
final MockVpn vpn = new MockVpn(primaryUser.id); final Vpn vpn = spyVpn(primaryUser.id);
final UidRange user = UidRange.createForUser(primaryUser.id); final UidRange user = UidRange.createForUser(primaryUser.id);
// Default state. // Default state.
vpn.assertUnblocked(user.start + PKG_UIDS[0], user.start + PKG_UIDS[1], user.start + PKG_UIDS[2], user.start + PKG_UIDS[3]); assertUnblocked(vpn, user.start + PKG_UIDS[0], user.start + PKG_UIDS[1], user.start + PKG_UIDS[2], user.start + PKG_UIDS[3]);
// Set always-on without lockdown. // Set always-on without lockdown.
assertTrue(vpn.setAlwaysOnPackage(PKGS[1], false)); assertTrue(vpn.setAlwaysOnPackage(PKGS[1], false));
vpn.assertUnblocked(user.start + PKG_UIDS[0], user.start + PKG_UIDS[1], user.start + PKG_UIDS[2], user.start + PKG_UIDS[3]); assertUnblocked(vpn, user.start + PKG_UIDS[0], user.start + PKG_UIDS[1], user.start + PKG_UIDS[2], user.start + PKG_UIDS[3]);
// Set always-on with lockdown. // Set always-on with lockdown.
assertTrue(vpn.setAlwaysOnPackage(PKGS[1], true)); assertTrue(vpn.setAlwaysOnPackage(PKGS[1], true));
@@ -182,8 +190,8 @@ public class VpnTest extends AndroidTestCase {
new UidRange(user.start, user.start + PKG_UIDS[1] - 1), new UidRange(user.start, user.start + PKG_UIDS[1] - 1),
new UidRange(user.start + PKG_UIDS[1] + 1, user.stop) new UidRange(user.start + PKG_UIDS[1] + 1, user.stop)
})); }));
vpn.assertBlocked(user.start + PKG_UIDS[0], user.start + PKG_UIDS[2], user.start + PKG_UIDS[3]); assertBlocked(vpn, user.start + PKG_UIDS[0], user.start + PKG_UIDS[2], user.start + PKG_UIDS[3]);
vpn.assertUnblocked(user.start + PKG_UIDS[1]); assertUnblocked(vpn, user.start + PKG_UIDS[1]);
// Switch to another app. // Switch to another app.
assertTrue(vpn.setAlwaysOnPackage(PKGS[3], true)); assertTrue(vpn.setAlwaysOnPackage(PKGS[3], true));
@@ -195,13 +203,13 @@ public class VpnTest extends AndroidTestCase {
new UidRange(user.start, user.start + PKG_UIDS[3] - 1), new UidRange(user.start, user.start + PKG_UIDS[3] - 1),
new UidRange(user.start + PKG_UIDS[3] + 1, user.stop) new UidRange(user.start + PKG_UIDS[3] + 1, user.stop)
})); }));
vpn.assertBlocked(user.start + PKG_UIDS[0], user.start + PKG_UIDS[1], user.start + PKG_UIDS[2]); assertBlocked(vpn, user.start + PKG_UIDS[0], user.start + PKG_UIDS[1], user.start + PKG_UIDS[2]);
vpn.assertUnblocked(user.start + PKG_UIDS[3]); assertUnblocked(vpn, user.start + PKG_UIDS[3]);
} }
@SmallTest @SmallTest
public void testLockdownAddingAProfile() throws Exception { public void testLockdownAddingAProfile() throws Exception {
final MockVpn vpn = new MockVpn(primaryUser.id); final Vpn vpn = spyVpn(primaryUser.id);
setMockedUsers(primaryUser); setMockedUsers(primaryUser);
// Make a copy of the restricted profile, as we're going to mark it deleted halfway through. // Make a copy of the restricted profile, as we're going to mark it deleted halfway through.
@@ -220,7 +228,7 @@ public class VpnTest extends AndroidTestCase {
})); }));
// Verify restricted user isn't affected at first. // Verify restricted user isn't affected at first.
vpn.assertUnblocked(profile.start + PKG_UIDS[0]); assertUnblocked(vpn, profile.start + PKG_UIDS[0]);
// Add the restricted user. // Add the restricted user.
setMockedUsers(primaryUser, tempProfile); setMockedUsers(primaryUser, tempProfile);
@@ -239,24 +247,53 @@ public class VpnTest extends AndroidTestCase {
})); }));
} }
@SmallTest
public void testNotificationShownForAlwaysOnApp() {
final Vpn vpn = spyVpn(primaryUser.id);
final InOrder order = inOrder(vpn);
setMockedUsers(primaryUser);
// Don't show a notification for regular disconnected states.
vpn.updateState(DetailedState.DISCONNECTED, TAG);
order.verify(vpn).updateAlwaysOnNotificationInternal(false);
// Start showing a notification for disconnected once always-on.
vpn.setAlwaysOnPackage(PKGS[0], false);
order.verify(vpn).updateAlwaysOnNotificationInternal(true);
// Stop showing the notification once connected.
vpn.updateState(DetailedState.CONNECTED, TAG);
order.verify(vpn).updateAlwaysOnNotificationInternal(false);
// Show the notification if we disconnect again.
vpn.updateState(DetailedState.DISCONNECTED, TAG);
order.verify(vpn).updateAlwaysOnNotificationInternal(true);
// Notification should be cleared after unsetting always-on package.
vpn.setAlwaysOnPackage(null, false);
order.verify(vpn).updateAlwaysOnNotificationInternal(false);
}
/** /**
* A subclass of {@link Vpn} with some of the fields pre-mocked. * Mock some methods of vpn object.
*/ */
private class MockVpn extends Vpn { private Vpn spyVpn(@UserIdInt int userId) {
public MockVpn(@UserIdInt int userId) { final Vpn vpn = spy(new Vpn(Looper.myLooper(), mContext, mNetService, userId));
super(Looper.myLooper(), mContext, mNetService, userId);
}
public void assertBlocked(int... uids) { // Block calls to the NotificationManager or PendingIntent#getActivity.
for (int uid : uids) { doNothing().when(vpn).updateAlwaysOnNotificationInternal(anyBoolean());
assertTrue("Uid " + uid + " should be blocked", isBlockingUid(uid)); return vpn;
} }
}
public void assertUnblocked(int... uids) { private static void assertBlocked(Vpn vpn, int... uids) {
for (int uid : uids) { for (int uid : uids) {
assertFalse("Uid " + uid + " should not be blocked", isBlockingUid(uid)); assertTrue("Uid " + uid + " should be blocked", vpn.isBlockingUid(uid));
} }
}
private static void assertUnblocked(Vpn vpn, int... uids) {
for (int uid : uids) {
assertFalse("Uid " + uid + " should not be blocked", vpn.isBlockingUid(uid));
} }
} }