1 /* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.systemui.statusbar.policy; 18 19 import android.content.Intent; 20 import android.net.ConnectivityManager; 21 import android.net.NetworkCapabilities; 22 import android.net.NetworkScoreManager; 23 import android.net.wifi.WifiManager; 24 import android.os.Looper; 25 import android.telephony.PhoneStateListener; 26 import android.telephony.ServiceState; 27 import android.telephony.SignalStrength; 28 import android.telephony.SubscriptionInfo; 29 import android.telephony.SubscriptionManager; 30 import android.telephony.TelephonyManager; 31 import android.util.Log; 32 import com.android.internal.telephony.cdma.EriInfo; 33 import com.android.settingslib.net.DataUsageController; 34 import com.android.systemui.statusbar.phone.SignalDrawable; 35 import com.android.systemui.statusbar.policy.DeviceProvisionedController.DeviceProvisionedListener; 36 import com.android.systemui.statusbar.policy.NetworkController.IconState; 37 import com.android.systemui.statusbar.policy.NetworkController.SignalCallback; 38 import com.android.systemui.statusbar.policy.NetworkControllerImpl.Config; 39 import com.android.systemui.statusbar.policy.NetworkControllerImpl.SubscriptionDefaults; 40 import com.android.systemui.SysuiTestCase; 41 42 import org.junit.Before; 43 import org.junit.Rule; 44 import org.junit.rules.TestWatcher; 45 import org.junit.runner.Description; 46 import org.mockito.ArgumentCaptor; 47 import org.mockito.Mockito; 48 import org.mockito.invocation.InvocationOnMock; 49 import org.mockito.stubbing.Answer; 50 51 import java.io.PrintWriter; 52 import java.io.StringWriter; 53 import java.util.ArrayList; 54 import java.util.List; 55 56 import static junit.framework.Assert.assertEquals; 57 58 import static org.mockito.Matchers.any; 59 import static org.mockito.Matchers.anyBoolean; 60 import static org.mockito.Matchers.anyInt; 61 import static org.mockito.Matchers.anyString; 62 import static org.mockito.Matchers.eq; 63 import static org.mockito.Mockito.doAnswer; 64 import static org.mockito.Mockito.mock; 65 import static org.mockito.Mockito.when; 66 67 public class NetworkControllerBaseTest extends SysuiTestCase { 68 private static final String TAG = "NetworkControllerBaseTest"; 69 protected static final int DEFAULT_LEVEL = 2; 70 protected static final int DEFAULT_SIGNAL_STRENGTH = DEFAULT_LEVEL; 71 protected static final int DEFAULT_QS_SIGNAL_STRENGTH = DEFAULT_LEVEL; 72 protected static final int DEFAULT_ICON = TelephonyIcons.ICON_3G; 73 protected static final int DEFAULT_QS_ICON = TelephonyIcons.QS_DATA_3G; 74 75 protected NetworkControllerImpl mNetworkController; 76 protected MobileSignalController mMobileSignalController; 77 protected PhoneStateListener mPhoneStateListener; 78 protected SignalStrength mSignalStrength; 79 protected ServiceState mServiceState; 80 protected ConnectivityManager mMockCm; 81 protected WifiManager mMockWm; 82 protected SubscriptionManager mMockSm; 83 protected TelephonyManager mMockTm; 84 protected Config mConfig; 85 protected CallbackHandler mCallbackHandler; 86 protected SubscriptionDefaults mMockSubDefaults; 87 protected NetworkScoreManager mMockNetworkScoreManager; 88 protected DeviceProvisionedController mMockProvisionController; 89 protected DeviceProvisionedListener mUserCallback; 90 91 protected int mSubId; 92 93 private NetworkCapabilities mNetCapabilities; 94 95 @Rule 96 public TestWatcher failWatcher = new TestWatcher() { 97 @Override 98 protected void failed(Throwable e, Description description) { 99 // Print out mNetworkController state if the test fails. 100 StringWriter sw = new StringWriter(); 101 PrintWriter pw = new PrintWriter(sw); 102 mNetworkController.dump(null, pw, null); 103 pw.flush(); 104 Log.d(TAG, sw.toString()); 105 } 106 }; 107 108 @Before 109 public void setUp() throws Exception { 110 mMockWm = mock(WifiManager.class); 111 mMockTm = mock(TelephonyManager.class); 112 mMockSm = mock(SubscriptionManager.class); 113 mMockCm = mock(ConnectivityManager.class); 114 mMockSubDefaults = mock(SubscriptionDefaults.class); 115 mNetCapabilities = new NetworkCapabilities(); 116 mMockNetworkScoreManager = mock(NetworkScoreManager.class); 117 118 when(mMockCm.isNetworkSupported(ConnectivityManager.TYPE_MOBILE)).thenReturn(true); 119 when(mMockCm.getDefaultNetworkCapabilitiesForUser(0)).thenReturn( 120 new NetworkCapabilities[] { mNetCapabilities }); 121 122 mSignalStrength = mock(SignalStrength.class); 123 mServiceState = mock(ServiceState.class); 124 125 mConfig = new Config(); 126 mConfig.hspaDataDistinguishable = true; 127 mCallbackHandler = mock(CallbackHandler.class); 128 129 mMockProvisionController = mock(DeviceProvisionedController.class); 130 when(mMockProvisionController.isUserSetup(anyInt())).thenReturn(true); 131 doAnswer(invocation -> { 132 mUserCallback = (DeviceProvisionedListener) invocation.getArguments()[0]; 133 mUserCallback.onUserSetupChanged(); 134 mUserCallback.onDeviceProvisionedChanged(); 135 return null; 136 }).when(mMockProvisionController).addCallback(any()); 137 138 mNetworkController = new NetworkControllerImpl(mContext, mMockCm, mMockNetworkScoreManager, 139 mMockTm, mMockWm, mMockSm, 140 mConfig, Looper.getMainLooper(), mCallbackHandler, 141 mock(AccessPointControllerImpl.class), mock(DataUsageController.class), 142 mMockSubDefaults, mMockProvisionController); 143 setupNetworkController(); 144 145 // Trigger blank callbacks to always get the current state (some tests don't trigger 146 // changes from default state). 147 mNetworkController.addCallback(mock(SignalCallback.class)); 148 mNetworkController.addEmergencyListener(null); 149 } 150 151 protected void setupNetworkController() { 152 // For now just pretend to be the data sim, so we can test that too. 153 mSubId = SubscriptionManager.DEFAULT_SUBSCRIPTION_ID; 154 when(mMockTm.getDataEnabled(mSubId)).thenReturn(true); 155 setDefaultSubId(mSubId); 156 setSubscriptions(mSubId); 157 mMobileSignalController = mNetworkController.mMobileSignalControllers.get(mSubId); 158 mPhoneStateListener = mMobileSignalController.mPhoneStateListener; 159 } 160 161 protected void setDefaultSubId(int subId) { 162 when(mMockSubDefaults.getDefaultDataSubId()).thenReturn(subId); 163 when(mMockSubDefaults.getDefaultVoiceSubId()).thenReturn(subId); 164 } 165 166 protected void setSubscriptions(int... subIds) { 167 List<SubscriptionInfo> subs = new ArrayList<SubscriptionInfo>(); 168 for (int subId : subIds) { 169 SubscriptionInfo subscription = mock(SubscriptionInfo.class); 170 when(subscription.getSubscriptionId()).thenReturn(subId); 171 subs.add(subscription); 172 } 173 when(mMockSm.getActiveSubscriptionInfoList()).thenReturn(subs); 174 mNetworkController.doUpdateMobileControllers(); 175 } 176 177 protected NetworkControllerImpl setUpNoMobileData() { 178 when(mMockCm.isNetworkSupported(ConnectivityManager.TYPE_MOBILE)).thenReturn(false); 179 NetworkControllerImpl networkControllerNoMobile 180 = new NetworkControllerImpl(mContext, mMockCm, mMockNetworkScoreManager, mMockTm, 181 mMockWm, mMockSm, mConfig, mContext.getMainLooper(), mCallbackHandler, 182 mock(AccessPointControllerImpl.class), 183 mock(DataUsageController.class), mMockSubDefaults, 184 mock(DeviceProvisionedController.class)); 185 186 setupNetworkController(); 187 188 return networkControllerNoMobile; 189 190 } 191 192 // 2 Bars 3G GSM. 193 public void setupDefaultSignal() { 194 setIsGsm(true); 195 setVoiceRegState(ServiceState.STATE_IN_SERVICE); 196 setGsmRoaming(false); 197 setLevel(DEFAULT_LEVEL); 198 updateDataConnectionState(TelephonyManager.DATA_CONNECTED, 199 TelephonyManager.NETWORK_TYPE_UMTS); 200 setConnectivity(NetworkCapabilities.TRANSPORT_CELLULAR, true, true); 201 } 202 203 public void setConnectivity(int networkType, boolean inetCondition, boolean isConnected) { 204 Intent i = new Intent(ConnectivityManager.INET_CONDITION_ACTION); 205 // TODO: Separate out into several NetworkCapabilities. 206 if (isConnected) { 207 mNetCapabilities.addTransportType(networkType); 208 } else { 209 mNetCapabilities.removeTransportType(networkType); 210 } 211 if (inetCondition) { 212 mNetCapabilities.addCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED); 213 } else { 214 mNetCapabilities.removeCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED); 215 } 216 217 mNetworkController.onReceive(mContext, i); 218 } 219 220 public void setGsmRoaming(boolean isRoaming) { 221 when(mServiceState.getRoaming()).thenReturn(isRoaming); 222 updateServiceState(); 223 } 224 225 public void setCdmaRoaming(boolean isRoaming) { 226 when(mServiceState.getCdmaEriIconIndex()).thenReturn(isRoaming ? 227 EriInfo.ROAMING_INDICATOR_ON : EriInfo.ROAMING_INDICATOR_OFF); 228 when(mServiceState.getCdmaEriIconMode()).thenReturn(isRoaming ? 229 EriInfo.ROAMING_ICON_MODE_NORMAL : -1); 230 updateServiceState(); 231 } 232 233 public void setVoiceRegState(int voiceRegState) { 234 when(mServiceState.getVoiceRegState()).thenReturn(voiceRegState); 235 updateServiceState(); 236 } 237 238 public void setDataRegState(int dataRegState) { 239 when(mServiceState.getDataRegState()).thenReturn(dataRegState); 240 updateServiceState(); 241 } 242 243 public void setIsEmergencyOnly(boolean isEmergency) { 244 when(mServiceState.isEmergencyOnly()).thenReturn(isEmergency); 245 updateServiceState(); 246 } 247 248 public void setCdmaLevel(int level) { 249 when(mSignalStrength.getCdmaLevel()).thenReturn(level); 250 updateSignalStrength(); 251 } 252 253 public void setLevel(int level) { 254 when(mSignalStrength.getLevel()).thenReturn(level); 255 updateSignalStrength(); 256 } 257 258 public void setIsGsm(boolean gsm) { 259 when(mSignalStrength.isGsm()).thenReturn(gsm); 260 updateSignalStrength(); 261 } 262 263 public void setCdmaEri(int index, int mode) { 264 // TODO: Figure this out. 265 } 266 267 private void updateSignalStrength() { 268 Log.d(TAG, "Sending Signal Strength: " + mSignalStrength); 269 mPhoneStateListener.onSignalStrengthsChanged(mSignalStrength); 270 } 271 272 protected void updateServiceState() { 273 Log.d(TAG, "Sending Service State: " + mServiceState); 274 mPhoneStateListener.onServiceStateChanged(mServiceState); 275 } 276 277 public void updateCallState(int state) { 278 // Inputs not currently used in NetworkControllerImpl. 279 mPhoneStateListener.onCallStateChanged(state, "0123456789"); 280 } 281 282 public void updateDataConnectionState(int dataState, int dataNetType) { 283 when(mServiceState.getDataNetworkType()).thenReturn(dataNetType); 284 mPhoneStateListener.onDataConnectionStateChanged(dataState, dataNetType); 285 } 286 287 public void updateDataActivity(int dataActivity) { 288 mPhoneStateListener.onDataActivity(dataActivity); 289 } 290 291 public void setCarrierNetworkChange(boolean enable) { 292 Log.d(TAG, "setCarrierNetworkChange(" + enable + ")"); 293 mPhoneStateListener.onCarrierNetworkChange(enable); 294 } 295 296 protected void verifyHasNoSims(boolean hasNoSimsVisible) { 297 ArgumentCaptor<Boolean> hasNoSimsArg = ArgumentCaptor.forClass(Boolean.class); 298 299 Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setNoSims(hasNoSimsArg.capture()); 300 assertEquals("No sims", hasNoSimsVisible, (boolean) hasNoSimsArg.getValue()); 301 } 302 303 protected void verifyLastQsMobileDataIndicators(boolean visible, int icon, int typeIcon, 304 boolean dataIn, boolean dataOut) { 305 ArgumentCaptor<IconState> iconArg = ArgumentCaptor.forClass(IconState.class); 306 ArgumentCaptor<Integer> typeIconArg = ArgumentCaptor.forClass(Integer.class); 307 ArgumentCaptor<Boolean> dataInArg = ArgumentCaptor.forClass(Boolean.class); 308 ArgumentCaptor<Boolean> dataOutArg = ArgumentCaptor.forClass(Boolean.class); 309 310 Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setMobileDataIndicators( 311 any(), 312 iconArg.capture(), 313 anyInt(), 314 typeIconArg.capture(), dataInArg.capture(), dataOutArg.capture(), 315 anyString(), anyString(), anyBoolean(), anyInt(), anyBoolean()); 316 IconState iconState = iconArg.getValue(); 317 int state = SignalDrawable.getState(icon, SignalStrength.NUM_SIGNAL_STRENGTH_BINS, 318 false); 319 assertEquals("Visibility in, quick settings", visible, iconState.visible); 320 assertEquals("Signal icon in, quick settings", state, iconState.icon); 321 assertEquals("Data icon in, quick settings", typeIcon, (int) typeIconArg.getValue()); 322 assertEquals("Data direction in, in quick settings", dataIn, 323 (boolean) dataInArg.getValue()); 324 assertEquals("Data direction out, in quick settings", dataOut, 325 (boolean) dataOutArg.getValue()); 326 } 327 328 protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon) { 329 verifyLastMobileDataIndicators(visible, icon, typeIcon, false); 330 } 331 332 protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon, 333 boolean roaming) { 334 verifyLastMobileDataIndicators(visible, icon, typeIcon, roaming, true); 335 } 336 337 protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon, 338 boolean roaming, boolean inet) { 339 ArgumentCaptor<IconState> iconArg = ArgumentCaptor.forClass(IconState.class); 340 ArgumentCaptor<Integer> typeIconArg = ArgumentCaptor.forClass(Integer.class); 341 342 // TODO: Verify all fields. 343 Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setMobileDataIndicators( 344 iconArg.capture(), 345 any(), 346 typeIconArg.capture(), 347 anyInt(), anyBoolean(), anyBoolean(), anyString(), anyString(), anyBoolean(), 348 anyInt(), eq(roaming)); 349 IconState iconState = iconArg.getValue(); 350 351 int state = icon == -1 ? 0 352 : SignalDrawable.getState(icon, SignalStrength.NUM_SIGNAL_STRENGTH_BINS, !inet); 353 assertEquals("Signal icon in status bar", state, iconState.icon); 354 assertEquals("Data icon in status bar", typeIcon, (int) typeIconArg.getValue()); 355 assertEquals("Visibility in status bar", visible, iconState.visible); 356 } 357 358 protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon, 359 boolean qsVisible, int qsIcon, int qsTypeIcon, boolean dataIn, boolean dataOut) { 360 ArgumentCaptor<IconState> iconArg = ArgumentCaptor.forClass(IconState.class); 361 ArgumentCaptor<Integer> typeIconArg = ArgumentCaptor.forClass(Integer.class); 362 ArgumentCaptor<IconState> qsIconArg = ArgumentCaptor.forClass(IconState.class); 363 ArgumentCaptor<Integer> qsTypeIconArg = ArgumentCaptor.forClass(Integer.class); 364 ArgumentCaptor<Boolean> dataInArg = ArgumentCaptor.forClass(Boolean.class); 365 ArgumentCaptor<Boolean> dataOutArg = ArgumentCaptor.forClass(Boolean.class); 366 367 Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setMobileDataIndicators( 368 iconArg.capture(), 369 qsIconArg.capture(), 370 typeIconArg.capture(), 371 qsTypeIconArg.capture(), 372 dataInArg.capture(), 373 dataOutArg.capture(), 374 anyString(), anyString(), anyBoolean(), anyInt(), anyBoolean()); 375 376 IconState iconState = iconArg.getValue(); 377 378 int state = SignalDrawable.getState(icon, SignalStrength.NUM_SIGNAL_STRENGTH_BINS, 379 false); 380 assertEquals("Data icon in status bar", typeIcon, (int) typeIconArg.getValue()); 381 assertEquals("Signal icon in status bar", state, iconState.icon); 382 assertEquals("Visibility in status bar", visible, iconState.visible); 383 384 iconState = qsIconArg.getValue(); 385 assertEquals("Visibility in quick settings", qsVisible, iconState.visible); 386 assertEquals("Signal icon in quick settings", state, iconState.icon); 387 assertEquals("Data icon in quick settings", qsTypeIcon, (int) qsTypeIconArg.getValue()); 388 assertEquals("Data direction in in quick settings", dataIn, 389 (boolean) dataInArg.getValue()); 390 assertEquals("Data direction out in quick settings", dataOut, 391 (boolean) dataOutArg.getValue()); 392 } 393 394 protected void assertNetworkNameEquals(String expected) { 395 assertEquals("Network name", expected, mMobileSignalController.getState().networkName); 396 } 397 } 398