import android.net.ConnectivityManager;
import android.net.LinkAddress;
import android.net.LinkProperties;
+import android.net.NetworkInfo;
import android.net.RouteInfo;
import android.os.INetworkManagementService;
import android.os.RemoteException;
// This must match the interface prefix in clatd.c.
private static final String CLAT_PREFIX = "v4-";
- // The network types we will start clatd on,
+ // The network types on which we will start clatd,
// allowing clat only on networks for which we can support IPv6-only.
private static final int[] NETWORK_TYPES = {
- ConnectivityManager.TYPE_MOBILE,
- ConnectivityManager.TYPE_WIFI,
- ConnectivityManager.TYPE_ETHERNET,
+ ConnectivityManager.TYPE_MOBILE,
+ ConnectivityManager.TYPE_WIFI,
+ ConnectivityManager.TYPE_ETHERNET,
+ };
+
+ // The network states in which running clatd is supported.
+ private static final NetworkInfo.State[] NETWORK_STATES = {
+ NetworkInfo.State.CONNECTED,
+ NetworkInfo.State.SUSPENDED,
};
private final INetworkManagementService mNMService;
*/
public static boolean requiresClat(NetworkAgentInfo nai) {
// TODO: migrate to NetworkCapabilities.TRANSPORT_*.
- final int netType = nai.networkInfo.getType();
final boolean supported = ArrayUtils.contains(NETWORK_TYPES, nai.networkInfo.getType());
- // TODO: this should also consider if the network is in SUSPENDED state to avoid stopping
- // clatd in SUSPENDED state.
- final boolean connected = nai.networkInfo.isConnected();
+ final boolean connected = ArrayUtils.contains(NETWORK_STATES, nai.networkInfo.getState());
// We only run clat on networks that don't have a native IPv4 address.
final boolean hasIPv4Address =
(nai.linkProperties != null) && nai.linkProperties.hasIPv4Address();
}
@Test
+ public void testRequiresClat() throws Exception {
+ final int[] supportedTypes = {
+ ConnectivityManager.TYPE_MOBILE,
+ ConnectivityManager.TYPE_WIFI,
+ ConnectivityManager.TYPE_ETHERNET,
+ };
+
+ // NetworkInfo doesn't allow setting the State directly, but rather
+ // requires setting DetailedState in order set State as a side-effect.
+ final NetworkInfo.DetailedState[] supportedDetailedStates = {
+ NetworkInfo.DetailedState.CONNECTED,
+ NetworkInfo.DetailedState.SUSPENDED,
+ };
+
+ for (int type : supportedTypes) {
+ mNai.networkInfo.setType(type);
+ for (NetworkInfo.DetailedState state : supportedDetailedStates) {
+ mNai.networkInfo.setDetailedState(state, "reason", "extraInfo");
+ assertTrue(
+ String.format("requiresClat expected for type=%d state=%s", type, state),
+ Nat464Xlat.requiresClat(mNai));
+ }
+ }
+ }
+
+ @Test
public void testNormalStartAndStop() throws Exception {
Nat464Xlat nat = makeNat464Xlat();
ArgumentCaptor<LinkProperties> c = ArgumentCaptor.forClass(LinkProperties.class);