[CS] Remove timeout event after first available

Guarantees that timeouts are only delivered if a network never
becomes available. Once a network is available the timeout is
canceled.

Bug: 31402633
Test: all timeout related unit tests pass (new one added)

(cherry picked from commit 5eba9d7061)

Change-Id: I7cd3086544c881915fc6dbf14b87a24ab0cd8748
This commit is contained in:
Etan Cohen
2016-10-27 15:05:50 -07:00
committed by Lorenzo Colitti
parent ebc2b946ee
commit 0aa0f341ba
2 changed files with 36 additions and 12 deletions

View File

@@ -5319,6 +5319,7 @@ public class ConnectivityService extends IConnectivityManager.Stub
// notify only this one new request of the current state // notify only this one new request of the current state
protected void notifyNetworkCallback(NetworkAgentInfo nai, NetworkRequestInfo nri) { protected void notifyNetworkCallback(NetworkAgentInfo nai, NetworkRequestInfo nri) {
int notifyType = ConnectivityManager.CALLBACK_AVAILABLE; int notifyType = ConnectivityManager.CALLBACK_AVAILABLE;
mHandler.removeMessages(EVENT_TIMEOUT_NETWORK_REQUEST, nri);
if (nri.mPendingIntent == null) { if (nri.mPendingIntent == null) {
callCallbackForRequest(nri, nai, notifyType, 0); callCallbackForRequest(nri, nai, notifyType, 0);
} else { } else {

View File

@@ -727,10 +727,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
static private void waitFor(Criteria criteria) { static private void waitFor(Criteria criteria) {
int delays = 0; int delays = 0;
while (!criteria.get()) { while (!criteria.get()) {
try { sleepFor(50);
Thread.sleep(50);
} catch (InterruptedException e) {
}
if (++delays == 10) fail(); if (++delays == 10) fail();
} }
} }
@@ -2327,10 +2324,30 @@ public class ConnectivityServiceTest extends AndroidTestCase {
networkCallback.expectCallback(CallbackState.AVAILABLE, mWiFiNetworkAgent); networkCallback.expectCallback(CallbackState.AVAILABLE, mWiFiNetworkAgent);
// pass timeout and validate that UNAVAILABLE is not called // pass timeout and validate that UNAVAILABLE is not called
try { sleepFor(15);
Thread.sleep(15); networkCallback.assertNoCallback();
} catch (InterruptedException e) { }
}
/**
* Validate that a satisfied network request followed by a disconnected (lost) network does
* not trigger onUnavailable() once the time-out period expires.
*/
@SmallTest
public void testSatisfiedThenLostNetworkRequestDoesNotTriggerOnUnavailable() {
NetworkRequest nr = new NetworkRequest.Builder().addTransportType(
NetworkCapabilities.TRANSPORT_WIFI).build();
final TestNetworkCallback networkCallback = new TestNetworkCallback();
mCm.requestNetwork(nr, networkCallback, 500);
mWiFiNetworkAgent = new MockNetworkAgent(TRANSPORT_WIFI);
mWiFiNetworkAgent.connect(false);
networkCallback.expectCallback(CallbackState.AVAILABLE, mWiFiNetworkAgent);
sleepFor(20);
mWiFiNetworkAgent.disconnect();
networkCallback.expectCallback(CallbackState.LOST, mWiFiNetworkAgent);
// pass timeout and validate that UNAVAILABLE is not called
sleepFor(600);
networkCallback.assertNoCallback(); networkCallback.assertNoCallback();
} }
@@ -2372,10 +2389,7 @@ public class ConnectivityServiceTest extends AndroidTestCase {
// pass timeout and validate that no callbacks // pass timeout and validate that no callbacks
// Note: doesn't validate that nothing called from CS since even if called the CM already // Note: doesn't validate that nothing called from CS since even if called the CM already
// unregisters the callback and won't pass it through! // unregisters the callback and won't pass it through!
try { sleepFor(15);
Thread.sleep(15);
} catch (InterruptedException e) {
}
networkCallback.assertNoCallback(); networkCallback.assertNoCallback();
// create a network satisfying request - validate that request not triggered // create a network satisfying request - validate that request not triggered
@@ -2788,4 +2802,13 @@ public class ConnectivityServiceTest extends AndroidTestCase {
mCm.unregisterNetworkCallback(pendingIntent); mCm.unregisterNetworkCallback(pendingIntent);
} }
} }
/* test utilities */
static private void sleepFor(int ms) {
try {
Thread.sleep(ms);
} catch (InterruptedException e) {
}
}
} }