1 /* 2 * Copyright (C) 2016 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 package com.android.server.wifi; 17 18 import static android.net.wifi.WifiManager.DEVICE_MOBILITY_STATE_HIGH_MVMT; 19 import static android.net.wifi.WifiManager.DEVICE_MOBILITY_STATE_LOW_MVMT; 20 import static android.net.wifi.WifiManager.DEVICE_MOBILITY_STATE_STATIONARY; 21 import static android.net.wifi.WifiManager.DEVICE_MOBILITY_STATE_UNKNOWN; 22 23 import static com.android.server.wifi.WifiMetricsTestUtil.assertDeviceMobilityStatePnoScanStatsEqual; 24 import static com.android.server.wifi.WifiMetricsTestUtil.assertExperimentProbeCountsEqual; 25 import static com.android.server.wifi.WifiMetricsTestUtil.assertHistogramBucketsEqual; 26 import static com.android.server.wifi.WifiMetricsTestUtil.assertKeyCountsEqual; 27 import static com.android.server.wifi.WifiMetricsTestUtil.assertLinkProbeFailureReasonCountsEqual; 28 import static com.android.server.wifi.WifiMetricsTestUtil.assertLinkProbeStaEventsEqual; 29 import static com.android.server.wifi.WifiMetricsTestUtil.buildDeviceMobilityStatePnoScanStats; 30 import static com.android.server.wifi.WifiMetricsTestUtil.buildExperimentProbeCounts; 31 import static com.android.server.wifi.WifiMetricsTestUtil.buildHistogramBucketInt32; 32 import static com.android.server.wifi.WifiMetricsTestUtil.buildInt32Count; 33 import static com.android.server.wifi.WifiMetricsTestUtil.buildLinkProbeFailureReasonCount; 34 import static com.android.server.wifi.WifiMetricsTestUtil.buildLinkProbeFailureStaEvent; 35 import static com.android.server.wifi.WifiMetricsTestUtil.buildLinkProbeSuccessStaEvent; 36 import static com.android.server.wifi.nano.WifiMetricsProto.StaEvent.TYPE_LINK_PROBE; 37 38 import static org.junit.Assert.assertEquals; 39 import static org.junit.Assert.assertFalse; 40 import static org.junit.Assert.assertNotNull; 41 import static org.junit.Assert.assertNull; 42 import static org.junit.Assert.assertTrue; 43 import static org.junit.Assert.fail; 44 import static org.mockito.Mockito.any; 45 import static org.mockito.Mockito.anyBoolean; 46 import static org.mockito.Mockito.anyInt; 47 import static org.mockito.Mockito.doThrow; 48 import static org.mockito.Mockito.eq; 49 import static org.mockito.Mockito.mock; 50 import static org.mockito.Mockito.never; 51 import static org.mockito.Mockito.verify; 52 import static org.mockito.Mockito.when; 53 54 import android.content.Context; 55 import android.net.wifi.EAPConstants; 56 import android.net.wifi.IOnWifiUsabilityStatsListener; 57 import android.net.wifi.ScanResult; 58 import android.net.wifi.SupplicantState; 59 import android.net.wifi.WifiConfiguration; 60 import android.net.wifi.WifiEnterpriseConfig; 61 import android.net.wifi.WifiInfo; 62 import android.net.wifi.WifiManager; 63 import android.net.wifi.WifiSsid; 64 import android.net.wifi.hotspot2.PasspointConfiguration; 65 import android.net.wifi.hotspot2.ProvisioningCallback; 66 import android.net.wifi.hotspot2.pps.Credential; 67 import android.os.Handler; 68 import android.os.IBinder; 69 import android.os.RemoteException; 70 import android.os.test.TestLooper; 71 import android.provider.Settings; 72 import android.telephony.TelephonyManager; 73 import android.util.Base64; 74 import android.util.Pair; 75 import android.util.SparseIntArray; 76 77 import androidx.test.filters.MediumTest; 78 import androidx.test.filters.SmallTest; 79 80 import com.android.server.wifi.aware.WifiAwareMetrics; 81 import com.android.server.wifi.hotspot2.NetworkDetail; 82 import com.android.server.wifi.hotspot2.PasspointManager; 83 import com.android.server.wifi.hotspot2.PasspointMatch; 84 import com.android.server.wifi.hotspot2.PasspointProvider; 85 import com.android.server.wifi.nano.WifiMetricsProto; 86 import com.android.server.wifi.nano.WifiMetricsProto.ConnectToNetworkNotificationAndActionCount; 87 import com.android.server.wifi.nano.WifiMetricsProto.DeviceMobilityStatePnoScanStats; 88 import com.android.server.wifi.nano.WifiMetricsProto.HistogramBucketInt32; 89 import com.android.server.wifi.nano.WifiMetricsProto.Int32Count; 90 import com.android.server.wifi.nano.WifiMetricsProto.LinkProbeStats; 91 import com.android.server.wifi.nano.WifiMetricsProto.LinkProbeStats.ExperimentProbeCounts; 92 import com.android.server.wifi.nano.WifiMetricsProto.LinkProbeStats.LinkProbeFailureReasonCount; 93 import com.android.server.wifi.nano.WifiMetricsProto.NetworkSelectionExperimentDecisions; 94 import com.android.server.wifi.nano.WifiMetricsProto.PasspointProfileTypeCount; 95 import com.android.server.wifi.nano.WifiMetricsProto.PasspointProvisionStats; 96 import com.android.server.wifi.nano.WifiMetricsProto.PnoScanMetrics; 97 import com.android.server.wifi.nano.WifiMetricsProto.SoftApConnectedClientsEvent; 98 import com.android.server.wifi.nano.WifiMetricsProto.StaEvent; 99 import com.android.server.wifi.nano.WifiMetricsProto.WifiIsUnusableEvent; 100 import com.android.server.wifi.nano.WifiMetricsProto.WifiRadioUsage; 101 import com.android.server.wifi.nano.WifiMetricsProto.WifiUsabilityStats; 102 import com.android.server.wifi.nano.WifiMetricsProto.WifiUsabilityStatsEntry; 103 import com.android.server.wifi.nano.WifiMetricsProto.WpsMetrics; 104 import com.android.server.wifi.p2p.WifiP2pMetrics; 105 import com.android.server.wifi.rtt.RttMetrics; 106 import com.android.server.wifi.util.ExternalCallbackTracker; 107 108 import org.junit.Before; 109 import org.junit.Test; 110 import org.mockito.ArgumentCaptor; 111 import org.mockito.Mock; 112 import org.mockito.MockitoAnnotations; 113 114 import java.io.ByteArrayOutputStream; 115 import java.io.FileDescriptor; 116 import java.io.PrintWriter; 117 import java.io.StringWriter; 118 import java.util.ArrayList; 119 import java.util.Arrays; 120 import java.util.BitSet; 121 import java.util.HashMap; 122 import java.util.List; 123 import java.util.Map; 124 import java.util.Random; 125 import java.util.regex.Matcher; 126 import java.util.regex.Pattern; 127 128 /** 129 * Unit tests for {@link com.android.server.wifi.WifiMetrics}. 130 */ 131 @SmallTest 132 public class WifiMetricsTest { 133 134 WifiMetrics mWifiMetrics; 135 WifiMetricsProto.WifiLog mDecodedProto; 136 TestLooper mTestLooper; 137 Random mRandom = new Random(); 138 private static final int TEST_WIFI_USABILITY_STATS_LISTENER_IDENTIFIER = 2; 139 private static final int TEST_NETWORK_ID = 42; 140 @Mock Context mContext; 141 @Mock FrameworkFacade mFacade; 142 @Mock Clock mClock; 143 @Mock ScoringParams mScoringParams; 144 @Mock WifiConfigManager mWcm; 145 @Mock PasspointManager mPpm; 146 @Mock WifiNetworkSelector mWns; 147 @Mock WifiPowerMetrics mWifiPowerMetrics; 148 @Mock WifiDataStall mWifiDataStall; 149 @Mock IBinder mAppBinder; 150 @Mock IOnWifiUsabilityStatsListener mOnWifiUsabilityStatsListener; 151 @Mock ExternalCallbackTracker<IOnWifiUsabilityStatsListener> mListenerTracker; 152 @Mock WifiP2pMetrics mWifiP2pMetrics; 153 @Mock DppMetrics mDppMetrics; 154 @Mock CellularLinkLayerStatsCollector mCellularLinkLayerStatsCollector; 155 @Mock CellularLinkLayerStats mCellularLinkLayerStats; 156 157 @Before setUp()158 public void setUp() throws Exception { 159 MockitoAnnotations.initMocks(this); 160 mDecodedProto = null; 161 when(mClock.getElapsedSinceBootMillis()).thenReturn((long) 0); 162 when(mCellularLinkLayerStatsCollector.update()).thenReturn(mCellularLinkLayerStats); 163 mTestLooper = new TestLooper(); 164 mWifiMetrics = new WifiMetrics(mContext, mFacade, mClock, mTestLooper.getLooper(), 165 new WifiAwareMetrics(mClock), new RttMetrics(mClock), mWifiPowerMetrics, 166 mWifiP2pMetrics, mDppMetrics, mCellularLinkLayerStatsCollector); 167 mWifiMetrics.setWifiConfigManager(mWcm); 168 mWifiMetrics.setPasspointManager(mPpm); 169 mWifiMetrics.setScoringParams(mScoringParams); 170 mWifiMetrics.setWifiNetworkSelector(mWns); 171 mWifiMetrics.setWifiDataStall(mWifiDataStall); 172 } 173 174 /** 175 * Test that startConnectionEvent and endConnectionEvent can be called repeatedly and out of 176 * order. Only tests no exception occurs. Creates 3 ConnectionEvents. 177 */ 178 @Test startAndEndConnectionEventSucceeds()179 public void startAndEndConnectionEventSucceeds() throws Exception { 180 //Start and end Connection event 181 mWifiMetrics.startConnectionEvent(null, "RED", 182 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 183 mWifiMetrics.endConnectionEvent( 184 WifiMetrics.ConnectionEvent.FAILURE_AUTHENTICATION_FAILURE, 185 WifiMetricsProto.ConnectionEvent.HLF_DHCP, 186 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 187 //end Connection event without starting one 188 mWifiMetrics.endConnectionEvent( 189 WifiMetrics.ConnectionEvent.FAILURE_AUTHENTICATION_FAILURE, 190 WifiMetricsProto.ConnectionEvent.HLF_DHCP, 191 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 192 //start two ConnectionEvents in a row 193 mWifiMetrics.startConnectionEvent(null, "BLUE", 194 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 195 mWifiMetrics.startConnectionEvent(null, "GREEN", 196 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 197 } 198 199 private static final long TEST_RECORD_DURATION_SEC = 12 * 60 * 60; 200 private static final long TEST_RECORD_DURATION_MILLIS = TEST_RECORD_DURATION_SEC * 1000; 201 /** 202 * Simulate how dumpsys gets the proto from mWifiMetrics, filter the proto bytes out and 203 * deserialize them into mDecodedProto 204 */ dumpProtoAndDeserialize()205 public void dumpProtoAndDeserialize() throws Exception { 206 ByteArrayOutputStream stream = new ByteArrayOutputStream(); 207 PrintWriter writer = new PrintWriter(stream); 208 209 when(mClock.getElapsedSinceBootMillis()).thenReturn(TEST_RECORD_DURATION_MILLIS); 210 //Test proto dump, by passing in proto arg option 211 String[] args = {WifiMetrics.PROTO_DUMP_ARG}; 212 mWifiMetrics.dump(null, writer, args); 213 writer.flush(); 214 Pattern pattern = Pattern.compile( 215 "(?<=WifiMetrics:\\n)([\\s\\S]*)(?=EndWifiMetrics)"); 216 Matcher matcher = pattern.matcher(stream.toString()); 217 assertTrue("Proto Byte string found in WifiMetrics.dump():\n" + stream.toString(), 218 matcher.find()); 219 String protoByteString = matcher.group(1); 220 byte[] protoBytes = Base64.decode(protoByteString, Base64.DEFAULT); 221 mDecodedProto = WifiMetricsProto.WifiLog.parseFrom(protoBytes); 222 } 223 224 /** 225 * Gets the 'clean dump' proto bytes from mWifiMetrics & deserializes it into 226 * mDecodedProto 227 */ cleanDumpProtoAndDeserialize()228 public void cleanDumpProtoAndDeserialize() throws Exception { 229 ByteArrayOutputStream stream = new ByteArrayOutputStream(); 230 PrintWriter writer = new PrintWriter(stream); 231 232 when(mClock.getElapsedSinceBootMillis()).thenReturn(TEST_RECORD_DURATION_MILLIS); 233 //Test proto dump, by passing in proto arg option 234 String[] args = {WifiMetrics.PROTO_DUMP_ARG, WifiMetrics.CLEAN_DUMP_ARG}; 235 mWifiMetrics.dump(null, writer, args); 236 writer.flush(); 237 String protoByteString = stream.toString(); 238 byte[] protoBytes = Base64.decode(protoByteString, Base64.DEFAULT); 239 mDecodedProto = WifiMetricsProto.WifiLog.parseFrom(protoBytes); 240 } 241 242 /** Verifies that dump() includes the expected header */ 243 @Test stateDumpIncludesHeader()244 public void stateDumpIncludesHeader() throws Exception { 245 assertStringContains(getStateDump(), "WifiMetrics"); 246 } 247 248 /** Verifies that dump() includes correct alert count when there are no alerts. */ 249 @Test stateDumpAlertCountIsCorrectWithNoAlerts()250 public void stateDumpAlertCountIsCorrectWithNoAlerts() throws Exception { 251 assertStringContains(getStateDump(), "mWifiLogProto.alertReasonCounts=()"); 252 } 253 254 /** Verifies that dump() includes correct alert count when there is one alert. */ 255 @Test stateDumpAlertCountIsCorrectWithOneAlert()256 public void stateDumpAlertCountIsCorrectWithOneAlert() throws Exception { 257 mWifiMetrics.logFirmwareAlert(1); 258 assertStringContains(getStateDump(), "mWifiLogProto.alertReasonCounts=(1,1)"); 259 } 260 261 /** Verifies that dump() includes correct alert count when there are multiple alerts. */ 262 @Test stateDumpAlertCountIsCorrectWithMultipleAlerts()263 public void stateDumpAlertCountIsCorrectWithMultipleAlerts() throws Exception { 264 mWifiMetrics.logFirmwareAlert(1); 265 mWifiMetrics.logFirmwareAlert(1); 266 mWifiMetrics.logFirmwareAlert(16); 267 assertStringContains(getStateDump(), "mWifiLogProto.alertReasonCounts=(1,2),(16,1)"); 268 } 269 270 @Test testDumpProtoAndDeserialize()271 public void testDumpProtoAndDeserialize() throws Exception { 272 setAndIncrementMetrics(); 273 dumpProtoAndDeserialize(); 274 verify(mWifiP2pMetrics).consolidateProto(); 275 assertDeserializedMetricsCorrect(); 276 } 277 278 private static final int NUM_OPEN_NETWORKS = 2; 279 private static final int NUM_LEGACY_PERSONAL_NETWORKS = 3; 280 private static final int NUM_LEGACY_ENTERPRISE_NETWORKS = 5; 281 private static final int NUM_ENHANCED_OPEN_NETWORKS = 1; 282 private static final int NUM_WPA3_PERSONAL_NETWORKS = 4; 283 private static final int NUM_WPA3_ENTERPRISE_NETWORKS = 6; 284 private static final int NUM_SAVED_NETWORKS = NUM_OPEN_NETWORKS + NUM_LEGACY_PERSONAL_NETWORKS 285 + NUM_LEGACY_ENTERPRISE_NETWORKS + NUM_ENHANCED_OPEN_NETWORKS 286 + NUM_WPA3_PERSONAL_NETWORKS + NUM_WPA3_ENTERPRISE_NETWORKS; 287 private static final int NUM_HIDDEN_NETWORKS = NUM_OPEN_NETWORKS; 288 private static final int NUM_PASSPOINT_NETWORKS = NUM_LEGACY_ENTERPRISE_NETWORKS; 289 private static final int NUM_NETWORKS_ADDED_BY_USER = 1; 290 private static final int NUM_NETWORKS_ADDED_BY_APPS = NUM_SAVED_NETWORKS 291 - NUM_NETWORKS_ADDED_BY_USER; 292 private static final boolean TEST_VAL_IS_LOCATION_ENABLED = true; 293 private static final boolean IS_SCANNING_ALWAYS_ENABLED = true; 294 private static final int NUM_EMPTY_SCAN_RESULTS = 19; 295 private static final int NUM_NON_EMPTY_SCAN_RESULTS = 23; 296 private static final int NUM_SCAN_UNKNOWN = 1; 297 private static final int NUM_SCAN_SUCCESS = 2; 298 private static final int NUM_SCAN_FAILURE_INTERRUPTED = 3; 299 private static final int NUM_SCAN_FAILURE_INVALID_CONFIGURATION = 5; 300 private static final int NUM_WIFI_UNKNOWN_SCREEN_OFF = 3; 301 private static final int NUM_WIFI_UNKNOWN_SCREEN_ON = 5; 302 private static final int NUM_WIFI_ASSOCIATED_SCREEN_OFF = 7; 303 private static final int NUM_WIFI_ASSOCIATED_SCREEN_ON = 11; 304 private static final int NUM_CONNECTIVITY_WATCHDOG_PNO_GOOD = 11; 305 private static final int NUM_CONNECTIVITY_WATCHDOG_PNO_BAD = 12; 306 private static final int NUM_CONNECTIVITY_WATCHDOG_BACKGROUND_GOOD = 13; 307 private static final int NUM_CONNECTIVITY_WATCHDOG_BACKGROUND_BAD = 14; 308 private static final int NUM_LAST_RESORT_WATCHDOG_TRIGGERS = 1; 309 private static final int NUM_LAST_RESORT_WATCHDOG_BAD_ASSOCIATION_NETWORKS_TOTAL = 2; 310 private static final int NUM_LAST_RESORT_WATCHDOG_BAD_AUTHENTICATION_NETWORKS_TOTAL = 3; 311 private static final int NUM_LAST_RESORT_WATCHDOG_BAD_DHCP_NETWORKS_TOTAL = 4; 312 private static final int NUM_LAST_RESORT_WATCHDOG_BAD_OTHER_NETWORKS_TOTAL = 5; 313 private static final int NUM_LAST_RESORT_WATCHDOG_AVAILABLE_NETWORKS_TOTAL = 6; 314 private static final int NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_ASSOCIATION = 7; 315 private static final int NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_AUTHENTICATION = 8; 316 private static final int NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_DHCP = 9; 317 private static final int NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_OTHER = 10; 318 private static final int NUM_LAST_RESORT_WATCHDOG_SUCCESSES = 5; 319 private static final int WATCHDOG_TOTAL_CONNECTION_FAILURE_COUNT_AFTER_TRIGGER = 6; 320 private static final int RSSI_POLL_FREQUENCY = 5150; 321 private static final int NUM_RSSI_LEVELS_TO_INCREMENT = 20; 322 private static final int NUM_OPEN_NETWORK_SCAN_RESULTS = 1; 323 private static final int NUM_LEGACY_PERSONAL_NETWORK_SCAN_RESULTS = 4; 324 private static final int NUM_LEGACY_ENTERPRISE_NETWORK_SCAN_RESULTS = 3; 325 private static final int NUM_ENHANCED_OPEN_NETWORK_SCAN_RESULTS = 1; 326 private static final int NUM_WPA3_PERSONAL_NETWORK_SCAN_RESULTS = 2; 327 private static final int NUM_WPA3_ENTERPRISE_NETWORK_SCAN_RESULTS = 1; 328 private static final int NUM_HIDDEN_NETWORK_SCAN_RESULTS = 1; 329 private static final int NUM_HOTSPOT2_R1_NETWORK_SCAN_RESULTS = 1; 330 private static final int NUM_HOTSPOT2_R2_NETWORK_SCAN_RESULTS = 2; 331 private static final int NUM_SCANS = 5; 332 private static final int NUM_CONNECTIVITY_ONESHOT_SCAN_EVENT = 4; 333 private static final int NUM_EXTERNAL_APP_ONESHOT_SCAN_REQUESTS = 15; 334 private static final int NUM_EXTERNAL_FOREGROUND_APP_ONESHOT_SCAN_REQUESTS_THROTTLED = 10; 335 private static final int NUM_EXTERNAL_BACKGROUND_APP_ONESHOT_SCAN_REQUESTS_THROTTLED = 16; 336 // Look at buildMockScanDetailList, this number needs to match the mocked results 337 private static final int NUM_TOTAL_SCAN_RESULTS = NUM_OPEN_NETWORK_SCAN_RESULTS 338 + NUM_LEGACY_PERSONAL_NETWORK_SCAN_RESULTS + NUM_LEGACY_ENTERPRISE_NETWORK_SCAN_RESULTS 339 + NUM_ENHANCED_OPEN_NETWORK_SCAN_RESULTS + NUM_WPA3_PERSONAL_NETWORK_SCAN_RESULTS 340 + NUM_WPA3_ENTERPRISE_NETWORK_SCAN_RESULTS; 341 private static final int MIN_RSSI_LEVEL = -127; 342 private static final int MAX_RSSI_LEVEL = 0; 343 private static final int WIFI_SCORE_RANGE_MIN = 0; 344 private static final int NUM_WIFI_SCORES_TO_INCREMENT = 20; 345 private static final int WIFI_SCORE_RANGE_MAX = 60; 346 private static final int NUM_OUT_OF_BOUND_ENTRIES = 10; 347 private static final int MAX_NUM_SOFTAP_RETURN_CODES = 3; 348 private static final int NUM_SOFTAP_START_SUCCESS = 3; 349 private static final int NUM_SOFTAP_FAILED_GENERAL_ERROR = 2; 350 private static final int NUM_SOFTAP_FAILED_NO_CHANNEL = 1; 351 private static final int NUM_HAL_CRASHES = 11; 352 private static final int NUM_WIFICOND_CRASHES = 12; 353 private static final int NUM_SUPPLICANT_CRASHES = 23; 354 private static final int NUM_HOSTAPD_CRASHES = 7; 355 private static final int NUM_WIFI_ON_FAILURE_DUE_TO_HAL = 13; 356 private static final int NUM_WIFI_ON_FAILURE_DUE_TO_WIFICOND = 14; 357 private static final int NUM_WIFI_ON_FAILURE_DUE_TO_SUPPLICANT = 20; 358 private static final int NUM_SOFTAP_ON_FAILURE_DUE_TO_HAL = 23; 359 private static final int NUM_SOFTAP_ON_FAILURE_DUE_TO_WIFICOND = 19; 360 private static final int NUM_SOFTAP_ON_FAILURE_DUE_TO_HOSTAPD = 31; 361 private static final int NUM_SOFTAP_INTERFACE_DOWN = 65; 362 private static final int NUM_CLIENT_INTERFACE_DOWN = 12; 363 private static final int NUM_PASSPOINT_PROVIDERS = 7; 364 private static final int NUM_PASSPOINT_PROVIDER_INSTALLATION = 5; 365 private static final int NUM_PASSPOINT_PROVIDER_INSTALL_SUCCESS = 4; 366 private static final int NUM_PASSPOINT_PROVIDER_UNINSTALLATION = 3; 367 private static final int NUM_PASSPOINT_PROVIDER_UNINSTALL_SUCCESS = 2; 368 private static final int NUM_PASSPOINT_PROVIDERS_SUCCESSFULLY_CONNECTED = 1; 369 private static final int NUM_EAP_SIM_TYPE = 1; 370 private static final int NUM_EAP_TTLS_TYPE = 2; 371 private static final int NUM_EAP_TLS_TYPE = 3; 372 private static final int NUM_EAP_AKA_TYPE = 4; 373 private static final int NUM_EAP_AKA_PRIME_TYPE = 5; 374 private static final SparseIntArray SAVED_PASSPOINT_PROVIDERS_TYPE = new SparseIntArray(); 375 static { SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_SIM, NUM_EAP_SIM_TYPE)376 SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_SIM, NUM_EAP_SIM_TYPE); SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_TTLS, NUM_EAP_TTLS_TYPE)377 SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_TTLS, NUM_EAP_TTLS_TYPE); SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_TLS, NUM_EAP_TLS_TYPE)378 SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_TLS, NUM_EAP_TLS_TYPE); SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_AKA, NUM_EAP_AKA_TYPE)379 SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_AKA, NUM_EAP_AKA_TYPE); SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_AKA_PRIME, NUM_EAP_AKA_PRIME_TYPE)380 SAVED_PASSPOINT_PROVIDERS_TYPE.put(EAPConstants.EAP_AKA_PRIME, NUM_EAP_AKA_PRIME_TYPE); 381 } 382 383 private static final int NUM_PARTIAL_SCAN_RESULTS = 73; 384 private static final int NUM_PNO_SCAN_ATTEMPTS = 20; 385 private static final int NUM_PNO_SCAN_FAILED = 5; 386 private static final int NUM_PNO_FOUND_NETWORK_EVENTS = 10; 387 private static final int NUM_WPS_ATTEMPTS = 17; 388 private static final int NUM_WPS_SUCCESS = 21; 389 private static final int NUM_WPS_START_FAILURE = 7; 390 private static final int NUM_WPS_OVERLAP_FAILURE = 3; 391 private static final int NUM_WPS_TIMEOUT_FAILURE = 8; 392 private static final int NUM_WPS_OTHER_CONNECTION_FAILURE = 16; 393 private static final int NUM_WPS_SUPPLICANT_FAILURE = 12; 394 private static final int NUM_WPS_CANCELLATION = 11; 395 private static final int NUM_RADIO_MODE_CHANGE_TO_MCC = 4; 396 private static final int NUM_RADIO_MODE_CHANGE_TO_SCC = 13; 397 private static final int NUM_RADIO_MODE_CHANGE_TO_SBS = 19; 398 private static final int NUM_RADIO_MODE_CHANGE_TO_DBS = 34; 399 private static final int NUM_SOFTAP_USER_BAND_PREFERENCE_UNSATISFIED = 14; 400 private static final long NUM_WATCHDOG_SUCCESS_DURATION_MS = 65; 401 private static final long WIFI_POWER_METRICS_LOGGING_DURATION = 280; 402 private static final long WIFI_POWER_METRICS_SCAN_TIME = 33; 403 private static final boolean WIFI_IS_UNUSABLE_EVENT_LOGGING_SETTING = true; 404 private static final boolean LINK_SPEED_COUNTS_LOGGING_SETTING = true; 405 private static final int DATA_STALL_MIN_TX_BAD_SETTING = 5; 406 private static final int DATA_STALL_MIN_TX_SUCCESS_WITHOUT_RX_SETTING = 75; 407 private static final int NUM_SAR_SENSOR_LISTENER_REGISTRATION_FAILURES = 5; 408 private static final int NUM_ONESHOT_SCAN_REQUESTS_WITH_DFS_CHANNELS = 4; 409 private static final int NUM_ADD_OR_UPDATE_NETWORK_CALLS = 5; 410 private static final int NUM_ENABLE_NETWORK_CALLS = 6; 411 412 /** Number of notifications per "Connect to Network" notification type. */ 413 private static final int[] NUM_CONNECT_TO_NETWORK_NOTIFICATIONS = {0, 10, 20, 30, 40}; 414 /** Number of notifications per "Connect to Network notification type and action type. */ 415 private static final int[][] NUM_CONNECT_TO_NETWORK_NOTIFICATION_ACTIONS = { 416 {0, 1, 2, 3, 4}, 417 {10, 11, 12, 13, 14}, 418 {20, 21, 22, 23, 24}, 419 {30, 31, 32, 33, 34}, 420 {40, 41, 42, 43, 44}}; 421 private static final int SIZE_OPEN_NETWORK_RECOMMENDER_BLOCKLIST = 10; 422 private static final boolean IS_WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON = true; 423 private static final int NUM_OPEN_NETWORK_CONNECT_MESSAGE_FAILED_TO_SEND = 5; 424 private static final int NUM_OPEN_NETWORK_RECOMMENDATION_UPDATES = 8; 425 private static final String OPEN_NET_NOTIFIER_TAG = OpenNetworkNotifier.TAG; 426 427 private static final int NUM_SOFT_AP_EVENT_ENTRIES = 3; 428 private static final int NUM_SOFT_AP_ASSOCIATED_STATIONS = 3; 429 private static final int SOFT_AP_CHANNEL_FREQUENCY = 2437; 430 private static final int SOFT_AP_CHANNEL_BANDWIDTH = SoftApConnectedClientsEvent.BANDWIDTH_20; 431 private static final boolean IS_MAC_RANDOMIZATION_ON = true; 432 private static final int NUM_LINK_SPEED_LEVELS_TO_INCREMENT = 30; 433 private static final int TEST_RSSI_LEVEL = -80; 434 buildMockScanDetail(boolean hidden, NetworkDetail.HSRelease hSRelease, String capabilities)435 private ScanDetail buildMockScanDetail(boolean hidden, NetworkDetail.HSRelease hSRelease, 436 String capabilities) { 437 ScanDetail mockScanDetail = mock(ScanDetail.class); 438 NetworkDetail mockNetworkDetail = mock(NetworkDetail.class); 439 ScanResult mockScanResult = mock(ScanResult.class); 440 when(mockScanDetail.getNetworkDetail()).thenReturn(mockNetworkDetail); 441 when(mockScanDetail.getScanResult()).thenReturn(mockScanResult); 442 when(mockNetworkDetail.isHiddenBeaconFrame()).thenReturn(hidden); 443 when(mockNetworkDetail.getHSRelease()).thenReturn(hSRelease); 444 mockScanResult.capabilities = capabilities; 445 return mockScanDetail; 446 } 447 buildMockScanDetail(String ssid, String bssid, boolean isOpen, boolean isSaved, boolean isProvider, boolean isWeakRssi)448 private ScanDetail buildMockScanDetail(String ssid, String bssid, boolean isOpen, 449 boolean isSaved, boolean isProvider, boolean isWeakRssi) { 450 ScanDetail mockScanDetail = mock(ScanDetail.class); 451 NetworkDetail mockNetworkDetail = mock(NetworkDetail.class); 452 ScanResult scanResult = new ScanResult(); 453 scanResult.SSID = ssid; 454 scanResult.BSSID = bssid; 455 when(mockScanDetail.getNetworkDetail()).thenReturn(mockNetworkDetail); 456 when(mockScanDetail.getScanResult()).thenReturn(scanResult); 457 when(mWns.isSignalTooWeak(eq(scanResult))).thenReturn(isWeakRssi); 458 scanResult.capabilities = isOpen ? "" : "PSK"; 459 if (isSaved) { 460 when(mWcm.getConfiguredNetworkForScanDetail(eq(mockScanDetail))) 461 .thenReturn(mock(WifiConfiguration.class)); 462 } 463 if (isProvider) { 464 PasspointProvider provider = mock(PasspointProvider.class); 465 Pair<PasspointProvider, PasspointMatch> providerMatch = Pair.create(provider, null); 466 when(mockNetworkDetail.isInterworking()).thenReturn(true); 467 when(mPpm.matchProvider(eq(scanResult))).thenReturn(providerMatch); 468 } 469 return mockScanDetail; 470 } 471 buildMockScanDetailPasspoint(String ssid, String bssid, long hessid, int anqpDomainId, NetworkDetail.HSRelease hsRelease, boolean weakSignal)472 private ScanDetail buildMockScanDetailPasspoint(String ssid, String bssid, long hessid, 473 int anqpDomainId, NetworkDetail.HSRelease hsRelease, boolean weakSignal) { 474 ScanDetail mockScanDetail = mock(ScanDetail.class); 475 NetworkDetail mockNetworkDetail = mock(NetworkDetail.class); 476 ScanResult scanResult = new ScanResult(); 477 scanResult.SSID = ssid; 478 scanResult.BSSID = bssid; 479 scanResult.hessid = hessid; 480 scanResult.capabilities = "PSK"; 481 when(mockScanDetail.getNetworkDetail()).thenReturn(mockNetworkDetail); 482 when(mockScanDetail.getScanResult()).thenReturn(scanResult); 483 when(mockNetworkDetail.getHSRelease()).thenReturn(hsRelease); 484 when(mockNetworkDetail.getAnqpDomainID()).thenReturn(anqpDomainId); 485 when(mockNetworkDetail.isInterworking()).thenReturn(true); 486 when(mWns.isSignalTooWeak(eq(scanResult))).thenReturn(weakSignal); 487 return mockScanDetail; 488 } 489 buildMockScanDetailList()490 private List<ScanDetail> buildMockScanDetailList() { 491 List<ScanDetail> mockScanDetails = new ArrayList<ScanDetail>(); 492 mockScanDetails.add(buildMockScanDetail(true, null, "[ESS]")); 493 mockScanDetails.add(buildMockScanDetail(false, null, "[WPA2-PSK-CCMP][ESS]")); 494 mockScanDetails.add(buildMockScanDetail(false, null, "[WPA-PSK-CCMP]")); 495 mockScanDetails.add(buildMockScanDetail(false, null, "[WPA2-SAE-CCMP]")); 496 mockScanDetails.add(buildMockScanDetail(false, null, "[WPA-PSK-CCMP]")); 497 mockScanDetails.add(buildMockScanDetail(false, null, "[WEP]")); 498 mockScanDetails.add(buildMockScanDetail(false, null, "[WPA2-SAE-CCMP]")); 499 mockScanDetails.add(buildMockScanDetail(false, null, "[WPA2-OWE-CCMP]")); 500 mockScanDetails.add(buildMockScanDetail(false, null, "[WPA2-EAP-SUITE-B-192]")); 501 mockScanDetails.add(buildMockScanDetail(false, NetworkDetail.HSRelease.R2, 502 "[WPA-EAP-CCMP]")); 503 mockScanDetails.add(buildMockScanDetail(false, NetworkDetail.HSRelease.R2, 504 "[WPA2-EAP+FT/EAP-CCMP]")); 505 mockScanDetails.add(buildMockScanDetail(false, NetworkDetail.HSRelease.R1, 506 "[WPA-EAP-CCMP]")); 507 return mockScanDetails; 508 } 509 buildSavedNetworkList()510 private List<WifiConfiguration> buildSavedNetworkList() { 511 List<WifiConfiguration> testSavedNetworks = new ArrayList<WifiConfiguration>(); 512 for (int i = 0; i < NUM_OPEN_NETWORKS; i++) { 513 testSavedNetworks.add(WifiConfigurationTestUtil.createOpenHiddenNetwork()); 514 } 515 for (int i = 0; i < NUM_LEGACY_PERSONAL_NETWORKS; i++) { 516 testSavedNetworks.add(WifiConfigurationTestUtil.createPskNetwork()); 517 } 518 for (int i = 0; i < NUM_LEGACY_ENTERPRISE_NETWORKS; i++) { 519 // Passpoint networks are counted in both Passpoint and Enterprise counters 520 testSavedNetworks.add(WifiConfigurationTestUtil.createPasspointNetwork()); 521 } 522 for (int i = 0; i < NUM_ENHANCED_OPEN_NETWORKS; i++) { 523 testSavedNetworks.add(WifiConfigurationTestUtil.createOweNetwork()); 524 } 525 for (int i = 0; i < NUM_WPA3_PERSONAL_NETWORKS; i++) { 526 testSavedNetworks.add(WifiConfigurationTestUtil.createSaeNetwork()); 527 } 528 for (int i = 0; i < NUM_WPA3_ENTERPRISE_NETWORKS; i++) { 529 testSavedNetworks.add(WifiConfigurationTestUtil.createEapSuiteBNetwork()); 530 } 531 testSavedNetworks.get(0).selfAdded = true; 532 testSavedNetworks.get(0).macRandomizationSetting = WifiConfiguration.RANDOMIZATION_NONE; 533 return testSavedNetworks; 534 } 535 createMockProvider(int eapType, boolean validateForR2)536 private PasspointProvider createMockProvider(int eapType, boolean validateForR2) { 537 PasspointProvider provider = mock(PasspointProvider.class); 538 PasspointConfiguration config = mock(PasspointConfiguration.class); 539 Credential credential = new Credential(); 540 541 switch (eapType) { 542 case EAPConstants.EAP_TLS: 543 credential.setCertCredential(new Credential.CertificateCredential()); 544 break; 545 case EAPConstants.EAP_TTLS: 546 credential.setUserCredential(new Credential.UserCredential()); 547 break; 548 case EAPConstants.EAP_AKA: 549 case EAPConstants.EAP_AKA_PRIME: 550 case EAPConstants.EAP_SIM: 551 Credential.SimCredential simCredential = new Credential.SimCredential(); 552 simCredential.setEapType(eapType); 553 credential.setSimCredential(simCredential); 554 break; 555 } 556 when(provider.getConfig()).thenReturn(config); 557 when(config.getCredential()).thenReturn(credential); 558 when(config.validateForR2()).thenReturn(validateForR2); 559 return provider; 560 } 561 562 /** 563 * Set simple metrics, increment others 564 */ setAndIncrementMetrics()565 public void setAndIncrementMetrics() throws Exception { 566 Map<String, PasspointProvider> providers = new HashMap<>(); 567 mWifiMetrics.updateSavedNetworks(buildSavedNetworkList()); 568 mWifiMetrics.updateSavedPasspointProfiles(NUM_PASSPOINT_PROVIDERS, 569 NUM_PASSPOINT_PROVIDERS_SUCCESSFULLY_CONNECTED); 570 for (int i = 0; i < SAVED_PASSPOINT_PROVIDERS_TYPE.size(); i++) { 571 int eapType = SAVED_PASSPOINT_PROVIDERS_TYPE.keyAt(i); 572 int count = SAVED_PASSPOINT_PROVIDERS_TYPE.valueAt(i); 573 for (int j = 0; j < count; j++) { 574 providers.put(Integer.toString(eapType) + j, createMockProvider(eapType, false)); 575 } 576 for (int j = count; j < count * 2; j++) { 577 providers.put(Integer.toString(eapType) + j, createMockProvider(eapType, true)); 578 } 579 } 580 mWifiMetrics.updateSavedPasspointProfilesInfo(providers); 581 582 mWifiMetrics.setIsLocationEnabled(TEST_VAL_IS_LOCATION_ENABLED); 583 mWifiMetrics.setIsScanningAlwaysEnabled(IS_SCANNING_ALWAYS_ENABLED); 584 585 for (int i = 0; i < NUM_EMPTY_SCAN_RESULTS; i++) { 586 mWifiMetrics.incrementEmptyScanResultCount(); 587 } 588 for (int i = 0; i < NUM_NON_EMPTY_SCAN_RESULTS; i++) { 589 mWifiMetrics.incrementNonEmptyScanResultCount(); 590 } 591 mWifiMetrics.incrementScanReturnEntry(WifiMetricsProto.WifiLog.SCAN_UNKNOWN, 592 NUM_SCAN_UNKNOWN); 593 mWifiMetrics.incrementScanReturnEntry(WifiMetricsProto.WifiLog.SCAN_SUCCESS, 594 NUM_SCAN_SUCCESS); 595 mWifiMetrics.incrementScanReturnEntry( 596 WifiMetricsProto.WifiLog.SCAN_FAILURE_INTERRUPTED, 597 NUM_SCAN_FAILURE_INTERRUPTED); 598 mWifiMetrics.incrementScanReturnEntry( 599 WifiMetricsProto.WifiLog.SCAN_FAILURE_INVALID_CONFIGURATION, 600 NUM_SCAN_FAILURE_INVALID_CONFIGURATION); 601 for (int i = 0; i < NUM_WIFI_UNKNOWN_SCREEN_OFF; i++) { 602 mWifiMetrics.incrementWifiSystemScanStateCount(WifiMetricsProto.WifiLog.WIFI_UNKNOWN, 603 false); 604 } 605 for (int i = 0; i < NUM_WIFI_UNKNOWN_SCREEN_ON; i++) { 606 mWifiMetrics.incrementWifiSystemScanStateCount(WifiMetricsProto.WifiLog.WIFI_UNKNOWN, 607 true); 608 } 609 for (int i = 0; i < NUM_WIFI_ASSOCIATED_SCREEN_OFF; i++) { 610 mWifiMetrics.incrementWifiSystemScanStateCount(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED, 611 false); 612 } 613 for (int i = 0; i < NUM_WIFI_ASSOCIATED_SCREEN_ON; i++) { 614 mWifiMetrics.incrementWifiSystemScanStateCount(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED, 615 true); 616 } 617 for (int i = 0; i < NUM_CONNECTIVITY_WATCHDOG_PNO_GOOD; i++) { 618 mWifiMetrics.incrementNumConnectivityWatchdogPnoGood(); 619 } 620 for (int i = 0; i < NUM_CONNECTIVITY_WATCHDOG_PNO_BAD; i++) { 621 mWifiMetrics.incrementNumConnectivityWatchdogPnoBad(); 622 } 623 for (int i = 0; i < NUM_CONNECTIVITY_WATCHDOG_BACKGROUND_GOOD; i++) { 624 mWifiMetrics.incrementNumConnectivityWatchdogBackgroundGood(); 625 } 626 for (int i = 0; i < NUM_CONNECTIVITY_WATCHDOG_BACKGROUND_BAD; i++) { 627 mWifiMetrics.incrementNumConnectivityWatchdogBackgroundBad(); 628 } 629 for (int i = 0; i < NUM_LAST_RESORT_WATCHDOG_TRIGGERS; i++) { 630 mWifiMetrics.incrementNumLastResortWatchdogTriggers(); 631 } 632 mWifiMetrics.addCountToNumLastResortWatchdogBadAssociationNetworksTotal( 633 NUM_LAST_RESORT_WATCHDOG_BAD_ASSOCIATION_NETWORKS_TOTAL); 634 mWifiMetrics.addCountToNumLastResortWatchdogBadAuthenticationNetworksTotal( 635 NUM_LAST_RESORT_WATCHDOG_BAD_AUTHENTICATION_NETWORKS_TOTAL); 636 mWifiMetrics.addCountToNumLastResortWatchdogBadDhcpNetworksTotal( 637 NUM_LAST_RESORT_WATCHDOG_BAD_DHCP_NETWORKS_TOTAL); 638 mWifiMetrics.addCountToNumLastResortWatchdogBadOtherNetworksTotal( 639 NUM_LAST_RESORT_WATCHDOG_BAD_OTHER_NETWORKS_TOTAL); 640 mWifiMetrics.addCountToNumLastResortWatchdogAvailableNetworksTotal( 641 NUM_LAST_RESORT_WATCHDOG_AVAILABLE_NETWORKS_TOTAL); 642 for (int i = 0; i < NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_ASSOCIATION; i++) { 643 mWifiMetrics.incrementNumLastResortWatchdogTriggersWithBadAssociation(); 644 } 645 for (int i = 0; i < NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_AUTHENTICATION; i++) { 646 mWifiMetrics.incrementNumLastResortWatchdogTriggersWithBadAuthentication(); 647 } 648 for (int i = 0; i < NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_DHCP; i++) { 649 mWifiMetrics.incrementNumLastResortWatchdogTriggersWithBadDhcp(); 650 } 651 for (int i = 0; i < NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_OTHER; i++) { 652 mWifiMetrics.incrementNumLastResortWatchdogTriggersWithBadOther(); 653 } 654 for (int i = 0; i < NUM_LAST_RESORT_WATCHDOG_SUCCESSES; i++) { 655 mWifiMetrics.incrementNumLastResortWatchdogSuccesses(); 656 } 657 for (int i = 0; i < WATCHDOG_TOTAL_CONNECTION_FAILURE_COUNT_AFTER_TRIGGER; i++) { 658 mWifiMetrics.incrementWatchdogTotalConnectionFailureCountAfterTrigger(); 659 } 660 for (int i = 0; i < NUM_RSSI_LEVELS_TO_INCREMENT; i++) { 661 for (int j = 0; j <= i; j++) { 662 mWifiMetrics.incrementRssiPollRssiCount(RSSI_POLL_FREQUENCY, MIN_RSSI_LEVEL + i); 663 } 664 } 665 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 666 mWifiMetrics.incrementRssiPollRssiCount(RSSI_POLL_FREQUENCY, MIN_RSSI_LEVEL - i); 667 } 668 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 669 mWifiMetrics.incrementRssiPollRssiCount(RSSI_POLL_FREQUENCY, MAX_RSSI_LEVEL + i); 670 } 671 672 // Test alert-reason clamping. 673 mWifiMetrics.logFirmwareAlert(WifiLoggerHal.WIFI_ALERT_REASON_MIN - 1); 674 mWifiMetrics.logFirmwareAlert(WifiLoggerHal.WIFI_ALERT_REASON_MAX + 1); 675 // Simple cases for alert reason. 676 mWifiMetrics.logFirmwareAlert(1); 677 mWifiMetrics.logFirmwareAlert(1); 678 mWifiMetrics.logFirmwareAlert(1); 679 mWifiMetrics.logFirmwareAlert(2); 680 List<ScanDetail> mockScanDetails = buildMockScanDetailList(); 681 for (int i = 0; i < NUM_SCANS; i++) { 682 mWifiMetrics.countScanResults(mockScanDetails); 683 } 684 // increment connectivity scan metrics 685 for (int i = 0; i < NUM_CONNECTIVITY_ONESHOT_SCAN_EVENT; i++) { 686 mWifiMetrics.incrementConnectivityOneshotScanCount(); 687 } 688 for (int i = 0; i < NUM_EXTERNAL_APP_ONESHOT_SCAN_REQUESTS; i++) { 689 mWifiMetrics.incrementExternalAppOneshotScanRequestsCount(); 690 } 691 for (int i = 0; i < NUM_EXTERNAL_FOREGROUND_APP_ONESHOT_SCAN_REQUESTS_THROTTLED; i++) { 692 mWifiMetrics.incrementExternalForegroundAppOneshotScanRequestsThrottledCount(); 693 } 694 for (int i = 0; i < NUM_EXTERNAL_BACKGROUND_APP_ONESHOT_SCAN_REQUESTS_THROTTLED; i++) { 695 mWifiMetrics.incrementExternalBackgroundAppOneshotScanRequestsThrottledCount(); 696 } 697 for (int score = 0; score < NUM_WIFI_SCORES_TO_INCREMENT; score++) { 698 for (int offset = 0; offset <= score; offset++) { 699 mWifiMetrics.incrementWifiScoreCount(WIFI_SCORE_RANGE_MIN + score); 700 } 701 } 702 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 703 mWifiMetrics.incrementWifiScoreCount(WIFI_SCORE_RANGE_MIN - i); 704 } 705 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 706 mWifiMetrics.incrementWifiScoreCount(WIFI_SCORE_RANGE_MAX + i); 707 } 708 for (int score = 0; score < NUM_WIFI_SCORES_TO_INCREMENT; score++) { 709 for (int offset = 0; offset <= score; offset++) { 710 mWifiMetrics.incrementWifiUsabilityScoreCount(1, WIFI_SCORE_RANGE_MIN + score, 15); 711 } 712 } 713 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 714 mWifiMetrics.incrementWifiUsabilityScoreCount(1, WIFI_SCORE_RANGE_MIN - i, 15); 715 } 716 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 717 mWifiMetrics.incrementWifiUsabilityScoreCount(1, WIFI_SCORE_RANGE_MAX + i, 15); 718 } 719 720 // increment soft ap start return codes 721 for (int i = 0; i < NUM_SOFTAP_START_SUCCESS; i++) { 722 mWifiMetrics.incrementSoftApStartResult(true, 0); 723 } 724 for (int i = 0; i < NUM_SOFTAP_FAILED_GENERAL_ERROR; i++) { 725 mWifiMetrics.incrementSoftApStartResult(false, WifiManager.SAP_START_FAILURE_GENERAL); 726 } 727 for (int i = 0; i < NUM_SOFTAP_FAILED_NO_CHANNEL; i++) { 728 mWifiMetrics.incrementSoftApStartResult(false, 729 WifiManager.SAP_START_FAILURE_NO_CHANNEL); 730 } 731 for (int i = 0; i < NUM_HAL_CRASHES; i++) { 732 mWifiMetrics.incrementNumHalCrashes(); 733 } 734 for (int i = 0; i < NUM_WIFICOND_CRASHES; i++) { 735 mWifiMetrics.incrementNumWificondCrashes(); 736 } 737 for (int i = 0; i < NUM_SUPPLICANT_CRASHES; i++) { 738 mWifiMetrics.incrementNumSupplicantCrashes(); 739 } 740 for (int i = 0; i < NUM_HOSTAPD_CRASHES; i++) { 741 mWifiMetrics.incrementNumHostapdCrashes(); 742 } 743 for (int i = 0; i < NUM_WIFI_ON_FAILURE_DUE_TO_HAL; i++) { 744 mWifiMetrics.incrementNumSetupClientInterfaceFailureDueToHal(); 745 } 746 for (int i = 0; i < NUM_WIFI_ON_FAILURE_DUE_TO_WIFICOND; i++) { 747 mWifiMetrics.incrementNumSetupClientInterfaceFailureDueToWificond(); 748 } 749 for (int i = 0; i < NUM_WIFI_ON_FAILURE_DUE_TO_SUPPLICANT; i++) { 750 mWifiMetrics.incrementNumSetupClientInterfaceFailureDueToSupplicant(); 751 } 752 for (int i = 0; i < NUM_SOFTAP_ON_FAILURE_DUE_TO_HAL; i++) { 753 mWifiMetrics.incrementNumSetupSoftApInterfaceFailureDueToHal(); 754 } 755 for (int i = 0; i < NUM_SOFTAP_ON_FAILURE_DUE_TO_WIFICOND; i++) { 756 mWifiMetrics.incrementNumSetupSoftApInterfaceFailureDueToWificond(); 757 } 758 for (int i = 0; i < NUM_SOFTAP_ON_FAILURE_DUE_TO_HOSTAPD; i++) { 759 mWifiMetrics.incrementNumSetupSoftApInterfaceFailureDueToHostapd(); 760 } 761 for (int i = 0; i < NUM_SOFTAP_INTERFACE_DOWN; i++) { 762 mWifiMetrics.incrementNumSoftApInterfaceDown(); 763 } 764 for (int i = 0; i < NUM_CLIENT_INTERFACE_DOWN; i++) { 765 mWifiMetrics.incrementNumClientInterfaceDown(); 766 } 767 for (int i = 0; i < NUM_PASSPOINT_PROVIDER_INSTALLATION; i++) { 768 mWifiMetrics.incrementNumPasspointProviderInstallation(); 769 } 770 for (int i = 0; i < NUM_PASSPOINT_PROVIDER_INSTALL_SUCCESS; i++) { 771 mWifiMetrics.incrementNumPasspointProviderInstallSuccess(); 772 } 773 for (int i = 0; i < NUM_PASSPOINT_PROVIDER_UNINSTALLATION; i++) { 774 mWifiMetrics.incrementNumPasspointProviderUninstallation(); 775 } 776 for (int i = 0; i < NUM_PASSPOINT_PROVIDER_UNINSTALL_SUCCESS; i++) { 777 mWifiMetrics.incrementNumPasspointProviderUninstallSuccess(); 778 } 779 for (int i = 0; i < NUM_RADIO_MODE_CHANGE_TO_MCC; i++) { 780 mWifiMetrics.incrementNumRadioModeChangeToMcc(); 781 } 782 for (int i = 0; i < NUM_RADIO_MODE_CHANGE_TO_SCC; i++) { 783 mWifiMetrics.incrementNumRadioModeChangeToScc(); 784 } 785 for (int i = 0; i < NUM_RADIO_MODE_CHANGE_TO_SBS; i++) { 786 mWifiMetrics.incrementNumRadioModeChangeToSbs(); 787 } 788 for (int i = 0; i < NUM_RADIO_MODE_CHANGE_TO_DBS; i++) { 789 mWifiMetrics.incrementNumRadioModeChangeToDbs(); 790 } 791 for (int i = 0; i < NUM_SOFTAP_USER_BAND_PREFERENCE_UNSATISFIED; i++) { 792 mWifiMetrics.incrementNumSoftApUserBandPreferenceUnsatisfied(); 793 } 794 795 // increment pno scan metrics 796 for (int i = 0; i < NUM_PNO_SCAN_ATTEMPTS; i++) { 797 mWifiMetrics.incrementPnoScanStartAttempCount(); 798 } 799 for (int i = 0; i < NUM_PNO_SCAN_FAILED; i++) { 800 mWifiMetrics.incrementPnoScanFailedCount(); 801 } 802 for (int i = 0; i < NUM_PNO_FOUND_NETWORK_EVENTS; i++) { 803 mWifiMetrics.incrementPnoFoundNetworkEventCount(); 804 } 805 806 // set and increment "connect to network" notification metrics 807 for (int i = 0; i < NUM_CONNECT_TO_NETWORK_NOTIFICATIONS.length; i++) { 808 int count = NUM_CONNECT_TO_NETWORK_NOTIFICATIONS[i]; 809 for (int j = 0; j < count; j++) { 810 mWifiMetrics.incrementConnectToNetworkNotification(OPEN_NET_NOTIFIER_TAG, i); 811 } 812 } 813 for (int i = 0; i < NUM_CONNECT_TO_NETWORK_NOTIFICATION_ACTIONS.length; i++) { 814 int[] actions = NUM_CONNECT_TO_NETWORK_NOTIFICATION_ACTIONS[i]; 815 for (int j = 0; j < actions.length; j++) { 816 int count = actions[j]; 817 for (int k = 0; k < count; k++) { 818 mWifiMetrics.incrementConnectToNetworkNotificationAction(OPEN_NET_NOTIFIER_TAG, 819 i, j); 820 } 821 } 822 } 823 mWifiMetrics.setNetworkRecommenderBlocklistSize(OPEN_NET_NOTIFIER_TAG, 824 SIZE_OPEN_NETWORK_RECOMMENDER_BLOCKLIST); 825 mWifiMetrics.setIsWifiNetworksAvailableNotificationEnabled(OPEN_NET_NOTIFIER_TAG, 826 IS_WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON); 827 for (int i = 0; i < NUM_OPEN_NETWORK_RECOMMENDATION_UPDATES; i++) { 828 mWifiMetrics.incrementNumNetworkRecommendationUpdates(OPEN_NET_NOTIFIER_TAG); 829 } 830 for (int i = 0; i < NUM_OPEN_NETWORK_CONNECT_MESSAGE_FAILED_TO_SEND; i++) { 831 mWifiMetrics.incrementNumNetworkConnectMessageFailedToSend(OPEN_NET_NOTIFIER_TAG); 832 } 833 834 addSoftApEventsToMetrics(); 835 836 // increment wps metrics 837 for (int i = 0; i < NUM_WPS_ATTEMPTS; i++) { 838 mWifiMetrics.incrementWpsAttemptCount(); 839 } 840 for (int i = 0; i < NUM_WPS_SUCCESS; i++) { 841 mWifiMetrics.incrementWpsSuccessCount(); 842 } 843 for (int i = 0; i < NUM_WPS_START_FAILURE; i++) { 844 mWifiMetrics.incrementWpsStartFailureCount(); 845 } 846 for (int i = 0; i < NUM_WPS_OVERLAP_FAILURE; i++) { 847 mWifiMetrics.incrementWpsOverlapFailureCount(); 848 } 849 for (int i = 0; i < NUM_WPS_TIMEOUT_FAILURE; i++) { 850 mWifiMetrics.incrementWpsTimeoutFailureCount(); 851 } 852 for (int i = 0; i < NUM_WPS_OTHER_CONNECTION_FAILURE; i++) { 853 mWifiMetrics.incrementWpsOtherConnectionFailureCount(); 854 } 855 for (int i = 0; i < NUM_WPS_SUPPLICANT_FAILURE; i++) { 856 mWifiMetrics.incrementWpsSupplicantFailureCount(); 857 } 858 for (int i = 0; i < NUM_WPS_CANCELLATION; i++) { 859 mWifiMetrics.incrementWpsCancellationCount(); 860 } 861 for (int i = 0; i < NUM_SAR_SENSOR_LISTENER_REGISTRATION_FAILURES; i++) { 862 mWifiMetrics.incrementNumSarSensorRegistrationFailures(); 863 } 864 for (int i = 0; i < NUM_ONESHOT_SCAN_REQUESTS_WITH_DFS_CHANNELS; i++) { 865 mWifiMetrics.incrementOneshotScanWithDfsCount(); 866 } 867 for (int i = 0; i < NUM_ADD_OR_UPDATE_NETWORK_CALLS; i++) { 868 mWifiMetrics.incrementNumAddOrUpdateNetworkCalls(); 869 } 870 for (int i = 0; i < NUM_ENABLE_NETWORK_CALLS; i++) { 871 mWifiMetrics.incrementNumEnableNetworkCalls(); 872 } 873 874 mWifiMetrics.setWatchdogSuccessTimeDurationMs(NUM_WATCHDOG_SUCCESS_DURATION_MS); 875 mWifiMetrics.setIsMacRandomizationOn(IS_MAC_RANDOMIZATION_ON); 876 877 addWifiPowerMetrics(); 878 879 mWifiMetrics.setWifiIsUnusableLoggingEnabled(WIFI_IS_UNUSABLE_EVENT_LOGGING_SETTING); 880 mWifiMetrics.setLinkSpeedCountsLoggingEnabled(LINK_SPEED_COUNTS_LOGGING_SETTING); 881 mWifiMetrics.setWifiDataStallMinTxBad(DATA_STALL_MIN_TX_BAD_SETTING); 882 mWifiMetrics.setWifiDataStallMinRxWithoutTx(DATA_STALL_MIN_TX_SUCCESS_WITHOUT_RX_SETTING); 883 } 884 addWifiPowerMetrics()885 private void addWifiPowerMetrics() { 886 WifiRadioUsage wifiRadioUsage = new WifiRadioUsage(); 887 wifiRadioUsage.loggingDurationMs = WIFI_POWER_METRICS_LOGGING_DURATION; 888 wifiRadioUsage.scanTimeMs = WIFI_POWER_METRICS_SCAN_TIME; 889 when(mWifiPowerMetrics.buildWifiRadioUsageProto()).thenReturn(wifiRadioUsage); 890 } 891 addSoftApEventsToMetrics()892 private void addSoftApEventsToMetrics() { 893 // Total number of events recorded is NUM_SOFT_AP_EVENT_ENTRIES in both modes 894 895 mWifiMetrics.addSoftApUpChangedEvent(true, WifiManager.IFACE_IP_MODE_TETHERED); 896 mWifiMetrics.addSoftApNumAssociatedStationsChangedEvent(NUM_SOFT_AP_ASSOCIATED_STATIONS, 897 WifiManager.IFACE_IP_MODE_TETHERED); 898 mWifiMetrics.addSoftApNumAssociatedStationsChangedEvent(NUM_SOFT_AP_ASSOCIATED_STATIONS, 899 WifiManager.IFACE_IP_MODE_UNSPECIFIED); // Should be dropped. 900 mWifiMetrics.addSoftApUpChangedEvent(false, WifiManager.IFACE_IP_MODE_TETHERED); 901 // Channel switch info should be added to the last Soft AP UP event in the list 902 mWifiMetrics.addSoftApChannelSwitchedEvent(SOFT_AP_CHANNEL_FREQUENCY, 903 SOFT_AP_CHANNEL_BANDWIDTH, WifiManager.IFACE_IP_MODE_TETHERED); 904 mWifiMetrics.addSoftApUpChangedEvent(true, WifiManager.IFACE_IP_MODE_LOCAL_ONLY); 905 mWifiMetrics.addSoftApNumAssociatedStationsChangedEvent(NUM_SOFT_AP_ASSOCIATED_STATIONS, 906 WifiManager.IFACE_IP_MODE_LOCAL_ONLY); 907 // Should be dropped. 908 mWifiMetrics.addSoftApUpChangedEvent(false, WifiManager.IFACE_IP_MODE_CONFIGURATION_ERROR); 909 mWifiMetrics.addSoftApUpChangedEvent(false, WifiManager.IFACE_IP_MODE_LOCAL_ONLY); 910 } 911 verifySoftApEventsStoredInProto()912 private void verifySoftApEventsStoredInProto() { 913 assertEquals(NUM_SOFT_AP_EVENT_ENTRIES, 914 mDecodedProto.softApConnectedClientsEventsTethered.length); 915 assertEquals(SoftApConnectedClientsEvent.SOFT_AP_UP, 916 mDecodedProto.softApConnectedClientsEventsTethered[0].eventType); 917 assertEquals(0, mDecodedProto.softApConnectedClientsEventsTethered[0].numConnectedClients); 918 assertEquals(SOFT_AP_CHANNEL_FREQUENCY, 919 mDecodedProto.softApConnectedClientsEventsTethered[0].channelFrequency); 920 assertEquals(SOFT_AP_CHANNEL_BANDWIDTH, 921 mDecodedProto.softApConnectedClientsEventsTethered[0].channelBandwidth); 922 assertEquals(SoftApConnectedClientsEvent.NUM_CLIENTS_CHANGED, 923 mDecodedProto.softApConnectedClientsEventsTethered[1].eventType); 924 assertEquals(NUM_SOFT_AP_ASSOCIATED_STATIONS, 925 mDecodedProto.softApConnectedClientsEventsTethered[1].numConnectedClients); 926 assertEquals(SoftApConnectedClientsEvent.SOFT_AP_DOWN, 927 mDecodedProto.softApConnectedClientsEventsTethered[2].eventType); 928 assertEquals(0, mDecodedProto.softApConnectedClientsEventsTethered[2].numConnectedClients); 929 930 assertEquals(SoftApConnectedClientsEvent.SOFT_AP_UP, 931 mDecodedProto.softApConnectedClientsEventsLocalOnly[0].eventType); 932 assertEquals(0, mDecodedProto.softApConnectedClientsEventsLocalOnly[0].numConnectedClients); 933 assertEquals(SoftApConnectedClientsEvent.NUM_CLIENTS_CHANGED, 934 mDecodedProto.softApConnectedClientsEventsLocalOnly[1].eventType); 935 assertEquals(NUM_SOFT_AP_ASSOCIATED_STATIONS, 936 mDecodedProto.softApConnectedClientsEventsLocalOnly[1].numConnectedClients); 937 assertEquals(SoftApConnectedClientsEvent.SOFT_AP_DOWN, 938 mDecodedProto.softApConnectedClientsEventsLocalOnly[2].eventType); 939 assertEquals(0, mDecodedProto.softApConnectedClientsEventsLocalOnly[2].numConnectedClients); 940 } 941 942 /** 943 * Assert that values in deserializedWifiMetrics match those set in 'setAndIncrementMetrics' 944 */ assertDeserializedMetricsCorrect()945 public void assertDeserializedMetricsCorrect() throws Exception { 946 assertEquals("mDecodedProto.numSavedNetworks == NUM_SAVED_NETWORKS", 947 NUM_SAVED_NETWORKS, mDecodedProto.numSavedNetworks); 948 assertEquals("mDecodedProto.numSavedNetworksWithMacRandomization == NUM_SAVED_NETWORKS-1", 949 NUM_SAVED_NETWORKS - 1, mDecodedProto.numSavedNetworksWithMacRandomization); 950 assertEquals("mDecodedProto.numOpenNetworks == NUM_OPEN_NETWORKS", 951 NUM_OPEN_NETWORKS, mDecodedProto.numOpenNetworks); 952 assertEquals("mDecodedProto.numLegacyPersonalNetworks == NUM_LEGACY_PERSONAL_NETWORKS", 953 NUM_LEGACY_PERSONAL_NETWORKS, mDecodedProto.numLegacyPersonalNetworks); 954 assertEquals( 955 "mDecodedProto.numLegacyEnterpriseNetworks == NUM_LEGACY_ENTERPRISE_NETWORKS", 956 NUM_LEGACY_ENTERPRISE_NETWORKS, mDecodedProto.numLegacyEnterpriseNetworks); 957 assertEquals("mDecodedProto.numEnhancedOpenNetworks == NUM_ENHANCED_OPEN_NETWORKS", 958 NUM_ENHANCED_OPEN_NETWORKS, mDecodedProto.numEnhancedOpenNetworks); 959 assertEquals("mDecodedProto.numWpa3PersonalNetworks == NUM_WPA3_PERSONAL_NETWORKS", 960 NUM_WPA3_PERSONAL_NETWORKS, mDecodedProto.numWpa3PersonalNetworks); 961 assertEquals("mDecodedProto.numWpa3EnterpriseNetworks == NUM_WPA3_ENTERPRISE_NETWORKS", 962 NUM_WPA3_ENTERPRISE_NETWORKS, mDecodedProto.numWpa3EnterpriseNetworks); 963 assertEquals("mDecodedProto.numNetworksAddedByUser == NUM_NETWORKS_ADDED_BY_USER", 964 NUM_NETWORKS_ADDED_BY_USER, mDecodedProto.numNetworksAddedByUser); 965 assertEquals(NUM_HIDDEN_NETWORKS, mDecodedProto.numHiddenNetworks); 966 assertEquals(NUM_PASSPOINT_NETWORKS, mDecodedProto.numPasspointNetworks); 967 assertEquals("mDecodedProto.numNetworksAddedByApps == NUM_NETWORKS_ADDED_BY_APPS", 968 NUM_NETWORKS_ADDED_BY_APPS, mDecodedProto.numNetworksAddedByApps); 969 assertEquals("mDecodedProto.isLocationEnabled == TEST_VAL_IS_LOCATION_ENABLED", 970 TEST_VAL_IS_LOCATION_ENABLED, mDecodedProto.isLocationEnabled); 971 assertEquals("mDecodedProto.isScanningAlwaysEnabled == IS_SCANNING_ALWAYS_ENABLED", 972 IS_SCANNING_ALWAYS_ENABLED, mDecodedProto.isScanningAlwaysEnabled); 973 assertEquals("mDecodedProto.numEmptyScanResults == NUM_EMPTY_SCAN_RESULTS", 974 NUM_EMPTY_SCAN_RESULTS, mDecodedProto.numEmptyScanResults); 975 assertEquals("mDecodedProto.numNonEmptyScanResults == NUM_NON_EMPTY_SCAN_RESULTS", 976 NUM_NON_EMPTY_SCAN_RESULTS, mDecodedProto.numNonEmptyScanResults); 977 assertScanReturnEntryEquals(WifiMetricsProto.WifiLog.SCAN_UNKNOWN, NUM_SCAN_UNKNOWN); 978 assertScanReturnEntryEquals(WifiMetricsProto.WifiLog.SCAN_SUCCESS, NUM_SCAN_SUCCESS); 979 assertScanReturnEntryEquals(WifiMetricsProto.WifiLog.SCAN_FAILURE_INTERRUPTED, 980 NUM_SCAN_FAILURE_INTERRUPTED); 981 assertScanReturnEntryEquals(WifiMetricsProto.WifiLog.SCAN_FAILURE_INVALID_CONFIGURATION, 982 NUM_SCAN_FAILURE_INVALID_CONFIGURATION); 983 assertSystemStateEntryEquals(WifiMetricsProto.WifiLog.WIFI_UNKNOWN, false, 984 NUM_WIFI_UNKNOWN_SCREEN_OFF); 985 assertSystemStateEntryEquals(WifiMetricsProto.WifiLog.WIFI_UNKNOWN, true, 986 NUM_WIFI_UNKNOWN_SCREEN_ON); 987 assertSystemStateEntryEquals( 988 WifiMetricsProto.WifiLog.WIFI_ASSOCIATED, false, NUM_WIFI_ASSOCIATED_SCREEN_OFF); 989 assertSystemStateEntryEquals(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED, true, 990 NUM_WIFI_ASSOCIATED_SCREEN_ON); 991 assertEquals(NUM_CONNECTIVITY_WATCHDOG_PNO_GOOD, 992 mDecodedProto.numConnectivityWatchdogPnoGood); 993 assertEquals(NUM_CONNECTIVITY_WATCHDOG_PNO_BAD, 994 mDecodedProto.numConnectivityWatchdogPnoBad); 995 assertEquals(NUM_CONNECTIVITY_WATCHDOG_BACKGROUND_GOOD, 996 mDecodedProto.numConnectivityWatchdogBackgroundGood); 997 assertEquals(NUM_CONNECTIVITY_WATCHDOG_BACKGROUND_BAD, 998 mDecodedProto.numConnectivityWatchdogBackgroundBad); 999 assertEquals(NUM_LAST_RESORT_WATCHDOG_TRIGGERS, 1000 mDecodedProto.numLastResortWatchdogTriggers); 1001 assertEquals(NUM_LAST_RESORT_WATCHDOG_BAD_ASSOCIATION_NETWORKS_TOTAL, 1002 mDecodedProto.numLastResortWatchdogBadAssociationNetworksTotal); 1003 assertEquals(NUM_LAST_RESORT_WATCHDOG_BAD_AUTHENTICATION_NETWORKS_TOTAL, 1004 mDecodedProto.numLastResortWatchdogBadAuthenticationNetworksTotal); 1005 assertEquals(NUM_LAST_RESORT_WATCHDOG_BAD_DHCP_NETWORKS_TOTAL, 1006 mDecodedProto.numLastResortWatchdogBadDhcpNetworksTotal); 1007 assertEquals(NUM_LAST_RESORT_WATCHDOG_BAD_OTHER_NETWORKS_TOTAL, 1008 mDecodedProto.numLastResortWatchdogBadOtherNetworksTotal); 1009 assertEquals(NUM_LAST_RESORT_WATCHDOG_AVAILABLE_NETWORKS_TOTAL, 1010 mDecodedProto.numLastResortWatchdogAvailableNetworksTotal); 1011 assertEquals(NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_ASSOCIATION, 1012 mDecodedProto.numLastResortWatchdogTriggersWithBadAssociation); 1013 assertEquals(NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_AUTHENTICATION, 1014 mDecodedProto.numLastResortWatchdogTriggersWithBadAuthentication); 1015 assertEquals(NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_DHCP, 1016 mDecodedProto.numLastResortWatchdogTriggersWithBadDhcp); 1017 assertEquals(NUM_LAST_RESORT_WATCHDOG_TRIGGERS_WITH_BAD_OTHER, 1018 mDecodedProto.numLastResortWatchdogTriggersWithBadOther); 1019 assertEquals(NUM_LAST_RESORT_WATCHDOG_SUCCESSES, 1020 mDecodedProto.numLastResortWatchdogSuccesses); 1021 assertEquals(WATCHDOG_TOTAL_CONNECTION_FAILURE_COUNT_AFTER_TRIGGER, 1022 mDecodedProto.watchdogTotalConnectionFailureCountAfterTrigger); 1023 assertEquals(TEST_RECORD_DURATION_SEC, 1024 mDecodedProto.recordDurationSec); 1025 for (int i = 0; i < NUM_RSSI_LEVELS_TO_INCREMENT; i++) { 1026 assertEquals(RSSI_POLL_FREQUENCY, 1027 mDecodedProto.rssiPollRssiCount[i].frequency); 1028 assertEquals(MIN_RSSI_LEVEL + i, mDecodedProto.rssiPollRssiCount[i].rssi); 1029 assertEquals(i + 1, mDecodedProto.rssiPollRssiCount[i].count); 1030 } 1031 StringBuilder sb_rssi = new StringBuilder(); 1032 sb_rssi.append("Number of RSSIs = " + mDecodedProto.rssiPollRssiCount.length); 1033 assertTrue(sb_rssi.toString(), (mDecodedProto.rssiPollRssiCount.length 1034 <= (MAX_RSSI_LEVEL - MIN_RSSI_LEVEL + 1))); 1035 assertEquals(2, mDecodedProto.alertReasonCount[0].count); // Clamped reasons. 1036 assertEquals(3, mDecodedProto.alertReasonCount[1].count); 1037 assertEquals(1, mDecodedProto.alertReasonCount[2].count); 1038 assertEquals(3, mDecodedProto.alertReasonCount.length); 1039 assertEquals(NUM_TOTAL_SCAN_RESULTS * NUM_SCANS, 1040 mDecodedProto.numTotalScanResults); 1041 assertEquals(NUM_OPEN_NETWORK_SCAN_RESULTS * NUM_SCANS, 1042 mDecodedProto.numOpenNetworkScanResults); 1043 assertEquals(NUM_LEGACY_PERSONAL_NETWORK_SCAN_RESULTS * NUM_SCANS, 1044 mDecodedProto.numLegacyPersonalNetworkScanResults); 1045 assertEquals(NUM_LEGACY_ENTERPRISE_NETWORK_SCAN_RESULTS * NUM_SCANS, 1046 mDecodedProto.numLegacyEnterpriseNetworkScanResults); 1047 assertEquals(NUM_ENHANCED_OPEN_NETWORK_SCAN_RESULTS * NUM_SCANS, 1048 mDecodedProto.numEnhancedOpenNetworkScanResults); 1049 assertEquals(NUM_WPA3_PERSONAL_NETWORK_SCAN_RESULTS * NUM_SCANS, 1050 mDecodedProto.numWpa3PersonalNetworkScanResults); 1051 assertEquals(NUM_WPA3_ENTERPRISE_NETWORK_SCAN_RESULTS * NUM_SCANS, 1052 mDecodedProto.numWpa3EnterpriseNetworkScanResults); 1053 assertEquals(NUM_HIDDEN_NETWORK_SCAN_RESULTS * NUM_SCANS, 1054 mDecodedProto.numHiddenNetworkScanResults); 1055 assertEquals(NUM_HOTSPOT2_R1_NETWORK_SCAN_RESULTS * NUM_SCANS, 1056 mDecodedProto.numHotspot2R1NetworkScanResults); 1057 assertEquals(NUM_HOTSPOT2_R2_NETWORK_SCAN_RESULTS * NUM_SCANS, 1058 mDecodedProto.numHotspot2R2NetworkScanResults); 1059 assertEquals(NUM_SCANS, 1060 mDecodedProto.numScans); 1061 assertEquals(NUM_CONNECTIVITY_ONESHOT_SCAN_EVENT, 1062 mDecodedProto.numConnectivityOneshotScans); 1063 assertEquals(NUM_EXTERNAL_APP_ONESHOT_SCAN_REQUESTS, 1064 mDecodedProto.numExternalAppOneshotScanRequests); 1065 assertEquals(NUM_EXTERNAL_FOREGROUND_APP_ONESHOT_SCAN_REQUESTS_THROTTLED, 1066 mDecodedProto.numExternalForegroundAppOneshotScanRequestsThrottled); 1067 assertEquals(NUM_EXTERNAL_BACKGROUND_APP_ONESHOT_SCAN_REQUESTS_THROTTLED, 1068 mDecodedProto.numExternalBackgroundAppOneshotScanRequestsThrottled); 1069 1070 for (int score_index = 0; score_index < NUM_WIFI_SCORES_TO_INCREMENT; score_index++) { 1071 assertEquals(WIFI_SCORE_RANGE_MIN + score_index, 1072 mDecodedProto.wifiScoreCount[score_index].score); 1073 assertEquals(WIFI_SCORE_RANGE_MIN + score_index + 1, 1074 mDecodedProto.wifiScoreCount[score_index].count); 1075 assertEquals(WIFI_SCORE_RANGE_MIN + score_index, 1076 mDecodedProto.wifiUsabilityScoreCount[score_index].score); 1077 assertEquals(WIFI_SCORE_RANGE_MIN + score_index + 1, 1078 mDecodedProto.wifiUsabilityScoreCount[score_index].count); 1079 } 1080 StringBuilder sb_wifi_score = new StringBuilder(); 1081 sb_wifi_score.append("Number of wifi_scores = " + mDecodedProto.wifiScoreCount.length); 1082 assertTrue(sb_wifi_score.toString(), (mDecodedProto.wifiScoreCount.length 1083 <= (WIFI_SCORE_RANGE_MAX - WIFI_SCORE_RANGE_MIN + 1))); 1084 StringBuilder sb_wifi_limits = new StringBuilder(); 1085 sb_wifi_limits.append("Wifi Score limit is " + ConnectedScore.WIFI_MAX_SCORE 1086 + ">= " + WIFI_SCORE_RANGE_MAX); 1087 assertTrue(sb_wifi_limits.toString(), 1088 ConnectedScore.WIFI_MAX_SCORE <= WIFI_SCORE_RANGE_MAX); 1089 StringBuilder sb_wifi_usability_score = new StringBuilder(); 1090 sb_wifi_usability_score.append("Number of wifi_usability_scores = " 1091 + mDecodedProto.wifiUsabilityScoreCount.length); 1092 assertTrue(sb_wifi_usability_score.toString(), (mDecodedProto.wifiUsabilityScoreCount.length 1093 <= (WIFI_SCORE_RANGE_MAX - WIFI_SCORE_RANGE_MIN + 1))); 1094 StringBuilder sb_wifi_usablity_limits = new StringBuilder(); 1095 sb_wifi_limits.append("Wifi Usability Score limit is " + ConnectedScore.WIFI_MAX_SCORE 1096 + ">= " + WIFI_SCORE_RANGE_MAX); 1097 assertTrue(sb_wifi_limits.toString(), 1098 ConnectedScore.WIFI_MAX_SCORE <= WIFI_SCORE_RANGE_MAX); 1099 assertEquals(MAX_NUM_SOFTAP_RETURN_CODES, mDecodedProto.softApReturnCode.length); 1100 assertEquals(WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_STARTED_SUCCESSFULLY, 1101 mDecodedProto.softApReturnCode[0].startResult); 1102 assertEquals(NUM_SOFTAP_START_SUCCESS, mDecodedProto.softApReturnCode[0].count); 1103 assertEquals(WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_GENERAL_ERROR, 1104 mDecodedProto.softApReturnCode[1].startResult); 1105 assertEquals(NUM_SOFTAP_FAILED_GENERAL_ERROR, 1106 mDecodedProto.softApReturnCode[1].count); 1107 assertEquals(WifiMetricsProto.SoftApReturnCodeCount.SOFT_AP_FAILED_NO_CHANNEL, 1108 mDecodedProto.softApReturnCode[2].startResult); 1109 assertEquals(NUM_SOFTAP_FAILED_NO_CHANNEL, 1110 mDecodedProto.softApReturnCode[2].count); 1111 assertEquals(NUM_HAL_CRASHES, mDecodedProto.numHalCrashes); 1112 assertEquals(NUM_WIFICOND_CRASHES, mDecodedProto.numWificondCrashes); 1113 assertEquals(NUM_SUPPLICANT_CRASHES, mDecodedProto.numSupplicantCrashes); 1114 assertEquals(NUM_HOSTAPD_CRASHES, mDecodedProto.numHostapdCrashes); 1115 assertEquals(NUM_WIFI_ON_FAILURE_DUE_TO_HAL, 1116 mDecodedProto.numSetupClientInterfaceFailureDueToHal); 1117 assertEquals(NUM_WIFI_ON_FAILURE_DUE_TO_WIFICOND, 1118 mDecodedProto.numSetupClientInterfaceFailureDueToWificond); 1119 assertEquals(NUM_WIFI_ON_FAILURE_DUE_TO_SUPPLICANT, 1120 mDecodedProto.numSetupClientInterfaceFailureDueToSupplicant); 1121 assertEquals(NUM_SOFTAP_ON_FAILURE_DUE_TO_HAL, 1122 mDecodedProto.numSetupSoftApInterfaceFailureDueToHal); 1123 assertEquals(NUM_SOFTAP_ON_FAILURE_DUE_TO_WIFICOND, 1124 mDecodedProto.numSetupSoftApInterfaceFailureDueToWificond); 1125 assertEquals(NUM_SOFTAP_ON_FAILURE_DUE_TO_HOSTAPD, 1126 mDecodedProto.numSetupSoftApInterfaceFailureDueToHostapd); 1127 assertEquals(NUM_CLIENT_INTERFACE_DOWN, mDecodedProto.numClientInterfaceDown); 1128 assertEquals(NUM_SOFTAP_INTERFACE_DOWN, mDecodedProto.numSoftApInterfaceDown); 1129 assertEquals(NUM_PASSPOINT_PROVIDERS, mDecodedProto.numPasspointProviders); 1130 assertPasspointProfileTypeCount(mDecodedProto.installedPasspointProfileTypeForR1); 1131 assertPasspointProfileTypeCount(mDecodedProto.installedPasspointProfileTypeForR2); 1132 assertEquals(NUM_PASSPOINT_PROVIDER_INSTALLATION, 1133 mDecodedProto.numPasspointProviderInstallation); 1134 assertEquals(NUM_PASSPOINT_PROVIDER_INSTALL_SUCCESS, 1135 mDecodedProto.numPasspointProviderInstallSuccess); 1136 assertEquals(NUM_PASSPOINT_PROVIDER_UNINSTALLATION, 1137 mDecodedProto.numPasspointProviderUninstallation); 1138 assertEquals(NUM_PASSPOINT_PROVIDER_UNINSTALL_SUCCESS, 1139 mDecodedProto.numPasspointProviderUninstallSuccess); 1140 assertEquals(NUM_PASSPOINT_PROVIDERS_SUCCESSFULLY_CONNECTED, 1141 mDecodedProto.numPasspointProvidersSuccessfullyConnected); 1142 assertEquals(NUM_RADIO_MODE_CHANGE_TO_MCC, mDecodedProto.numRadioModeChangeToMcc); 1143 assertEquals(NUM_RADIO_MODE_CHANGE_TO_SCC, mDecodedProto.numRadioModeChangeToScc); 1144 assertEquals(NUM_RADIO_MODE_CHANGE_TO_SBS, mDecodedProto.numRadioModeChangeToSbs); 1145 assertEquals(NUM_RADIO_MODE_CHANGE_TO_DBS, mDecodedProto.numRadioModeChangeToDbs); 1146 assertEquals(NUM_SOFTAP_USER_BAND_PREFERENCE_UNSATISFIED, 1147 mDecodedProto.numSoftApUserBandPreferenceUnsatisfied); 1148 1149 PnoScanMetrics pno_metrics = mDecodedProto.pnoScanMetrics; 1150 assertNotNull(pno_metrics); 1151 assertEquals(NUM_PNO_SCAN_ATTEMPTS, pno_metrics.numPnoScanAttempts); 1152 assertEquals(NUM_PNO_SCAN_FAILED, pno_metrics.numPnoScanFailed); 1153 assertEquals(NUM_PNO_FOUND_NETWORK_EVENTS, pno_metrics.numPnoFoundNetworkEvents); 1154 1155 for (ConnectToNetworkNotificationAndActionCount notificationCount 1156 : mDecodedProto.connectToNetworkNotificationCount) { 1157 assertEquals(NUM_CONNECT_TO_NETWORK_NOTIFICATIONS[notificationCount.notification], 1158 notificationCount.count); 1159 assertEquals(ConnectToNetworkNotificationAndActionCount.RECOMMENDER_OPEN, 1160 notificationCount.recommender); 1161 } 1162 for (ConnectToNetworkNotificationAndActionCount notificationActionCount 1163 : mDecodedProto.connectToNetworkNotificationActionCount) { 1164 assertEquals(NUM_CONNECT_TO_NETWORK_NOTIFICATION_ACTIONS 1165 [notificationActionCount.notification] 1166 [notificationActionCount.action], 1167 notificationActionCount.count); 1168 assertEquals(ConnectToNetworkNotificationAndActionCount.RECOMMENDER_OPEN, 1169 notificationActionCount.recommender); 1170 } 1171 1172 assertEquals(SIZE_OPEN_NETWORK_RECOMMENDER_BLOCKLIST, 1173 mDecodedProto.openNetworkRecommenderBlacklistSize); 1174 assertEquals(IS_WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON, 1175 mDecodedProto.isWifiNetworksAvailableNotificationOn); 1176 assertEquals(NUM_OPEN_NETWORK_RECOMMENDATION_UPDATES, 1177 mDecodedProto.numOpenNetworkRecommendationUpdates); 1178 assertEquals(NUM_OPEN_NETWORK_CONNECT_MESSAGE_FAILED_TO_SEND, 1179 mDecodedProto.numOpenNetworkConnectMessageFailedToSend); 1180 1181 verifySoftApEventsStoredInProto(); 1182 1183 WpsMetrics wps_metrics = mDecodedProto.wpsMetrics; 1184 assertNotNull(wps_metrics); 1185 assertEquals(NUM_WPS_ATTEMPTS, wps_metrics.numWpsAttempts); 1186 assertEquals(NUM_WPS_SUCCESS, wps_metrics.numWpsSuccess); 1187 assertEquals(NUM_WPS_START_FAILURE, wps_metrics.numWpsStartFailure); 1188 assertEquals(NUM_WPS_OVERLAP_FAILURE, wps_metrics.numWpsOverlapFailure); 1189 assertEquals(NUM_WPS_TIMEOUT_FAILURE, wps_metrics.numWpsTimeoutFailure); 1190 assertEquals(NUM_WPS_OTHER_CONNECTION_FAILURE, wps_metrics.numWpsOtherConnectionFailure); 1191 assertEquals(NUM_WPS_SUPPLICANT_FAILURE, wps_metrics.numWpsSupplicantFailure); 1192 assertEquals(NUM_WPS_CANCELLATION, wps_metrics.numWpsCancellation); 1193 1194 assertEquals(NUM_WATCHDOG_SUCCESS_DURATION_MS, 1195 mDecodedProto.watchdogTriggerToConnectionSuccessDurationMs); 1196 assertEquals(IS_MAC_RANDOMIZATION_ON, mDecodedProto.isMacRandomizationOn); 1197 assertEquals(WIFI_POWER_METRICS_LOGGING_DURATION, 1198 mDecodedProto.wifiRadioUsage.loggingDurationMs); 1199 assertEquals(WIFI_POWER_METRICS_SCAN_TIME, 1200 mDecodedProto.wifiRadioUsage.scanTimeMs); 1201 assertEquals(WIFI_IS_UNUSABLE_EVENT_LOGGING_SETTING, 1202 mDecodedProto.experimentValues.wifiIsUnusableLoggingEnabled); 1203 assertEquals(LINK_SPEED_COUNTS_LOGGING_SETTING, 1204 mDecodedProto.experimentValues.linkSpeedCountsLoggingEnabled); 1205 assertEquals(DATA_STALL_MIN_TX_BAD_SETTING, 1206 mDecodedProto.experimentValues.wifiDataStallMinTxBad); 1207 assertEquals(DATA_STALL_MIN_TX_SUCCESS_WITHOUT_RX_SETTING, 1208 mDecodedProto.experimentValues.wifiDataStallMinTxSuccessWithoutRx); 1209 1210 assertEquals(NUM_SAR_SENSOR_LISTENER_REGISTRATION_FAILURES, 1211 mDecodedProto.numSarSensorRegistrationFailures); 1212 assertEquals(NUM_ONESHOT_SCAN_REQUESTS_WITH_DFS_CHANNELS, 1213 mDecodedProto.numOneshotHasDfsChannelScans); 1214 assertEquals(NUM_ADD_OR_UPDATE_NETWORK_CALLS, mDecodedProto.numAddOrUpdateNetworkCalls); 1215 assertEquals(NUM_ENABLE_NETWORK_CALLS, mDecodedProto.numEnableNetworkCalls); 1216 } 1217 1218 /** 1219 * Assert deserialized metrics Scan Return Entry equals count 1220 */ assertScanReturnEntryEquals(int returnCode, int count)1221 public void assertScanReturnEntryEquals(int returnCode, int count) { 1222 for (int i = 0; i < mDecodedProto.scanReturnEntries.length; i++) { 1223 if (mDecodedProto.scanReturnEntries[i].scanReturnCode == returnCode) { 1224 assertEquals(count, mDecodedProto.scanReturnEntries[i].scanResultsCount); 1225 return; 1226 } 1227 } 1228 assertEquals(null, count); 1229 } 1230 1231 /** 1232 * Assert deserialized metrics SystemState entry equals count 1233 */ assertSystemStateEntryEquals(int state, boolean screenOn, int count)1234 public void assertSystemStateEntryEquals(int state, boolean screenOn, int count) { 1235 for (int i = 0; i < mDecodedProto.wifiSystemStateEntries.length; i++) { 1236 if (mDecodedProto.wifiSystemStateEntries[i].wifiState == state 1237 && mDecodedProto.wifiSystemStateEntries[i].isScreenOn == screenOn) { 1238 assertEquals(count, mDecodedProto.wifiSystemStateEntries[i].wifiStateCount); 1239 return; 1240 } 1241 } 1242 assertEquals(null, count); 1243 } 1244 1245 /** 1246 * Test the number of Passpoint provision with the failure code are collected correctly 1247 * 1248 * @throws Exception 1249 */ 1250 @Test testPasspointProvisionMetrics()1251 public void testPasspointProvisionMetrics() throws Exception { 1252 //Increment count for provisioning success. 1253 mWifiMetrics.incrementPasspointProvisionSuccess(); 1254 1255 // Increment count for provisioning unavailable 1256 mWifiMetrics.incrementPasspointProvisionFailure( 1257 ProvisioningCallback.OSU_FAILURE_PROVISIONING_NOT_AVAILABLE); 1258 mWifiMetrics.incrementPasspointProvisionFailure( 1259 ProvisioningCallback.OSU_FAILURE_PROVISIONING_NOT_AVAILABLE); 1260 1261 // Increment count for server connection failure 1262 mWifiMetrics.incrementPasspointProvisionFailure( 1263 ProvisioningCallback.OSU_FAILURE_AP_CONNECTION); 1264 1265 // Dump proto and deserialize 1266 dumpProtoAndDeserialize(); 1267 1268 assertEquals(mDecodedProto.passpointProvisionStats.numProvisionSuccess, 1); 1269 assertEquals(mDecodedProto.passpointProvisionStats.provisionFailureCount.length, 2); 1270 assertEquals(mDecodedProto.passpointProvisionStats.provisionFailureCount[0].failureCode, 1271 PasspointProvisionStats.OSU_FAILURE_AP_CONNECTION); 1272 assertEquals(mDecodedProto.passpointProvisionStats.provisionFailureCount[0].count, 1); 1273 assertEquals(mDecodedProto.passpointProvisionStats.provisionFailureCount[1].failureCode, 1274 PasspointProvisionStats.OSU_FAILURE_PROVISIONING_NOT_AVAILABLE); 1275 assertEquals(mDecodedProto.passpointProvisionStats.provisionFailureCount[1].count, 2); 1276 } 1277 1278 /** 1279 * Combination of all other WifiMetrics unit tests, an internal-integration test, or functional 1280 * test 1281 */ 1282 @Test setMetricsSerializeDeserializeAssertMetricsSame()1283 public void setMetricsSerializeDeserializeAssertMetricsSame() throws Exception { 1284 setAndIncrementMetrics(); 1285 startAndEndConnectionEventSucceeds(); 1286 dumpProtoAndDeserialize(); 1287 assertDeserializedMetricsCorrect(); 1288 assertEquals("mDecodedProto.connectionEvent.length", 1289 2, mDecodedProto.connectionEvent.length); 1290 //<TODO> test individual connectionEvents for correctness, 1291 // check scanReturnEntries & wifiSystemStateEntries counts and individual elements 1292 // pending their implementation</TODO> 1293 } 1294 1295 /** 1296 * Test that score breach events are properly generated 1297 */ 1298 @Test testScoreBeachEvents()1299 public void testScoreBeachEvents() throws Exception { 1300 int upper = WifiMetrics.LOW_WIFI_SCORE + 7; 1301 int mid = WifiMetrics.LOW_WIFI_SCORE; 1302 int lower = WifiMetrics.LOW_WIFI_SCORE - 8; 1303 mWifiMetrics.setWifiState(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED); 1304 for (int score = upper; score >= mid; score--) mWifiMetrics.incrementWifiScoreCount(score); 1305 mWifiMetrics.incrementWifiScoreCount(mid + 1); 1306 mWifiMetrics.incrementWifiScoreCount(lower); // First breach 1307 for (int score = lower; score <= mid; score++) mWifiMetrics.incrementWifiScoreCount(score); 1308 mWifiMetrics.incrementWifiScoreCount(mid - 1); 1309 mWifiMetrics.incrementWifiScoreCount(upper); // Second breach 1310 1311 dumpProtoAndDeserialize(); 1312 1313 assertEquals(2, mDecodedProto.staEventList.length); 1314 assertEquals(StaEvent.TYPE_SCORE_BREACH, mDecodedProto.staEventList[0].type); 1315 assertEquals(lower, mDecodedProto.staEventList[0].lastScore); 1316 assertEquals(StaEvent.TYPE_SCORE_BREACH, mDecodedProto.staEventList[1].type); 1317 assertEquals(upper, mDecodedProto.staEventList[1].lastScore); 1318 } 1319 1320 /** 1321 * Test that Wifi usability score breach events are properly generated 1322 */ 1323 @Test testWifiUsabilityScoreBreachEvents()1324 public void testWifiUsabilityScoreBreachEvents() throws Exception { 1325 int upper = WifiMetrics.LOW_WIFI_USABILITY_SCORE + 7; 1326 int mid = WifiMetrics.LOW_WIFI_USABILITY_SCORE; 1327 int lower = WifiMetrics.LOW_WIFI_USABILITY_SCORE - 8; 1328 mWifiMetrics.setWifiState(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED); 1329 for (int score = upper; score >= mid; score--) { 1330 mWifiMetrics.incrementWifiUsabilityScoreCount(1, score, 15); 1331 } 1332 mWifiMetrics.incrementWifiUsabilityScoreCount(1, mid + 1, 15); 1333 mWifiMetrics.incrementWifiUsabilityScoreCount(1, lower, 15); // First breach 1334 for (int score = lower; score <= mid; score++) { 1335 mWifiMetrics.incrementWifiUsabilityScoreCount(1, score, 15); 1336 } 1337 mWifiMetrics.incrementWifiUsabilityScoreCount(1, mid - 1, 15); 1338 mWifiMetrics.incrementWifiUsabilityScoreCount(1, upper, 15); // Second breach 1339 1340 dumpProtoAndDeserialize(); 1341 1342 assertEquals(2, mDecodedProto.staEventList.length); 1343 assertEquals(StaEvent.TYPE_WIFI_USABILITY_SCORE_BREACH, mDecodedProto.staEventList[0].type); 1344 assertEquals(lower, mDecodedProto.staEventList[0].lastWifiUsabilityScore); 1345 assertEquals(StaEvent.TYPE_WIFI_USABILITY_SCORE_BREACH, mDecodedProto.staEventList[1].type); 1346 assertEquals(upper, mDecodedProto.staEventList[1].lastWifiUsabilityScore); 1347 } 1348 1349 private static final String SSID = "red"; 1350 private static final int CONFIG_DTIM = 3; 1351 private static final int NETWORK_DETAIL_WIFIMODE = 5; 1352 private static final int NETWORK_DETAIL_DTIM = 7; 1353 private static final int SCAN_RESULT_LEVEL = -30; 1354 /** 1355 * Test that WifiMetrics is correctly getting data from ScanDetail and WifiConfiguration 1356 */ 1357 @Test testScanDetailAndWifiConfigurationUsage()1358 public void testScanDetailAndWifiConfigurationUsage() throws Exception { 1359 //Setup mock configs and scan details 1360 NetworkDetail networkDetail = mock(NetworkDetail.class); 1361 when(networkDetail.getWifiMode()).thenReturn(NETWORK_DETAIL_WIFIMODE); 1362 when(networkDetail.getSSID()).thenReturn(SSID); 1363 when(networkDetail.getDtimInterval()).thenReturn(NETWORK_DETAIL_DTIM); 1364 ScanResult scanResult = mock(ScanResult.class); 1365 scanResult.level = SCAN_RESULT_LEVEL; 1366 scanResult.capabilities = "EAP"; 1367 WifiConfiguration config = mock(WifiConfiguration.class); 1368 config.SSID = "\"" + SSID + "\""; 1369 config.dtimInterval = CONFIG_DTIM; 1370 config.macRandomizationSetting = WifiConfiguration.RANDOMIZATION_PERSISTENT; 1371 config.allowedKeyManagement = new BitSet(); 1372 config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_EAP); 1373 config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.IEEE8021X); 1374 config.enterpriseConfig = new WifiEnterpriseConfig(); 1375 config.enterpriseConfig.setEapMethod(WifiEnterpriseConfig.Eap.TTLS); 1376 config.enterpriseConfig.setPhase2Method(WifiEnterpriseConfig.Phase2.MSCHAPV2); 1377 WifiConfiguration.NetworkSelectionStatus networkSelectionStat = 1378 mock(WifiConfiguration.NetworkSelectionStatus.class); 1379 when(networkSelectionStat.getCandidate()).thenReturn(scanResult); 1380 when(config.getNetworkSelectionStatus()).thenReturn(networkSelectionStat); 1381 ScanDetail scanDetail = mock(ScanDetail.class); 1382 when(scanDetail.getNetworkDetail()).thenReturn(networkDetail); 1383 when(scanDetail.getScanResult()).thenReturn(scanResult); 1384 1385 config.networkId = TEST_NETWORK_ID; 1386 mWifiMetrics.setNominatorForNetwork(TEST_NETWORK_ID, 1387 WifiMetricsProto.ConnectionEvent.NOMINATOR_MANUAL); 1388 1389 //Create a connection event using only the config 1390 mWifiMetrics.startConnectionEvent(config, "Red", 1391 WifiMetricsProto.ConnectionEvent.ROAM_NONE); 1392 mWifiMetrics.endConnectionEvent( 1393 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1394 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1395 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1396 1397 //Change configuration to open without randomization 1398 config.macRandomizationSetting = WifiConfiguration.RANDOMIZATION_NONE; 1399 scanResult.capabilities = ""; 1400 //Create a connection event using the config and a scan detail 1401 mWifiMetrics.startConnectionEvent(config, "Green", 1402 WifiMetricsProto.ConnectionEvent.ROAM_NONE); 1403 mWifiMetrics.setConnectionScanDetail(scanDetail); 1404 mWifiMetrics.endConnectionEvent( 1405 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1406 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1407 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1408 1409 //Dump proto from mWifiMetrics and deserialize it to mDecodedProto 1410 dumpProtoAndDeserialize(); 1411 1412 //Check that the correct values are being flowed through 1413 assertEquals(2, mDecodedProto.connectionEvent.length); 1414 assertEquals(CONFIG_DTIM, mDecodedProto.connectionEvent[0].routerFingerprint.dtim); 1415 assertEquals(WifiMetricsProto.RouterFingerPrint.AUTH_ENTERPRISE, 1416 mDecodedProto.connectionEvent[0].routerFingerprint.authentication); 1417 assertEquals(WifiMetricsProto.RouterFingerPrint.TYPE_EAP_TTLS, 1418 mDecodedProto.connectionEvent[0].routerFingerprint.eapMethod); 1419 assertEquals(WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_MSCHAPV2, 1420 mDecodedProto.connectionEvent[0].routerFingerprint.authPhase2Method); 1421 assertEquals(SCAN_RESULT_LEVEL, mDecodedProto.connectionEvent[0].signalStrength); 1422 assertEquals(NETWORK_DETAIL_DTIM, mDecodedProto.connectionEvent[1].routerFingerprint.dtim); 1423 assertEquals(WifiMetricsProto.RouterFingerPrint.AUTH_OPEN, 1424 mDecodedProto.connectionEvent[1].routerFingerprint.authentication); 1425 assertEquals(WifiMetricsProto.RouterFingerPrint.TYPE_EAP_UNKNOWN, 1426 mDecodedProto.connectionEvent[1].routerFingerprint.eapMethod); 1427 assertEquals(WifiMetricsProto.RouterFingerPrint.TYPE_PHASE2_NONE, 1428 mDecodedProto.connectionEvent[1].routerFingerprint.authPhase2Method); 1429 assertEquals(SCAN_RESULT_LEVEL, mDecodedProto.connectionEvent[1].signalStrength); 1430 assertEquals(NETWORK_DETAIL_WIFIMODE, 1431 mDecodedProto.connectionEvent[1].routerFingerprint.routerTechnology); 1432 assertTrue(mDecodedProto.connectionEvent[0].useRandomizedMac); 1433 assertFalse(mDecodedProto.connectionEvent[1].useRandomizedMac); 1434 assertEquals(WifiMetricsProto.ConnectionEvent.NOMINATOR_MANUAL, 1435 mDecodedProto.connectionEvent[0].connectionNominator); 1436 } 1437 1438 /** 1439 * Tests that the mapping from networkId to nominatorId is not cleared. 1440 */ 1441 @Test testNetworkToNominatorNotCleared()1442 public void testNetworkToNominatorNotCleared() throws Exception { 1443 //Setup mock configs and scan details 1444 NetworkDetail networkDetail = mock(NetworkDetail.class); 1445 when(networkDetail.getWifiMode()).thenReturn(NETWORK_DETAIL_WIFIMODE); 1446 when(networkDetail.getSSID()).thenReturn(SSID); 1447 when(networkDetail.getDtimInterval()).thenReturn(NETWORK_DETAIL_DTIM); 1448 ScanResult scanResult = mock(ScanResult.class); 1449 scanResult.level = SCAN_RESULT_LEVEL; 1450 WifiConfiguration config = mock(WifiConfiguration.class); 1451 config.SSID = "\"" + SSID + "\""; 1452 config.dtimInterval = CONFIG_DTIM; 1453 config.macRandomizationSetting = WifiConfiguration.RANDOMIZATION_PERSISTENT; 1454 WifiConfiguration.NetworkSelectionStatus networkSelectionStat = 1455 mock(WifiConfiguration.NetworkSelectionStatus.class); 1456 when(networkSelectionStat.getCandidate()).thenReturn(scanResult); 1457 when(config.getNetworkSelectionStatus()).thenReturn(networkSelectionStat); 1458 ScanDetail scanDetail = mock(ScanDetail.class); 1459 when(scanDetail.getNetworkDetail()).thenReturn(networkDetail); 1460 when(scanDetail.getScanResult()).thenReturn(scanResult); 1461 1462 config.networkId = TEST_NETWORK_ID; 1463 mWifiMetrics.setNominatorForNetwork(TEST_NETWORK_ID, 1464 WifiMetricsProto.ConnectionEvent.NOMINATOR_CARRIER); 1465 1466 // dump() calls clear() internally 1467 mWifiMetrics.dump(null, new PrintWriter(new StringWriter()), 1468 new String[]{WifiMetrics.PROTO_DUMP_ARG}); 1469 1470 // Create a connection event using only the config 1471 mWifiMetrics.startConnectionEvent(config, "Red", 1472 WifiMetricsProto.ConnectionEvent.ROAM_NONE); 1473 mWifiMetrics.endConnectionEvent( 1474 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1475 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1476 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1477 1478 dumpProtoAndDeserialize(); 1479 1480 assertEquals(WifiMetricsProto.ConnectionEvent.NOMINATOR_CARRIER, 1481 mDecodedProto.connectionEvent[0].connectionNominator); 1482 } 1483 1484 /** 1485 * Test that WifiMetrics is serializing/deserializing association time out events. 1486 */ 1487 @Test testMetricsAssociationTimedOut()1488 public void testMetricsAssociationTimedOut() throws Exception { 1489 mWifiMetrics.startConnectionEvent(null, "RED", 1490 WifiMetricsProto.ConnectionEvent.ROAM_NONE); 1491 mWifiMetrics.endConnectionEvent( 1492 WifiMetrics.ConnectionEvent.FAILURE_ASSOCIATION_TIMED_OUT, 1493 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1494 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1495 1496 //Dump proto and deserialize 1497 //This should clear all the metrics in mWifiMetrics, 1498 dumpProtoAndDeserialize(); 1499 //Check there is only 1 connection events 1500 assertEquals(1, mDecodedProto.connectionEvent.length); 1501 assertEquals(WifiMetrics.ConnectionEvent.FAILURE_ASSOCIATION_TIMED_OUT, 1502 mDecodedProto.connectionEvent[0].level2FailureCode); 1503 assertEquals(WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN, 1504 mDecodedProto.connectionEvent[0].level2FailureReason); 1505 } 1506 1507 /** 1508 * Test that WifiMetrics is serializing/deserializing authentication failure events. 1509 */ 1510 @Test testMetricsAuthenticationFailureReason()1511 public void testMetricsAuthenticationFailureReason() throws Exception { 1512 mWifiMetrics.startConnectionEvent(null, "RED", 1513 WifiMetricsProto.ConnectionEvent.ROAM_NONE); 1514 mWifiMetrics.endConnectionEvent( 1515 WifiMetrics.ConnectionEvent.FAILURE_AUTHENTICATION_FAILURE, 1516 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1517 WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_WRONG_PSWD); 1518 1519 //Dump proto and deserialize 1520 //This should clear all the metrics in mWifiMetrics, 1521 dumpProtoAndDeserialize(); 1522 //Check there is only 1 connection events 1523 assertEquals(1, mDecodedProto.connectionEvent.length); 1524 assertEquals(WifiMetrics.ConnectionEvent.FAILURE_AUTHENTICATION_FAILURE, 1525 mDecodedProto.connectionEvent[0].level2FailureCode); 1526 //Check the authentication failure reason 1527 assertEquals(WifiMetricsProto.ConnectionEvent.AUTH_FAILURE_WRONG_PSWD, 1528 mDecodedProto.connectionEvent[0].level2FailureReason); 1529 } 1530 1531 /** 1532 * Test that WifiMetrics is being cleared after dumping via proto 1533 */ 1534 @Test testMetricsClearedAfterProtoRequested()1535 public void testMetricsClearedAfterProtoRequested() throws Exception { 1536 // Create 3 ConnectionEvents 1537 mWifiMetrics.startConnectionEvent(null, "RED", 1538 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1539 mWifiMetrics.endConnectionEvent( 1540 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1541 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1542 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1543 mWifiMetrics.startConnectionEvent(null, "YELLOW", 1544 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1545 mWifiMetrics.endConnectionEvent( 1546 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1547 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1548 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1549 mWifiMetrics.startConnectionEvent(null, "GREEN", 1550 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1551 mWifiMetrics.endConnectionEvent( 1552 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1553 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1554 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1555 mWifiMetrics.startConnectionEvent(null, "ORANGE", 1556 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1557 mWifiMetrics.endConnectionEvent( 1558 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1559 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1560 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1561 1562 //Dump proto and deserialize 1563 //This should clear all the metrics in mWifiMetrics, 1564 dumpProtoAndDeserialize(); 1565 //Check there are 4 connection events 1566 assertEquals(4, mDecodedProto.connectionEvent.length); 1567 assertEquals(0, mDecodedProto.rssiPollRssiCount.length); 1568 assertEquals(0, mDecodedProto.alertReasonCount.length); 1569 1570 // Create 2 ConnectionEvents 1571 mWifiMetrics.startConnectionEvent(null, "BLUE", 1572 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1573 mWifiMetrics.endConnectionEvent( 1574 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1575 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1576 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1577 mWifiMetrics.startConnectionEvent(null, "RED", 1578 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1579 mWifiMetrics.endConnectionEvent( 1580 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1581 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1582 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1583 1584 //Dump proto and deserialize 1585 dumpProtoAndDeserialize(); 1586 //Check there are only 2 connection events 1587 assertEquals(2, mDecodedProto.connectionEvent.length); 1588 } 1589 1590 /** 1591 * Test that current ongoing ConnectionEvent is not cleared and logged 1592 * when proto is dumped 1593 */ 1594 @Test testCurrentConnectionEventNotClearedAfterProtoRequested()1595 public void testCurrentConnectionEventNotClearedAfterProtoRequested() throws Exception { 1596 // Create 2 complete ConnectionEvents and 1 ongoing un-ended ConnectionEvent 1597 mWifiMetrics.startConnectionEvent(null, "RED", 1598 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1599 mWifiMetrics.endConnectionEvent( 1600 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1601 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1602 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1603 mWifiMetrics.startConnectionEvent(null, "YELLOW", 1604 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1605 mWifiMetrics.endConnectionEvent( 1606 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1607 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1608 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1609 mWifiMetrics.startConnectionEvent(null, "GREEN", 1610 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 1611 1612 // Dump proto and deserialize 1613 // This should clear the metrics in mWifiMetrics, 1614 dumpProtoAndDeserialize(); 1615 assertEquals(2, mDecodedProto.connectionEvent.length); 1616 1617 // End the ongoing ConnectionEvent 1618 mWifiMetrics.endConnectionEvent( 1619 WifiMetrics.ConnectionEvent.FAILURE_NONE, 1620 WifiMetricsProto.ConnectionEvent.HLF_NONE, 1621 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 1622 1623 dumpProtoAndDeserialize(); 1624 assertEquals(1, mDecodedProto.connectionEvent.length); 1625 } 1626 1627 /** 1628 * Tests that after setting metrics values they can be serialized and deserialized with the 1629 * $ adb shell dumpsys wifi wifiMetricsProto clean 1630 */ 1631 @Test testClearMetricsDump()1632 public void testClearMetricsDump() throws Exception { 1633 setAndIncrementMetrics(); 1634 startAndEndConnectionEventSucceeds(); 1635 cleanDumpProtoAndDeserialize(); 1636 assertDeserializedMetricsCorrect(); 1637 assertEquals("mDecodedProto.connectionEvent.length", 1638 2, mDecodedProto.connectionEvent.length); 1639 } 1640 1641 private static final int NUM_REPEATED_DELTAS = 7; 1642 private static final int REPEATED_DELTA = 0; 1643 private static final int SINGLE_GOOD_DELTA = 1; 1644 private static final int SINGLE_TIMEOUT_DELTA = 2; 1645 private static final int NUM_REPEATED_BOUND_DELTAS = 2; 1646 private static final int MAX_DELTA_LEVEL = 127; 1647 private static final int MIN_DELTA_LEVEL = -127; 1648 private static final int ARBITRARY_DELTA_LEVEL = 20; 1649 1650 /** 1651 * Sunny day RSSI delta logging scenario. 1652 * Logs one rssi delta value multiple times 1653 * Logs a different delta value a single time 1654 */ 1655 @Test testRssiDeltasSuccessfulLogging()1656 public void testRssiDeltasSuccessfulLogging() throws Exception { 1657 // Generate some repeated deltas 1658 for (int i = 0; i < NUM_REPEATED_DELTAS; i++) { 1659 generateRssiDelta(MIN_RSSI_LEVEL, REPEATED_DELTA, 1660 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS); 1661 } 1662 // Generate a single delta 1663 generateRssiDelta(MIN_RSSI_LEVEL, SINGLE_GOOD_DELTA, 1664 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS); 1665 dumpProtoAndDeserialize(); 1666 assertEquals(2, mDecodedProto.rssiPollDeltaCount.length); 1667 // Check the repeated deltas 1668 assertEquals(NUM_REPEATED_DELTAS, mDecodedProto.rssiPollDeltaCount[0].count); 1669 assertEquals(REPEATED_DELTA, mDecodedProto.rssiPollDeltaCount[0].rssi); 1670 // Check the single delta 1671 assertEquals(1, mDecodedProto.rssiPollDeltaCount[1].count); 1672 assertEquals(SINGLE_GOOD_DELTA, mDecodedProto.rssiPollDeltaCount[1].rssi); 1673 } 1674 1675 /** 1676 * Tests that Rssi Delta events whose scanResult and Rssi Poll come too far apart, timeout, 1677 * and are not logged. 1678 */ 1679 @Test testRssiDeltasTimeout()1680 public void testRssiDeltasTimeout() throws Exception { 1681 // Create timed out rssi deltas 1682 generateRssiDelta(MIN_RSSI_LEVEL, REPEATED_DELTA, 1683 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS + 1); 1684 generateRssiDelta(MIN_RSSI_LEVEL, SINGLE_TIMEOUT_DELTA, 1685 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS + 1); 1686 dumpProtoAndDeserialize(); 1687 assertEquals(0, mDecodedProto.rssiPollDeltaCount.length); 1688 } 1689 1690 /** 1691 * Tests the exact inclusive boundaries of RSSI delta logging. 1692 */ 1693 @Test testRssiDeltaSuccessfulLoggingExactBounds()1694 public void testRssiDeltaSuccessfulLoggingExactBounds() throws Exception { 1695 generateRssiDelta(MIN_RSSI_LEVEL, MAX_DELTA_LEVEL, 1696 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS); 1697 generateRssiDelta(MAX_RSSI_LEVEL, MIN_DELTA_LEVEL, 1698 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS); 1699 dumpProtoAndDeserialize(); 1700 assertEquals(2, mDecodedProto.rssiPollDeltaCount.length); 1701 assertEquals(MIN_DELTA_LEVEL, mDecodedProto.rssiPollDeltaCount[0].rssi); 1702 assertEquals(1, mDecodedProto.rssiPollDeltaCount[0].count); 1703 assertEquals(MAX_DELTA_LEVEL, mDecodedProto.rssiPollDeltaCount[1].rssi); 1704 assertEquals(1, mDecodedProto.rssiPollDeltaCount[1].count); 1705 } 1706 1707 /** 1708 * Tests the exact exclusive boundaries of RSSI delta logging. 1709 * This test ensures that too much data is not generated. 1710 */ 1711 @Test testRssiDeltaOutOfBounds()1712 public void testRssiDeltaOutOfBounds() throws Exception { 1713 generateRssiDelta(MIN_RSSI_LEVEL, MAX_DELTA_LEVEL + 1, 1714 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS); 1715 generateRssiDelta(MAX_RSSI_LEVEL, MIN_DELTA_LEVEL - 1, 1716 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS); 1717 dumpProtoAndDeserialize(); 1718 assertEquals(0, mDecodedProto.rssiPollDeltaCount.length); 1719 } 1720 1721 /** 1722 * This test ensures no rssi Delta is logged after an unsuccessful ConnectionEvent 1723 */ 1724 @Test testUnsuccesfulConnectionEventRssiDeltaIsNotLogged()1725 public void testUnsuccesfulConnectionEventRssiDeltaIsNotLogged() throws Exception { 1726 generateRssiDelta(MIN_RSSI_LEVEL, ARBITRARY_DELTA_LEVEL, 1727 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS, 1728 false, // successfulConnectionEvent 1729 true, // completeConnectionEvent 1730 true, // useValidScanResult 1731 true // dontDeserializeBeforePoll 1732 ); 1733 1734 dumpProtoAndDeserialize(); 1735 assertEquals(0, mDecodedProto.rssiPollDeltaCount.length); 1736 } 1737 1738 /** 1739 * This test ensures rssi Deltas can be logged during a ConnectionEvent 1740 */ 1741 @Test testIncompleteConnectionEventRssiDeltaIsLogged()1742 public void testIncompleteConnectionEventRssiDeltaIsLogged() throws Exception { 1743 generateRssiDelta(MIN_RSSI_LEVEL, ARBITRARY_DELTA_LEVEL, 1744 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS, 1745 true, // successfulConnectionEvent 1746 false, // completeConnectionEvent 1747 true, // useValidScanResult 1748 true // dontDeserializeBeforePoll 1749 ); 1750 dumpProtoAndDeserialize(); 1751 assertEquals(1, mDecodedProto.rssiPollDeltaCount.length); 1752 assertEquals(ARBITRARY_DELTA_LEVEL, mDecodedProto.rssiPollDeltaCount[0].rssi); 1753 assertEquals(1, mDecodedProto.rssiPollDeltaCount[0].count); 1754 } 1755 1756 /** 1757 * This test ensures that no delta is logged for a null ScanResult Candidate 1758 */ 1759 @Test testRssiDeltaNotLoggedForNullCandidateScanResult()1760 public void testRssiDeltaNotLoggedForNullCandidateScanResult() throws Exception { 1761 generateRssiDelta(MIN_RSSI_LEVEL, ARBITRARY_DELTA_LEVEL, 1762 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS, 1763 true, // successfulConnectionEvent 1764 true, // completeConnectionEvent 1765 false, // useValidScanResult 1766 true // dontDeserializeBeforePoll 1767 ); 1768 dumpProtoAndDeserialize(); 1769 assertEquals(0, mDecodedProto.rssiPollDeltaCount.length); 1770 } 1771 1772 /** 1773 * This test ensures that Rssi Deltas are not logged over a 'clear()' call (Metrics Serialized) 1774 */ 1775 @Test testMetricsSerializedDuringRssiDeltaEventLogsNothing()1776 public void testMetricsSerializedDuringRssiDeltaEventLogsNothing() throws Exception { 1777 generateRssiDelta(MIN_RSSI_LEVEL, ARBITRARY_DELTA_LEVEL, 1778 WifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS, 1779 true, // successfulConnectionEvent 1780 true, // completeConnectionEvent 1781 true, // useValidScanResult 1782 false // dontDeserializeBeforePoll 1783 ); 1784 dumpProtoAndDeserialize(); 1785 assertEquals(0, mDecodedProto.rssiPollDeltaCount.length); 1786 } 1787 1788 private static final int DEAUTH_REASON = 7; 1789 private static final int ASSOC_STATUS = 11; 1790 private static final int ASSOC_TIMEOUT = 1; 1791 private static final int LOCAL_GEN = 1; 1792 private static final int AUTH_FAILURE_REASON = WifiManager.ERROR_AUTH_FAILURE_WRONG_PSWD; 1793 private static final int NUM_TEST_STA_EVENTS = 19; 1794 private static final String sSSID = "\"SomeTestSsid\""; 1795 private static final WifiSsid sWifiSsid = WifiSsid.createFromAsciiEncoded(sSSID); 1796 private static final String sBSSID = "01:02:03:04:05:06"; 1797 1798 private final StateChangeResult mStateDisconnected = 1799 new StateChangeResult(0, sWifiSsid, sBSSID, SupplicantState.DISCONNECTED); 1800 private final StateChangeResult mStateCompleted = 1801 new StateChangeResult(0, sWifiSsid, sBSSID, SupplicantState.COMPLETED); 1802 // Test bitmasks of supplicant state changes 1803 private final int mSupBm1 = WifiMetrics.supplicantStateToBit(mStateDisconnected.state); 1804 private final int mSupBm2 = WifiMetrics.supplicantStateToBit(mStateDisconnected.state) 1805 | WifiMetrics.supplicantStateToBit(mStateCompleted.state); 1806 // An invalid but interesting wifiConfiguration that exercises the StaEvent.ConfigInfo encoding 1807 private final WifiConfiguration mTestWifiConfig = createComplexWifiConfig(); 1808 // <msg.what> <msg.arg1> <msg.arg2> 1809 private int[][] mTestStaMessageInts = { 1810 {WifiMonitor.ASSOCIATION_REJECTION_EVENT, ASSOC_TIMEOUT, ASSOC_STATUS}, 1811 {WifiMonitor.AUTHENTICATION_FAILURE_EVENT, AUTH_FAILURE_REASON, -1}, 1812 {WifiMonitor.NETWORK_CONNECTION_EVENT, 0, 0}, 1813 {WifiMonitor.NETWORK_DISCONNECTION_EVENT, LOCAL_GEN, DEAUTH_REASON}, 1814 {WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT, 0, 0}, 1815 {ClientModeImpl.CMD_ASSOCIATED_BSSID, 0, 0}, 1816 {ClientModeImpl.CMD_TARGET_BSSID, 0, 0}, 1817 {WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT, 0, 0}, 1818 {WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT, 0, 0} 1819 }; 1820 private Object[] mTestStaMessageObjs = { 1821 null, 1822 null, 1823 null, 1824 null, 1825 mStateDisconnected, 1826 null, 1827 null, 1828 mStateDisconnected, 1829 mStateCompleted 1830 }; 1831 // Values used to generate the StaEvent log calls from ClientModeImpl 1832 // <StaEvent.Type>, <StaEvent.FrameworkDisconnectReason>, <1|0>(testWifiConfiguration, null) 1833 private int[][] mTestStaLogInts = { 1834 {StaEvent.TYPE_CMD_IP_CONFIGURATION_SUCCESSFUL, 0, 0}, 1835 {StaEvent.TYPE_CMD_IP_CONFIGURATION_LOST, 0, 0}, 1836 {StaEvent.TYPE_CMD_IP_REACHABILITY_LOST, 0, 0}, 1837 {StaEvent.TYPE_CMD_START_CONNECT, 0, 1}, 1838 {StaEvent.TYPE_CMD_START_ROAM, 0, 1}, 1839 {StaEvent.TYPE_CONNECT_NETWORK, 0, 1}, 1840 {StaEvent.TYPE_NETWORK_AGENT_VALID_NETWORK, 0, 0}, 1841 {StaEvent.TYPE_FRAMEWORK_DISCONNECT, StaEvent.DISCONNECT_API, 0}, 1842 {StaEvent.TYPE_SCORE_BREACH, 0, 0}, 1843 {StaEvent.TYPE_MAC_CHANGE, 0, 1}, 1844 {StaEvent.TYPE_WIFI_ENABLED, 0, 0}, 1845 {StaEvent.TYPE_WIFI_DISABLED, 0, 0}, 1846 {StaEvent.TYPE_WIFI_USABILITY_SCORE_BREACH, 0, 0} 1847 }; 1848 // Values used to generate the StaEvent log calls from WifiMonitor 1849 // <type>, <reason>, <status>, <local_gen>, 1850 // <auth_fail_reason>, <assoc_timed_out> <supplicantStateChangeBitmask> <1|0>(has ConfigInfo) 1851 private int[][] mExpectedValues = { 1852 {StaEvent.TYPE_ASSOCIATION_REJECTION_EVENT, -1, ASSOC_STATUS, 0, 1853 /**/ 0, ASSOC_TIMEOUT, 0, 0}, /**/ 1854 {StaEvent.TYPE_AUTHENTICATION_FAILURE_EVENT, -1, -1, 0, 1855 /**/StaEvent.AUTH_FAILURE_WRONG_PSWD, 0, 0, 0}, /**/ 1856 {StaEvent.TYPE_NETWORK_CONNECTION_EVENT, -1, -1, 0, 1857 /**/ 0, 0, 0, 0}, /**/ 1858 {StaEvent.TYPE_NETWORK_DISCONNECTION_EVENT, DEAUTH_REASON, -1, LOCAL_GEN, 1859 /**/ 0, 0, 0, 0}, /**/ 1860 {StaEvent.TYPE_CMD_ASSOCIATED_BSSID, -1, -1, 0, 1861 /**/ 0, 0, mSupBm1, 0}, /**/ 1862 {StaEvent.TYPE_CMD_TARGET_BSSID, -1, -1, 0, 1863 /**/ 0, 0, 0, 0}, /**/ 1864 {StaEvent.TYPE_CMD_IP_CONFIGURATION_SUCCESSFUL, -1, -1, 0, 1865 /**/ 0, 0, mSupBm2, 0}, /**/ 1866 {StaEvent.TYPE_CMD_IP_CONFIGURATION_LOST, -1, -1, 0, 1867 /**/ 0, 0, 0, 0}, /**/ 1868 {StaEvent.TYPE_CMD_IP_REACHABILITY_LOST, -1, -1, 0, 1869 /**/ 0, 0, 0, 0}, /**/ 1870 {StaEvent.TYPE_CMD_START_CONNECT, -1, -1, 0, 1871 /**/ 0, 0, 0, 1}, /**/ 1872 {StaEvent.TYPE_CMD_START_ROAM, -1, -1, 0, 1873 /**/ 0, 0, 0, 1}, /**/ 1874 {StaEvent.TYPE_CONNECT_NETWORK, -1, -1, 0, 1875 /**/ 0, 0, 0, 1}, /**/ 1876 {StaEvent.TYPE_NETWORK_AGENT_VALID_NETWORK, -1, -1, 0, 1877 /**/ 0, 0, 0, 0}, /**/ 1878 {StaEvent.TYPE_FRAMEWORK_DISCONNECT, -1, -1, 0, 1879 /**/ 0, 0, 0, 0}, /**/ 1880 {StaEvent.TYPE_SCORE_BREACH, -1, -1, 0, 1881 /**/ 0, 0, 0, 0}, /**/ 1882 {StaEvent.TYPE_MAC_CHANGE, -1, -1, 0, 1883 /**/ 0, 0, 0, 1}, /**/ 1884 {StaEvent.TYPE_WIFI_ENABLED, -1, -1, 0, 1885 /**/ 0, 0, 0, 0}, /**/ 1886 {StaEvent.TYPE_WIFI_DISABLED, -1, -1, 0, 1887 /**/ 0, 0, 0, 0}, /**/ 1888 {StaEvent.TYPE_WIFI_USABILITY_SCORE_BREACH, -1, -1, 0, 1889 /**/ 0, 0, 0, 0} /**/ 1890 }; 1891 1892 /** 1893 * Generates events from all the rows in mTestStaMessageInts, and then mTestStaLogInts 1894 */ generateStaEvents(WifiMetrics wifiMetrics)1895 private void generateStaEvents(WifiMetrics wifiMetrics) { 1896 Handler handler = wifiMetrics.getHandler(); 1897 for (int i = 0; i < mTestStaMessageInts.length; i++) { 1898 int[] mia = mTestStaMessageInts[i]; 1899 handler.sendMessage( 1900 handler.obtainMessage(mia[0], mia[1], mia[2], mTestStaMessageObjs[i])); 1901 } 1902 mTestLooper.dispatchAll(); 1903 for (int i = 0; i < mTestStaLogInts.length; i++) { 1904 int[] lia = mTestStaLogInts[i]; 1905 wifiMetrics.logStaEvent(lia[0], lia[1], lia[2] == 1 ? mTestWifiConfig : null); 1906 } 1907 } verifyDeserializedStaEvents(WifiMetricsProto.WifiLog wifiLog)1908 private void verifyDeserializedStaEvents(WifiMetricsProto.WifiLog wifiLog) { 1909 assertNotNull(mTestWifiConfig); 1910 assertEquals(NUM_TEST_STA_EVENTS, wifiLog.staEventList.length); 1911 int j = 0; // De-serialized event index 1912 for (int i = 0; i < mTestStaMessageInts.length; i++) { 1913 StaEvent event = wifiLog.staEventList[j]; 1914 int[] mia = mTestStaMessageInts[i]; 1915 int[] evs = mExpectedValues[j]; 1916 if (mia[0] != WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT) { 1917 assertEquals(evs[0], event.type); 1918 assertEquals(evs[1], event.reason); 1919 assertEquals(evs[2], event.status); 1920 assertEquals(evs[3] == 1 ? true : false, event.localGen); 1921 assertEquals(evs[4], event.authFailureReason); 1922 assertEquals(evs[5] == 1 ? true : false, event.associationTimedOut); 1923 assertEquals(evs[6], event.supplicantStateChangesBitmask); 1924 assertConfigInfoEqualsWifiConfig( 1925 evs[7] == 1 ? mTestWifiConfig : null, event.configInfo); 1926 j++; 1927 } 1928 } 1929 for (int i = 0; i < mTestStaLogInts.length; i++) { 1930 StaEvent event = wifiLog.staEventList[j]; 1931 int[] evs = mExpectedValues[j]; 1932 assertEquals(evs[0], event.type); 1933 assertEquals(evs[1], event.reason); 1934 assertEquals(evs[2], event.status); 1935 assertEquals(evs[3] == 1 ? true : false, event.localGen); 1936 assertEquals(evs[4], event.authFailureReason); 1937 assertEquals(evs[5] == 1 ? true : false, event.associationTimedOut); 1938 assertEquals(evs[6], event.supplicantStateChangesBitmask); 1939 assertConfigInfoEqualsWifiConfig( 1940 evs[7] == 1 ? mTestWifiConfig : null, event.configInfo); 1941 j++; 1942 } 1943 assertEquals(mExpectedValues.length, j); 1944 } 1945 1946 /** 1947 * Generate StaEvents of each type, ensure all the different values are logged correctly, 1948 * and that they survive serialization & de-serialization 1949 */ 1950 @Test testStaEventsLogSerializeDeserialize()1951 public void testStaEventsLogSerializeDeserialize() throws Exception { 1952 generateStaEvents(mWifiMetrics); 1953 dumpProtoAndDeserialize(); 1954 verifyDeserializedStaEvents(mDecodedProto); 1955 } 1956 1957 /** 1958 * Ensure the number of StaEvents does not exceed MAX_STA_EVENTS by generating lots of events 1959 * and checking how many are deserialized 1960 */ 1961 @Test testStaEventBounding()1962 public void testStaEventBounding() throws Exception { 1963 for (int i = 0; i < (WifiMetrics.MAX_STA_EVENTS + 10); i++) { 1964 mWifiMetrics.logStaEvent(StaEvent.TYPE_CMD_START_CONNECT); 1965 } 1966 dumpProtoAndDeserialize(); 1967 assertEquals(WifiMetrics.MAX_STA_EVENTS, mDecodedProto.staEventList.length); 1968 } 1969 1970 /** 1971 * Tests that link probe StaEvents do not exceed 1972 * {@link WifiMetrics#MAX_LINK_PROBE_STA_EVENTS}. 1973 */ 1974 @Test testLinkProbeStaEventBounding()1975 public void testLinkProbeStaEventBounding() throws Exception { 1976 for (int i = 0; i < WifiMetrics.MAX_LINK_PROBE_STA_EVENTS; i++) { 1977 mWifiMetrics.logLinkProbeSuccess(0, 0, 0, 0); 1978 mWifiMetrics.logLinkProbeFailure(0, 0, 0, 0); 1979 } 1980 for (int i = 0; i < 10; i++) { 1981 mWifiMetrics.logStaEvent(StaEvent.TYPE_CMD_START_CONNECT); 1982 } 1983 1984 dumpProtoAndDeserialize(); 1985 1986 long numLinkProbeStaEvents = Arrays.stream(mDecodedProto.staEventList) 1987 .filter(event -> event.type == TYPE_LINK_PROBE) 1988 .count(); 1989 assertEquals(WifiMetrics.MAX_LINK_PROBE_STA_EVENTS, numLinkProbeStaEvents); 1990 assertEquals(WifiMetrics.MAX_LINK_PROBE_STA_EVENTS + 10, mDecodedProto.staEventList.length); 1991 } 1992 1993 /** 1994 * Ensure WifiMetrics doesn't cause a null pointer exception when called with null args 1995 */ 1996 @Test testDumpNullArg()1997 public void testDumpNullArg() { 1998 mWifiMetrics.dump(new FileDescriptor(), new PrintWriter(new StringWriter()), null); 1999 } 2000 2001 /** 2002 * Test the generation of 'NumConnectableNetwork' histograms from two scans of different 2003 * ScanDetails produces the correct histogram values, and relevant bounds are observed 2004 */ 2005 @MediumTest 2006 @Test testNumConnectableNetworksGeneration()2007 public void testNumConnectableNetworksGeneration() throws Exception { 2008 List<ScanDetail> scan = new ArrayList<ScanDetail>(); 2009 // ssid, bssid, isOpen, isSaved, isProvider, isWeakRssi) 2010 scan.add(buildMockScanDetail("PASSPOINT_1", "bssid0", false, false, true, false)); 2011 scan.add(buildMockScanDetail("PASSPOINT_2", "bssid1", false, false, true, false)); 2012 scan.add(buildMockScanDetail("SSID_B", "bssid2", true, true, false, false)); 2013 scan.add(buildMockScanDetail("SSID_B", "bssid3", true, true, false, false)); 2014 scan.add(buildMockScanDetail("SSID_C", "bssid4", true, false, false, false)); 2015 scan.add(buildMockScanDetail("SSID_D", "bssid5", false, true, false, false)); 2016 scan.add(buildMockScanDetail("SSID_E", "bssid6", false, true, false, false)); 2017 scan.add(buildMockScanDetail("SSID_F", "bssid7", false, false, false, false)); 2018 scan.add(buildMockScanDetail("SSID_G_WEAK", "bssid9", false, false, false, true)); 2019 scan.add(buildMockScanDetail("SSID_H_WEAK", "bssid10", false, false, false, true)); 2020 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2021 scan.add(buildMockScanDetail("SSID_B", "bssid8", true, true, false, false)); 2022 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2023 for (int i = 0; i < NUM_PARTIAL_SCAN_RESULTS; i++) { 2024 mWifiMetrics.incrementAvailableNetworksHistograms(scan, false); 2025 } 2026 dumpProtoAndDeserialize(); 2027 verifyHist(mDecodedProto.totalSsidsInScanHistogram, 1, a(7), a(2)); 2028 verifyHist(mDecodedProto.totalBssidsInScanHistogram, 2, a(8, 9), a(1, 1)); 2029 verifyHist(mDecodedProto.availableOpenSsidsInScanHistogram, 1, a(2), a(2)); 2030 verifyHist(mDecodedProto.availableOpenBssidsInScanHistogram, 2, a(3, 4), a(1, 1)); 2031 verifyHist(mDecodedProto.availableSavedSsidsInScanHistogram, 1, a(3), a(2)); 2032 verifyHist(mDecodedProto.availableSavedBssidsInScanHistogram, 2, a(4, 5), a(1, 1)); 2033 verifyHist(mDecodedProto.availableOpenOrSavedSsidsInScanHistogram, 1, a(4), a(2)); 2034 verifyHist(mDecodedProto.availableOpenOrSavedBssidsInScanHistogram, 2, a(5, 6), a(1, 1)); 2035 verifyHist(mDecodedProto.availableSavedPasspointProviderProfilesInScanHistogram, 1, 2036 a(2), a(2)); 2037 verifyHist(mDecodedProto.availableSavedPasspointProviderBssidsInScanHistogram, 1, 2038 a(2), a(2)); 2039 assertEquals(2, mDecodedProto.fullBandAllSingleScanListenerResults); 2040 assertEquals(NUM_PARTIAL_SCAN_RESULTS, mDecodedProto.partialAllSingleScanListenerResults); 2041 2042 // Check Bounds 2043 scan.clear(); 2044 int lotsOfSSids = Math.max(WifiMetrics.MAX_TOTAL_SCAN_RESULT_SSIDS_BUCKET, 2045 WifiMetrics.MAX_CONNECTABLE_SSID_NETWORK_BUCKET) + 5; 2046 for (int i = 0; i < lotsOfSSids; i++) { 2047 scan.add(buildMockScanDetail("SSID_" + i, "bssid_" + i, true, true, false, false)); 2048 } 2049 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2050 dumpProtoAndDeserialize(); 2051 verifyHist(mDecodedProto.totalSsidsInScanHistogram, 1, 2052 a(WifiMetrics.MAX_TOTAL_SCAN_RESULT_SSIDS_BUCKET), a(1)); 2053 verifyHist(mDecodedProto.availableOpenSsidsInScanHistogram, 1, 2054 a(WifiMetrics.MAX_CONNECTABLE_SSID_NETWORK_BUCKET), a(1)); 2055 verifyHist(mDecodedProto.availableSavedSsidsInScanHistogram, 1, 2056 a(WifiMetrics.MAX_CONNECTABLE_SSID_NETWORK_BUCKET), a(1)); 2057 verifyHist(mDecodedProto.availableOpenOrSavedSsidsInScanHistogram, 1, 2058 a(WifiMetrics.MAX_CONNECTABLE_SSID_NETWORK_BUCKET), a(1)); 2059 scan.clear(); 2060 int lotsOfBssids = Math.max(WifiMetrics.MAX_TOTAL_SCAN_RESULTS_BUCKET, 2061 WifiMetrics.MAX_CONNECTABLE_BSSID_NETWORK_BUCKET) + 5; 2062 for (int i = 0; i < lotsOfBssids; i++) { 2063 scan.add(buildMockScanDetail("SSID", "bssid_" + i, true, true, false, false)); 2064 } 2065 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2066 dumpProtoAndDeserialize(); 2067 verifyHist(mDecodedProto.totalBssidsInScanHistogram, 1, 2068 a(WifiMetrics.MAX_TOTAL_SCAN_RESULTS_BUCKET), a(1)); 2069 verifyHist(mDecodedProto.availableOpenBssidsInScanHistogram, 1, 2070 a(WifiMetrics.MAX_CONNECTABLE_BSSID_NETWORK_BUCKET), a(1)); 2071 verifyHist(mDecodedProto.availableSavedBssidsInScanHistogram, 1, 2072 a(WifiMetrics.MAX_CONNECTABLE_BSSID_NETWORK_BUCKET), a(1)); 2073 verifyHist(mDecodedProto.availableOpenOrSavedBssidsInScanHistogram, 1, 2074 a(WifiMetrics.MAX_CONNECTABLE_BSSID_NETWORK_BUCKET), a(1)); 2075 } 2076 2077 /** 2078 * Test that Hotspot 2.0 (Passpoint) scan results are collected correctly and that relevant 2079 * bounds are observed. 2080 */ 2081 @Test testObservedHotspotAps()2082 public void testObservedHotspotAps() throws Exception { 2083 List<ScanDetail> scan = new ArrayList<ScanDetail>(); 2084 // 2 R1 (Unknown AP isn't counted) passpoint APs belonging to a single provider: hessid1 2085 long hessid1 = 10; 2086 int anqpDomainId1 = 5; 2087 scan.add(buildMockScanDetailPasspoint("PASSPOINT_XX", "00:02:03:04:05:06", hessid1, 2088 anqpDomainId1, NetworkDetail.HSRelease.R1, true)); 2089 scan.add(buildMockScanDetailPasspoint("PASSPOINT_XY", "01:02:03:04:05:06", hessid1, 2090 anqpDomainId1, NetworkDetail.HSRelease.R1, true)); 2091 scan.add(buildMockScanDetailPasspoint("PASSPOINT_XYZ", "02:02:03:04:05:06", hessid1, 2092 anqpDomainId1, NetworkDetail.HSRelease.Unknown, true)); 2093 // 2 R2 passpoint APs belonging to a single provider: hessid2 2094 long hessid2 = 12; 2095 int anqpDomainId2 = 6; 2096 scan.add(buildMockScanDetailPasspoint("PASSPOINT_Y", "AA:02:03:04:05:06", hessid2, 2097 anqpDomainId2, NetworkDetail.HSRelease.R2, true)); 2098 scan.add(buildMockScanDetailPasspoint("PASSPOINT_Z", "AB:02:03:04:05:06", hessid2, 2099 anqpDomainId2, NetworkDetail.HSRelease.R2, true)); 2100 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2101 scan = new ArrayList<ScanDetail>(); 2102 // 3 R2 passpoint APs belonging to a single provider: hessid3 (in next scan) 2103 long hessid3 = 15; 2104 int anqpDomainId3 = 8; 2105 scan.add(buildMockScanDetailPasspoint("PASSPOINT_Y", "AA:02:03:04:05:06", hessid3, 2106 anqpDomainId3, NetworkDetail.HSRelease.R2, true)); 2107 scan.add(buildMockScanDetailPasspoint("PASSPOINT_Y", "AA:02:03:04:05:06", hessid3, 2108 anqpDomainId3, NetworkDetail.HSRelease.R2, false)); 2109 scan.add(buildMockScanDetailPasspoint("PASSPOINT_Z", "AB:02:03:04:05:06", hessid3, 2110 anqpDomainId3, NetworkDetail.HSRelease.R2, true)); 2111 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2112 dumpProtoAndDeserialize(); 2113 2114 verifyHist(mDecodedProto.observedHotspotR1ApsInScanHistogram, 2, a(0, 2), a(1, 1)); 2115 verifyHist(mDecodedProto.observedHotspotR2ApsInScanHistogram, 2, a(2, 3), a(1, 1)); 2116 verifyHist(mDecodedProto.observedHotspotR1EssInScanHistogram, 2, a(0, 1), a(1, 1)); 2117 verifyHist(mDecodedProto.observedHotspotR2EssInScanHistogram, 1, a(1), a(2)); 2118 verifyHist(mDecodedProto.observedHotspotR1ApsPerEssInScanHistogram, 1, a(2), a(1)); 2119 verifyHist(mDecodedProto.observedHotspotR2ApsPerEssInScanHistogram, 2, a(2, 3), a(1, 1)); 2120 2121 // check bounds 2122 scan.clear(); 2123 int lotsOfSSids = Math.max(WifiMetrics.MAX_TOTAL_PASSPOINT_APS_BUCKET, 2124 WifiMetrics.MAX_TOTAL_PASSPOINT_UNIQUE_ESS_BUCKET) + 5; 2125 for (int i = 0; i < lotsOfSSids; i++) { 2126 scan.add(buildMockScanDetailPasspoint("PASSPOINT_XX" + i, "00:02:03:04:05:06", i, 2127 i + 10, NetworkDetail.HSRelease.R1, true)); 2128 scan.add(buildMockScanDetailPasspoint("PASSPOINT_XY" + i, "AA:02:03:04:05:06", 1000 * i, 2129 i + 10, NetworkDetail.HSRelease.R2, false)); 2130 } 2131 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2132 dumpProtoAndDeserialize(); 2133 verifyHist(mDecodedProto.observedHotspotR1ApsInScanHistogram, 1, 2134 a(WifiMetrics.MAX_TOTAL_PASSPOINT_APS_BUCKET), a(1)); 2135 verifyHist(mDecodedProto.observedHotspotR2ApsInScanHistogram, 1, 2136 a(WifiMetrics.MAX_TOTAL_PASSPOINT_APS_BUCKET), a(1)); 2137 verifyHist(mDecodedProto.observedHotspotR1EssInScanHistogram, 1, 2138 a(WifiMetrics.MAX_TOTAL_PASSPOINT_UNIQUE_ESS_BUCKET), a(1)); 2139 verifyHist(mDecodedProto.observedHotspotR2EssInScanHistogram, 1, 2140 a(WifiMetrics.MAX_TOTAL_PASSPOINT_UNIQUE_ESS_BUCKET), a(1)); 2141 } 2142 2143 /** 2144 * Test that IEEE 802.11mc scan results are collected correctly and that relevant 2145 * bounds are observed. 2146 */ 2147 @Test testObserved80211mcAps()2148 public void testObserved80211mcAps() throws Exception { 2149 ScanDetail mockScanDetailNon80211mc = mock(ScanDetail.class); 2150 ScanDetail mockScanDetail80211mc = mock(ScanDetail.class); 2151 NetworkDetail mockNetworkDetailNon80211mc = mock(NetworkDetail.class); 2152 NetworkDetail mockNetworkDetail80211mc = mock(NetworkDetail.class); 2153 when(mockNetworkDetail80211mc.is80211McResponderSupport()).thenReturn(true); 2154 ScanResult mockScanResult = mock(ScanResult.class); 2155 mockScanResult.capabilities = ""; 2156 when(mockScanDetailNon80211mc.getNetworkDetail()).thenReturn(mockNetworkDetailNon80211mc); 2157 when(mockScanDetail80211mc.getNetworkDetail()).thenReturn(mockNetworkDetail80211mc); 2158 when(mockScanDetailNon80211mc.getScanResult()).thenReturn(mockScanResult); 2159 when(mockScanDetail80211mc.getScanResult()).thenReturn(mockScanResult); 2160 when(mWns.isSignalTooWeak(eq(mockScanDetail80211mc.getScanResult()))).thenReturn(true); 2161 List<ScanDetail> scan = new ArrayList<ScanDetail>(); 2162 2163 // 4 scans (a few non-802.11mc supporting APs on each) 2164 // scan1: no 802.11mc supporting APs 2165 2166 scan.add(mockScanDetailNon80211mc); 2167 scan.add(mockScanDetailNon80211mc); 2168 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2169 2170 // scan2: 2 802.11mc supporting APs 2171 scan.clear(); 2172 scan.add(mockScanDetailNon80211mc); 2173 scan.add(mockScanDetail80211mc); 2174 scan.add(mockScanDetail80211mc); 2175 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2176 2177 // scan3: 100 802.11mc supporting APs (> limit) 2178 scan.clear(); 2179 scan.add(mockScanDetailNon80211mc); 2180 scan.add(mockScanDetailNon80211mc); 2181 scan.add(mockScanDetailNon80211mc); 2182 for (int i = 0; i < 100; ++i) { 2183 scan.add(mockScanDetail80211mc); 2184 } 2185 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2186 2187 // scan4: 2 802.11mc supporting APs 2188 scan.clear(); 2189 scan.add(mockScanDetailNon80211mc); 2190 scan.add(mockScanDetail80211mc); 2191 scan.add(mockScanDetail80211mc); 2192 scan.add(mockScanDetailNon80211mc); 2193 mWifiMetrics.incrementAvailableNetworksHistograms(scan, true); 2194 2195 dumpProtoAndDeserialize(); 2196 2197 verifyHist(mDecodedProto.observed80211McSupportingApsInScanHistogram, 3, 2198 a(0, 2, WifiMetrics.MAX_TOTAL_80211MC_APS_BUCKET), a(1, 2, 1)); 2199 } 2200 2201 /** 2202 * Test Open Network Notification blocklist size and feature state are not cleared when proto 2203 * is dumped. 2204 */ 2205 @Test testOpenNetworkNotificationBlocklistSizeAndFeatureStateNotCleared()2206 public void testOpenNetworkNotificationBlocklistSizeAndFeatureStateNotCleared() 2207 throws Exception { 2208 mWifiMetrics.setNetworkRecommenderBlocklistSize(OPEN_NET_NOTIFIER_TAG, 2209 SIZE_OPEN_NETWORK_RECOMMENDER_BLOCKLIST); 2210 mWifiMetrics.setIsWifiNetworksAvailableNotificationEnabled(OPEN_NET_NOTIFIER_TAG, 2211 IS_WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON); 2212 for (int i = 0; i < NUM_OPEN_NETWORK_RECOMMENDATION_UPDATES; i++) { 2213 mWifiMetrics.incrementNumNetworkRecommendationUpdates(OPEN_NET_NOTIFIER_TAG); 2214 } 2215 2216 // This should clear most metrics in mWifiMetrics 2217 dumpProtoAndDeserialize(); 2218 assertEquals(SIZE_OPEN_NETWORK_RECOMMENDER_BLOCKLIST, 2219 mDecodedProto.openNetworkRecommenderBlacklistSize); 2220 assertEquals(IS_WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON, 2221 mDecodedProto.isWifiNetworksAvailableNotificationOn); 2222 assertEquals(NUM_OPEN_NETWORK_RECOMMENDATION_UPDATES, 2223 mDecodedProto.numOpenNetworkRecommendationUpdates); 2224 2225 // Check that blocklist size and feature state persist on next dump but 2226 // others do not. 2227 dumpProtoAndDeserialize(); 2228 assertEquals(SIZE_OPEN_NETWORK_RECOMMENDER_BLOCKLIST, 2229 mDecodedProto.openNetworkRecommenderBlacklistSize); 2230 assertEquals(IS_WIFI_NETWORKS_AVAILABLE_NOTIFICATION_ON, 2231 mDecodedProto.isWifiNetworksAvailableNotificationOn); 2232 assertEquals(0, mDecodedProto.numOpenNetworkRecommendationUpdates); 2233 } 2234 2235 /** 2236 * Check network selector id 2237 */ 2238 @Test testNetworkSelectorExperimentId()2239 public void testNetworkSelectorExperimentId() throws Exception { 2240 final int id = 42888888; 2241 mWifiMetrics.setNetworkSelectorExperimentId(id); 2242 mWifiMetrics.startConnectionEvent(mTestWifiConfig, "TestNetwork", 2243 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 2244 mWifiMetrics.endConnectionEvent( 2245 WifiMetrics.ConnectionEvent.FAILURE_NONE, 2246 WifiMetricsProto.ConnectionEvent.HLF_NONE, 2247 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 2248 dumpProtoAndDeserialize(); 2249 assertEquals(id, mDecodedProto.connectionEvent[0].networkSelectorExperimentId); 2250 } 2251 2252 /** 2253 * Check ScoringParams 2254 */ 2255 @Test testExperimentId()2256 public void testExperimentId() throws Exception { 2257 final int id = 42; 2258 final String expectId = "x" + id; 2259 when(mScoringParams.getExperimentIdentifier()).thenReturn(id); 2260 dumpProtoAndDeserialize(); 2261 assertEquals(expectId, mDecodedProto.scoreExperimentId); 2262 } 2263 2264 /** 2265 * Check ScoringParams default case 2266 */ 2267 @Test testDefaultExperimentId()2268 public void testDefaultExperimentId() throws Exception { 2269 final int id = 0; 2270 final String expectId = ""; 2271 when(mScoringParams.getExperimentIdentifier()).thenReturn(id); 2272 dumpProtoAndDeserialize(); 2273 assertEquals(expectId, mDecodedProto.scoreExperimentId); 2274 } 2275 2276 /** short hand for instantiating an anonymous int array, instead of 'new int[]{a1, a2, ...}' */ a(int... element)2277 private int[] a(int... element) { 2278 return element; 2279 } 2280 verifyHist(WifiMetricsProto.NumConnectableNetworksBucket[] hist, int size, int[] keys, int[] counts)2281 private void verifyHist(WifiMetricsProto.NumConnectableNetworksBucket[] hist, int size, 2282 int[] keys, int[] counts) throws Exception { 2283 assertEquals(size, hist.length); 2284 for (int i = 0; i < keys.length; i++) { 2285 assertEquals(keys[i], hist[i].numConnectableNetworks); 2286 assertEquals(counts[i], hist[i].count); 2287 } 2288 } 2289 2290 /** 2291 * Generate an RSSI delta event by creating a connection event and an RSSI poll within 2292 * 'interArrivalTime' milliseconds of each other. 2293 * Event will not be logged if interArrivalTime > mWifiMetrics.TIMEOUT_RSSI_DELTA_MILLIS 2294 * successfulConnectionEvent, completeConnectionEvent, useValidScanResult and 2295 * dontDeserializeBeforePoll 2296 * each create an anomalous condition when set to false. 2297 */ generateRssiDelta(int scanRssi, int rssiDelta, long interArrivalTime, boolean successfulConnectionEvent, boolean completeConnectionEvent, boolean useValidScanResult, boolean dontDeserializeBeforePoll)2298 private void generateRssiDelta(int scanRssi, int rssiDelta, 2299 long interArrivalTime, boolean successfulConnectionEvent, 2300 boolean completeConnectionEvent, boolean useValidScanResult, 2301 boolean dontDeserializeBeforePoll) throws Exception { 2302 when(mClock.getElapsedSinceBootMillis()).thenReturn((long) 0); 2303 ScanResult scanResult = null; 2304 if (useValidScanResult) { 2305 scanResult = mock(ScanResult.class); 2306 scanResult.level = scanRssi; 2307 } 2308 WifiConfiguration config = mock(WifiConfiguration.class); 2309 WifiConfiguration.NetworkSelectionStatus networkSelectionStat = 2310 mock(WifiConfiguration.NetworkSelectionStatus.class); 2311 when(networkSelectionStat.getCandidate()).thenReturn(scanResult); 2312 when(config.getNetworkSelectionStatus()).thenReturn(networkSelectionStat); 2313 mWifiMetrics.startConnectionEvent(config, "TestNetwork", 2314 WifiMetricsProto.ConnectionEvent.ROAM_ENTERPRISE); 2315 if (completeConnectionEvent) { 2316 if (successfulConnectionEvent) { 2317 mWifiMetrics.endConnectionEvent( 2318 WifiMetrics.ConnectionEvent.FAILURE_NONE, 2319 WifiMetricsProto.ConnectionEvent.HLF_NONE, 2320 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 2321 } else { 2322 mWifiMetrics.endConnectionEvent( 2323 WifiMetrics.ConnectionEvent.FAILURE_AUTHENTICATION_FAILURE, 2324 WifiMetricsProto.ConnectionEvent.HLF_NONE, 2325 WifiMetricsProto.ConnectionEvent.FAILURE_REASON_UNKNOWN); 2326 } 2327 } 2328 when(mClock.getElapsedSinceBootMillis()).thenReturn(interArrivalTime); 2329 if (!dontDeserializeBeforePoll) { 2330 dumpProtoAndDeserialize(); 2331 } 2332 mWifiMetrics.incrementRssiPollRssiCount(RSSI_POLL_FREQUENCY, scanRssi + rssiDelta); 2333 } 2334 2335 /** 2336 * Generate an RSSI delta event, with all extra conditions set to true. 2337 */ generateRssiDelta(int scanRssi, int rssiDelta, long interArrivalTime)2338 private void generateRssiDelta(int scanRssi, int rssiDelta, 2339 long interArrivalTime) throws Exception { 2340 generateRssiDelta(scanRssi, rssiDelta, interArrivalTime, true, true, true, true); 2341 } 2342 assertStringContains( String actualString, String expectedSubstring)2343 private void assertStringContains( 2344 String actualString, String expectedSubstring) { 2345 assertTrue("Expected text not found in: " + actualString, 2346 actualString.contains(expectedSubstring)); 2347 } 2348 getStateDump()2349 private String getStateDump() { 2350 ByteArrayOutputStream stream = new ByteArrayOutputStream(); 2351 PrintWriter writer = new PrintWriter(stream); 2352 String[] args = new String[0]; 2353 mWifiMetrics.dump(null, writer, args); 2354 writer.flush(); 2355 return stream.toString(); 2356 } 2357 2358 private static final int TEST_ALLOWED_KEY_MANAGEMENT = 83; 2359 private static final int TEST_ALLOWED_PROTOCOLS = 22; 2360 private static final int TEST_ALLOWED_AUTH_ALGORITHMS = 11; 2361 private static final int TEST_ALLOWED_PAIRWISE_CIPHERS = 67; 2362 private static final int TEST_ALLOWED_GROUP_CIPHERS = 231; 2363 private static final int TEST_CANDIDATE_LEVEL = -80; 2364 private static final int TEST_CANDIDATE_FREQ = 2345; 2365 createComplexWifiConfig()2366 private WifiConfiguration createComplexWifiConfig() { 2367 WifiConfiguration config = new WifiConfiguration(); 2368 config.allowedKeyManagement = intToBitSet(TEST_ALLOWED_KEY_MANAGEMENT); 2369 config.allowedProtocols = intToBitSet(TEST_ALLOWED_PROTOCOLS); 2370 config.allowedAuthAlgorithms = intToBitSet(TEST_ALLOWED_AUTH_ALGORITHMS); 2371 config.allowedPairwiseCiphers = intToBitSet(TEST_ALLOWED_PAIRWISE_CIPHERS); 2372 config.allowedGroupCiphers = intToBitSet(TEST_ALLOWED_GROUP_CIPHERS); 2373 config.hiddenSSID = true; 2374 config.ephemeral = true; 2375 config.getNetworkSelectionStatus().setHasEverConnected(true); 2376 ScanResult candidate = new ScanResult(); 2377 candidate.level = TEST_CANDIDATE_LEVEL; 2378 candidate.frequency = TEST_CANDIDATE_FREQ; 2379 config.getNetworkSelectionStatus().setCandidate(candidate); 2380 return config; 2381 } 2382 assertConfigInfoEqualsWifiConfig(WifiConfiguration config, StaEvent.ConfigInfo info)2383 private void assertConfigInfoEqualsWifiConfig(WifiConfiguration config, 2384 StaEvent.ConfigInfo info) { 2385 if (config == null && info == null) return; 2386 assertEquals(config.allowedKeyManagement, intToBitSet(info.allowedKeyManagement)); 2387 assertEquals(config.allowedProtocols, intToBitSet(info.allowedProtocols)); 2388 assertEquals(config.allowedAuthAlgorithms, intToBitSet(info.allowedAuthAlgorithms)); 2389 assertEquals(config.allowedPairwiseCiphers, intToBitSet(info.allowedPairwiseCiphers)); 2390 assertEquals(config.allowedGroupCiphers, intToBitSet(info.allowedGroupCiphers)); 2391 assertEquals(config.hiddenSSID, info.hiddenSsid); 2392 assertEquals(config.ephemeral, info.isEphemeral); 2393 assertEquals(config.getNetworkSelectionStatus().getHasEverConnected(), 2394 info.hasEverConnected); 2395 assertEquals(config.getNetworkSelectionStatus().getCandidate().level, info.scanRssi); 2396 assertEquals(config.getNetworkSelectionStatus().getCandidate().frequency, info.scanFreq); 2397 } 2398 2399 /** 2400 * Sets the values of bitSet to match an int mask 2401 */ intToBitSet(int mask)2402 private static BitSet intToBitSet(int mask) { 2403 BitSet bitSet = new BitSet(); 2404 for (int bitIndex = 0; mask > 0; mask >>>= 1, bitIndex++) { 2405 if ((mask & 1) != 0) bitSet.set(bitIndex); 2406 } 2407 return bitSet; 2408 } 2409 2410 private static final int NUM_UNUSABLE_EVENT = 5; 2411 private static final int NUM_UNUSABLE_EVENT_TIME_THROTTLE = 3; 2412 2413 /** 2414 * Values used to generate WifiIsUnusableEvent 2415 * <WifiIsUnusableEvent.TriggerType>, <last_score>, <tx_success_delta>, <tx_retries_delta>, 2416 * <tx_bad_delta>, <rx_success_delta>, <packet_update_time_delta>, <firmware_alert_code>, 2417 * <last_wifi_usability_score> 2418 */ 2419 private int[][] mTestUnusableEvents = { 2420 {WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX, 60, 60, 50, 40, 30, 1000, -1, 51}, 2421 {WifiIsUnusableEvent.TYPE_DATA_STALL_TX_WITHOUT_RX, 55, 40, 30, 0, 0, 500, -1, 52}, 2422 {WifiIsUnusableEvent.TYPE_DATA_STALL_BOTH, 60, 90, 30, 30, 0, 1000, -1, 53}, 2423 {WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT, 55, 55, 30, 15, 10, 1000, 4, 54}, 2424 {WifiIsUnusableEvent.TYPE_IP_REACHABILITY_LOST, 50, 56, 28, 17, 12, 1000, -1, 45} 2425 }; 2426 2427 /** 2428 * Generate all WifiIsUnusableEvents from mTestUnusableEvents 2429 */ generateAllUnusableEvents(WifiMetrics wifiMetrics)2430 private void generateAllUnusableEvents(WifiMetrics wifiMetrics) { 2431 for (int i = 0; i < mTestUnusableEvents.length; i++) { 2432 generateUnusableEventAtGivenTime(i, i * (WifiMetrics.MIN_DATA_STALL_WAIT_MS + 1000)); 2433 } 2434 } 2435 2436 /** 2437 * Generate a WifiIsUnusableEvent at the given timestamp with data from 2438 * mTestUnusableEvents[index] 2439 */ generateUnusableEventAtGivenTime(int index, long eventTime)2440 private void generateUnusableEventAtGivenTime(int index, long eventTime) { 2441 when(mClock.getElapsedSinceBootMillis()).thenReturn(eventTime); 2442 int[] trigger = mTestUnusableEvents[index]; 2443 mWifiMetrics.incrementWifiScoreCount(trigger[1]); 2444 mWifiMetrics.incrementWifiUsabilityScoreCount(1, trigger[8], 15); 2445 mWifiMetrics.updateWifiIsUnusableLinkLayerStats(trigger[2], trigger[3], trigger[4], 2446 trigger[5], trigger[6]); 2447 mWifiMetrics.setScreenState(true); 2448 switch(trigger[0]) { 2449 case WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX: 2450 case WifiIsUnusableEvent.TYPE_DATA_STALL_TX_WITHOUT_RX: 2451 case WifiIsUnusableEvent.TYPE_DATA_STALL_BOTH: 2452 mWifiMetrics.logWifiIsUnusableEvent(trigger[0]); 2453 break; 2454 case WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT: 2455 mWifiMetrics.logWifiIsUnusableEvent(trigger[0], trigger[7]); 2456 break; 2457 case WifiIsUnusableEvent.TYPE_IP_REACHABILITY_LOST: 2458 mWifiMetrics.logWifiIsUnusableEvent(trigger[0]); 2459 break; 2460 default: 2461 break; 2462 } 2463 } 2464 2465 /** 2466 * Verify that WifiIsUnusableEvent in wifiLog matches mTestUnusableEvents 2467 */ verifyDeserializedUnusableEvents(WifiMetricsProto.WifiLog wifiLog)2468 private void verifyDeserializedUnusableEvents(WifiMetricsProto.WifiLog wifiLog) { 2469 assertEquals(NUM_UNUSABLE_EVENT, wifiLog.wifiIsUnusableEventList.length); 2470 for (int i = 0; i < mTestUnusableEvents.length; i++) { 2471 WifiIsUnusableEvent event = wifiLog.wifiIsUnusableEventList[i]; 2472 verifyUnusableEvent(event, i); 2473 } 2474 } 2475 2476 /** 2477 * Verify that the given WifiIsUnusableEvent matches mTestUnusableEvents 2478 * at given index 2479 */ verifyUnusableEvent(WifiIsUnusableEvent event, int index)2480 private void verifyUnusableEvent(WifiIsUnusableEvent event, int index) { 2481 int[] expectedValues = mTestUnusableEvents[index]; 2482 assertEquals(expectedValues[0], event.type); 2483 assertEquals(expectedValues[1], event.lastScore); 2484 assertEquals(expectedValues[2], event.txSuccessDelta); 2485 assertEquals(expectedValues[3], event.txRetriesDelta); 2486 assertEquals(expectedValues[4], event.txBadDelta); 2487 assertEquals(expectedValues[5], event.rxSuccessDelta); 2488 assertEquals(expectedValues[6], event.packetUpdateTimeDelta); 2489 assertEquals(expectedValues[7], event.firmwareAlertCode); 2490 assertEquals(expectedValues[8], event.lastWifiUsabilityScore); 2491 assertEquals(true, event.screenOn); 2492 } 2493 2494 /** 2495 * Verify that no WifiIsUnusableEvent is generated when it is disabled in the settings 2496 */ 2497 @Test testNoUnusableEventLogWhenDisabled()2498 public void testNoUnusableEventLogWhenDisabled() throws Exception { 2499 when(mFacade.getIntegerSetting(eq(mContext), 2500 eq(Settings.Global.WIFI_IS_UNUSABLE_EVENT_METRICS_ENABLED), 2501 anyInt())).thenReturn(0); 2502 mWifiMetrics.loadSettings(); 2503 generateAllUnusableEvents(mWifiMetrics); 2504 dumpProtoAndDeserialize(); 2505 assertEquals(0, mDecodedProto.wifiIsUnusableEventList.length); 2506 } 2507 2508 /** 2509 * Generate WifiIsUnusableEvent and verify that they are logged correctly 2510 */ 2511 @Test testUnusableEventLogSerializeDeserialize()2512 public void testUnusableEventLogSerializeDeserialize() throws Exception { 2513 when(mFacade.getIntegerSetting(eq(mContext), 2514 eq(Settings.Global.WIFI_IS_UNUSABLE_EVENT_METRICS_ENABLED), 2515 anyInt())).thenReturn(1); 2516 mWifiMetrics.loadSettings(); 2517 generateAllUnusableEvents(mWifiMetrics); 2518 dumpProtoAndDeserialize(); 2519 verifyDeserializedUnusableEvents(mDecodedProto); 2520 } 2521 2522 /** 2523 * Verify that the number of WifiIsUnusableEvents does not exceed MAX_UNUSABLE_EVENTS 2524 */ 2525 @Test testUnusableEventBounding()2526 public void testUnusableEventBounding() throws Exception { 2527 when(mFacade.getIntegerSetting(eq(mContext), 2528 eq(Settings.Global.WIFI_IS_UNUSABLE_EVENT_METRICS_ENABLED), 2529 anyInt())).thenReturn(1); 2530 mWifiMetrics.loadSettings(); 2531 for (int i = 0; i < (WifiMetrics.MAX_UNUSABLE_EVENTS + 2); i++) { 2532 generateAllUnusableEvents(mWifiMetrics); 2533 } 2534 dumpProtoAndDeserialize(); 2535 assertEquals(WifiMetrics.MAX_UNUSABLE_EVENTS, mDecodedProto.wifiIsUnusableEventList.length); 2536 } 2537 2538 /** 2539 * Verify that we don't generate new WifiIsUnusableEvent from data stalls 2540 * until MIN_DATA_STALL_WAIT_MS has passed since the last data stall WifiIsUnusableEvent 2541 */ 2542 @Test testUnusableEventTimeThrottleForDataStall()2543 public void testUnusableEventTimeThrottleForDataStall() throws Exception { 2544 when(mFacade.getIntegerSetting(eq(mContext), 2545 eq(Settings.Global.WIFI_IS_UNUSABLE_EVENT_METRICS_ENABLED), 2546 anyInt())).thenReturn(1); 2547 mWifiMetrics.loadSettings(); 2548 generateUnusableEventAtGivenTime(0, 0); 2549 // should be time throttled 2550 generateUnusableEventAtGivenTime(1, 1); 2551 generateUnusableEventAtGivenTime(2, WifiMetrics.MIN_DATA_STALL_WAIT_MS + 1000); 2552 // no time throttle for firmware alert 2553 generateUnusableEventAtGivenTime(3, WifiMetrics.MIN_DATA_STALL_WAIT_MS + 1001); 2554 dumpProtoAndDeserialize(); 2555 assertEquals(NUM_UNUSABLE_EVENT_TIME_THROTTLE, 2556 mDecodedProto.wifiIsUnusableEventList.length); 2557 verifyUnusableEvent(mDecodedProto.wifiIsUnusableEventList[0], 0); 2558 verifyUnusableEvent(mDecodedProto.wifiIsUnusableEventList[1], 2); 2559 verifyUnusableEvent(mDecodedProto.wifiIsUnusableEventList[2], 3); 2560 } 2561 2562 /** 2563 * Verify that LinkSpeedCounts is correctly logged in metrics 2564 */ 2565 @Test testLinkSpeedCounts()2566 public void testLinkSpeedCounts() throws Exception { 2567 when(mFacade.getIntegerSetting(eq(mContext), 2568 eq(Settings.Global.WIFI_LINK_SPEED_METRICS_ENABLED), anyInt())).thenReturn(1); 2569 mWifiMetrics.loadSettings(); 2570 for (int i = 0; i < NUM_LINK_SPEED_LEVELS_TO_INCREMENT; i++) { 2571 for (int j = 0; j <= i; j++) { 2572 mWifiMetrics.incrementLinkSpeedCount( 2573 WifiMetrics.MIN_LINK_SPEED_MBPS + i, TEST_RSSI_LEVEL); 2574 } 2575 } 2576 dumpProtoAndDeserialize(); 2577 assertEquals(NUM_LINK_SPEED_LEVELS_TO_INCREMENT, mDecodedProto.linkSpeedCounts.length); 2578 for (int i = 0; i < NUM_LINK_SPEED_LEVELS_TO_INCREMENT; i++) { 2579 assertEquals("Incorrect link speed", WifiMetrics.MIN_LINK_SPEED_MBPS + i, 2580 mDecodedProto.linkSpeedCounts[i].linkSpeedMbps); 2581 assertEquals("Incorrect count of link speed", 2582 i + 1, mDecodedProto.linkSpeedCounts[i].count); 2583 assertEquals("Incorrect sum of absolute values of rssi values", 2584 Math.abs(TEST_RSSI_LEVEL) * (i + 1), 2585 mDecodedProto.linkSpeedCounts[i].rssiSumDbm); 2586 assertEquals("Incorrect sum of squares of rssi values", 2587 TEST_RSSI_LEVEL * TEST_RSSI_LEVEL * (i + 1), 2588 mDecodedProto.linkSpeedCounts[i].rssiSumOfSquaresDbmSq); 2589 } 2590 } 2591 2592 /** 2593 * Verify that Tx and Rx per-band LinkSpeedCounts are correctly logged in metrics 2594 */ 2595 @Test testTxRxLinkSpeedBandCounts()2596 public void testTxRxLinkSpeedBandCounts() throws Exception { 2597 when(mFacade.getIntegerSetting(eq(mContext), 2598 eq(Settings.Global.WIFI_LINK_SPEED_METRICS_ENABLED), anyInt())).thenReturn(1); 2599 mWifiMetrics.loadSettings(); 2600 for (int i = 0; i < NUM_LINK_SPEED_LEVELS_TO_INCREMENT; i++) { 2601 for (int j = 0; j <= i; j++) { 2602 mWifiMetrics.incrementTxLinkSpeedBandCount( 2603 WifiMetrics.MIN_LINK_SPEED_MBPS + i, RSSI_POLL_FREQUENCY); 2604 mWifiMetrics.incrementRxLinkSpeedBandCount( 2605 WifiMetrics.MIN_LINK_SPEED_MBPS + i + 1, RSSI_POLL_FREQUENCY); 2606 } 2607 } 2608 dumpProtoAndDeserialize(); 2609 assertEquals(0, mDecodedProto.txLinkSpeedCount2G.length); 2610 assertEquals(0, mDecodedProto.rxLinkSpeedCount2G.length); 2611 assertEquals(NUM_LINK_SPEED_LEVELS_TO_INCREMENT, 2612 mDecodedProto.txLinkSpeedCount5GLow.length); 2613 assertEquals(NUM_LINK_SPEED_LEVELS_TO_INCREMENT, 2614 mDecodedProto.rxLinkSpeedCount5GLow.length); 2615 assertEquals(0, mDecodedProto.txLinkSpeedCount5GMid.length); 2616 assertEquals(0, mDecodedProto.rxLinkSpeedCount5GMid.length); 2617 assertEquals(0, mDecodedProto.txLinkSpeedCount5GHigh.length); 2618 assertEquals(0, mDecodedProto.rxLinkSpeedCount5GHigh.length); 2619 for (int i = 0; i < NUM_LINK_SPEED_LEVELS_TO_INCREMENT; i++) { 2620 assertEquals("Incorrect Tx link speed", WifiMetrics.MIN_LINK_SPEED_MBPS + i, 2621 mDecodedProto.txLinkSpeedCount5GLow[i].key); 2622 assertEquals("Incorrect Rx link speed", WifiMetrics.MIN_LINK_SPEED_MBPS + i + 1, 2623 mDecodedProto.rxLinkSpeedCount5GLow[i].key); 2624 assertEquals("Incorrect count of Tx link speed", 2625 i + 1, mDecodedProto.txLinkSpeedCount5GLow[i].count); 2626 assertEquals("Incorrect count of Rx link speed", 2627 i + 1, mDecodedProto.rxLinkSpeedCount5GLow[i].count); 2628 } 2629 } 2630 2631 /** 2632 * Verify that LinkSpeedCounts is not logged when disabled in settings 2633 */ 2634 @Test testNoLinkSpeedCountsWhenDisabled()2635 public void testNoLinkSpeedCountsWhenDisabled() throws Exception { 2636 when(mFacade.getIntegerSetting(eq(mContext), 2637 eq(Settings.Global.WIFI_LINK_SPEED_METRICS_ENABLED), anyInt())).thenReturn(0); 2638 mWifiMetrics.loadSettings(); 2639 for (int i = 0; i < NUM_LINK_SPEED_LEVELS_TO_INCREMENT; i++) { 2640 for (int j = 0; j <= i; j++) { 2641 mWifiMetrics.incrementLinkSpeedCount( 2642 WifiMetrics.MIN_LINK_SPEED_MBPS + i, TEST_RSSI_LEVEL); 2643 mWifiMetrics.incrementTxLinkSpeedBandCount( 2644 WifiMetrics.MIN_LINK_SPEED_MBPS - i, RSSI_POLL_FREQUENCY); 2645 mWifiMetrics.incrementRxLinkSpeedBandCount( 2646 WifiMetrics.MIN_LINK_SPEED_MBPS - i, RSSI_POLL_FREQUENCY); 2647 } 2648 } 2649 dumpProtoAndDeserialize(); 2650 assertEquals("LinkSpeedCounts should not be logged when disabled in settings", 2651 0, mDecodedProto.linkSpeedCounts.length); 2652 assertEquals("Tx LinkSpeedCounts should not be logged when disabled in settings", 2653 0, mDecodedProto.txLinkSpeedCount5GLow.length); 2654 assertEquals("Rx LinkSpeedCounts should not be logged when disabled in settings", 2655 0, mDecodedProto.rxLinkSpeedCount5GLow.length); 2656 } 2657 2658 /** 2659 * Verify that LinkSpeedCounts is not logged when the link speed value is lower than 2660 * MIN_LINK_SPEED_MBPS or when the rssi value is outside of 2661 * [MIN_RSSI_LEVEL, MAX_RSSI_LEVEL] 2662 */ 2663 @Test testNoLinkSpeedCountsForOutOfBoundValues()2664 public void testNoLinkSpeedCountsForOutOfBoundValues() throws Exception { 2665 when(mFacade.getIntegerSetting(eq(mContext), 2666 eq(Settings.Global.WIFI_LINK_SPEED_METRICS_ENABLED), anyInt())).thenReturn(1); 2667 mWifiMetrics.loadSettings(); 2668 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 2669 mWifiMetrics.incrementLinkSpeedCount( 2670 WifiMetrics.MIN_LINK_SPEED_MBPS - i, MIN_RSSI_LEVEL); 2671 mWifiMetrics.incrementTxLinkSpeedBandCount( 2672 WifiMetrics.MIN_LINK_SPEED_MBPS - i, RSSI_POLL_FREQUENCY); 2673 mWifiMetrics.incrementRxLinkSpeedBandCount( 2674 WifiMetrics.MIN_LINK_SPEED_MBPS - i, RSSI_POLL_FREQUENCY); 2675 } 2676 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 2677 mWifiMetrics.incrementLinkSpeedCount( 2678 WifiMetrics.MIN_LINK_SPEED_MBPS, MIN_RSSI_LEVEL - i); 2679 } 2680 for (int i = 1; i < NUM_OUT_OF_BOUND_ENTRIES; i++) { 2681 mWifiMetrics.incrementLinkSpeedCount( 2682 WifiMetrics.MIN_LINK_SPEED_MBPS, MAX_RSSI_LEVEL + i); 2683 } 2684 dumpProtoAndDeserialize(); 2685 assertEquals("LinkSpeedCounts should not be logged for out of bound values", 2686 0, mDecodedProto.linkSpeedCounts.length); 2687 assertEquals("Tx LinkSpeedCounts should not be logged for out of bound values", 2688 0, mDecodedProto.txLinkSpeedCount5GLow.length); 2689 assertEquals("Rx LinkSpeedCounts should not be logged for out of bound values", 2690 0, mDecodedProto.rxLinkSpeedCount5GLow.length); 2691 } 2692 nextRandInt()2693 private int nextRandInt() { 2694 return mRandom.nextInt(1000); 2695 } 2696 nextRandomStats(WifiLinkLayerStats current)2697 private WifiLinkLayerStats nextRandomStats(WifiLinkLayerStats current) { 2698 WifiLinkLayerStats out = new WifiLinkLayerStats(); 2699 out.timeStampInMs = current.timeStampInMs + nextRandInt(); 2700 2701 out.rxmpdu_be = current.rxmpdu_be + nextRandInt(); 2702 out.txmpdu_be = current.txmpdu_be + nextRandInt(); 2703 out.lostmpdu_be = current.lostmpdu_be + nextRandInt(); 2704 out.retries_be = current.retries_be + nextRandInt(); 2705 2706 out.rxmpdu_bk = current.rxmpdu_bk + nextRandInt(); 2707 out.txmpdu_bk = current.txmpdu_bk + nextRandInt(); 2708 out.lostmpdu_bk = current.lostmpdu_bk + nextRandInt(); 2709 out.retries_bk = current.retries_bk + nextRandInt(); 2710 2711 out.rxmpdu_vi = current.rxmpdu_vi + nextRandInt(); 2712 out.txmpdu_vi = current.txmpdu_vi + nextRandInt(); 2713 out.lostmpdu_vi = current.lostmpdu_vi + nextRandInt(); 2714 out.retries_vi = current.retries_vi + nextRandInt(); 2715 2716 out.rxmpdu_vo = current.rxmpdu_vo + nextRandInt(); 2717 out.txmpdu_vo = current.txmpdu_vo + nextRandInt(); 2718 out.lostmpdu_vo = current.lostmpdu_vo + nextRandInt(); 2719 out.retries_vo = current.retries_vo + nextRandInt(); 2720 2721 out.on_time = current.on_time + nextRandInt(); 2722 out.tx_time = current.tx_time + nextRandInt(); 2723 out.rx_time = current.rx_time + nextRandInt(); 2724 out.on_time_scan = current.on_time_scan + nextRandInt(); 2725 out.on_time_nan_scan = current.on_time_nan_scan + nextRandInt(); 2726 out.on_time_background_scan = current.on_time_background_scan + nextRandInt(); 2727 out.on_time_roam_scan = current.on_time_roam_scan + nextRandInt(); 2728 out.on_time_pno_scan = current.on_time_pno_scan + nextRandInt(); 2729 out.on_time_hs20_scan = current.on_time_hs20_scan + nextRandInt(); 2730 return out; 2731 } 2732 assertWifiLinkLayerUsageHasDiff(WifiLinkLayerStats oldStats, WifiLinkLayerStats newStats)2733 private void assertWifiLinkLayerUsageHasDiff(WifiLinkLayerStats oldStats, 2734 WifiLinkLayerStats newStats) { 2735 assertEquals(newStats.timeStampInMs - oldStats.timeStampInMs, 2736 mDecodedProto.wifiLinkLayerUsageStats.loggingDurationMs); 2737 assertEquals(newStats.on_time - oldStats.on_time, 2738 mDecodedProto.wifiLinkLayerUsageStats.radioOnTimeMs); 2739 assertEquals(newStats.tx_time - oldStats.tx_time, 2740 mDecodedProto.wifiLinkLayerUsageStats.radioTxTimeMs); 2741 assertEquals(newStats.rx_time - oldStats.rx_time, 2742 mDecodedProto.wifiLinkLayerUsageStats.radioRxTimeMs); 2743 assertEquals(newStats.on_time_scan - oldStats.on_time_scan, 2744 mDecodedProto.wifiLinkLayerUsageStats.radioScanTimeMs); 2745 assertEquals(newStats.on_time_nan_scan - oldStats.on_time_nan_scan, 2746 mDecodedProto.wifiLinkLayerUsageStats.radioNanScanTimeMs); 2747 assertEquals(newStats.on_time_background_scan - oldStats.on_time_background_scan, 2748 mDecodedProto.wifiLinkLayerUsageStats.radioBackgroundScanTimeMs); 2749 assertEquals(newStats.on_time_roam_scan - oldStats.on_time_roam_scan, 2750 mDecodedProto.wifiLinkLayerUsageStats.radioRoamScanTimeMs); 2751 assertEquals(newStats.on_time_pno_scan - oldStats.on_time_pno_scan, 2752 mDecodedProto.wifiLinkLayerUsageStats.radioPnoScanTimeMs); 2753 assertEquals(newStats.on_time_hs20_scan - oldStats.on_time_hs20_scan, 2754 mDecodedProto.wifiLinkLayerUsageStats.radioHs20ScanTimeMs); 2755 2756 } 2757 2758 /** 2759 * Verify that WifiMetrics is counting link layer usage correctly when given a series of 2760 * valid input. 2761 * @throws Exception 2762 */ 2763 @Test testWifiLinkLayerUsageStats()2764 public void testWifiLinkLayerUsageStats() throws Exception { 2765 WifiLinkLayerStats stat1 = nextRandomStats(new WifiLinkLayerStats()); 2766 WifiLinkLayerStats stat2 = nextRandomStats(stat1); 2767 WifiLinkLayerStats stat3 = nextRandomStats(stat2); 2768 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat1); 2769 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat2); 2770 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat3); 2771 dumpProtoAndDeserialize(); 2772 2773 // After 2 increments, the counters should have difference between |stat1| and |stat3| 2774 assertWifiLinkLayerUsageHasDiff(stat1, stat3); 2775 } 2776 2777 /** 2778 * Verify that null input is handled and wifi link layer usage stats are not incremented. 2779 * @throws Exception 2780 */ 2781 @Test testWifiLinkLayerUsageStatsNullInput()2782 public void testWifiLinkLayerUsageStatsNullInput() throws Exception { 2783 WifiLinkLayerStats stat1 = nextRandomStats(new WifiLinkLayerStats()); 2784 WifiLinkLayerStats stat2 = null; 2785 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat1); 2786 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat2); 2787 dumpProtoAndDeserialize(); 2788 2789 // Counter should be zero 2790 assertWifiLinkLayerUsageHasDiff(stat1, stat1); 2791 } 2792 2793 /** 2794 * Verify that when the new data appears to be bad link layer usage stats are not being 2795 * incremented and the buffered WifiLinkLayerStats get cleared. 2796 * @throws Exception 2797 */ 2798 @Test testWifiLinkLayerUsageStatsChipReset()2799 public void testWifiLinkLayerUsageStatsChipReset() throws Exception { 2800 WifiLinkLayerStats stat1 = nextRandomStats(new WifiLinkLayerStats()); 2801 WifiLinkLayerStats stat2 = nextRandomStats(stat1); 2802 stat2.on_time = stat1.on_time - 1; 2803 WifiLinkLayerStats stat3 = nextRandomStats(stat2); 2804 WifiLinkLayerStats stat4 = nextRandomStats(stat3); 2805 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat1); 2806 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat2); 2807 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat3); 2808 mWifiMetrics.incrementWifiLinkLayerUsageStats(stat4); 2809 dumpProtoAndDeserialize(); 2810 2811 // Should only count the difference between |stat3| and |stat4| 2812 assertWifiLinkLayerUsageHasDiff(stat3, stat4); 2813 } 2814 assertUsabilityStatsAssignment(WifiInfo info, WifiLinkLayerStats stats, WifiUsabilityStatsEntry usabilityStats)2815 private void assertUsabilityStatsAssignment(WifiInfo info, WifiLinkLayerStats stats, 2816 WifiUsabilityStatsEntry usabilityStats) { 2817 assertEquals(info.getRssi(), usabilityStats.rssi); 2818 assertEquals(info.getLinkSpeed(), usabilityStats.linkSpeedMbps); 2819 assertEquals(info.getRxLinkSpeedMbps(), usabilityStats.rxLinkSpeedMbps); 2820 assertEquals(stats.timeStampInMs, usabilityStats.timeStampMs); 2821 assertEquals(stats.txmpdu_be + stats.txmpdu_bk + stats.txmpdu_vi + stats.txmpdu_vo, 2822 usabilityStats.totalTxSuccess); 2823 assertEquals(stats.retries_be + stats.retries_bk + stats.retries_vi + stats.retries_vo, 2824 usabilityStats.totalTxRetries); 2825 assertEquals(stats.lostmpdu_be + stats.lostmpdu_bk + stats.lostmpdu_vi + stats.lostmpdu_vo, 2826 usabilityStats.totalTxBad); 2827 assertEquals(stats.rxmpdu_be + stats.rxmpdu_bk + stats.rxmpdu_vi + stats.rxmpdu_vo, 2828 usabilityStats.totalRxSuccess); 2829 assertEquals(stats.on_time, usabilityStats.totalRadioOnTimeMs); 2830 assertEquals(stats.tx_time, usabilityStats.totalRadioTxTimeMs); 2831 assertEquals(stats.rx_time, usabilityStats.totalRadioRxTimeMs); 2832 assertEquals(stats.on_time_scan, usabilityStats.totalScanTimeMs); 2833 assertEquals(stats.on_time_nan_scan, usabilityStats.totalNanScanTimeMs); 2834 assertEquals(stats.on_time_background_scan, usabilityStats.totalBackgroundScanTimeMs); 2835 assertEquals(stats.on_time_roam_scan, usabilityStats.totalRoamScanTimeMs); 2836 assertEquals(stats.on_time_pno_scan, usabilityStats.totalPnoScanTimeMs); 2837 assertEquals(stats.on_time_hs20_scan, usabilityStats.totalHotspot2ScanTimeMs); 2838 assertEquals(stats.beacon_rx, usabilityStats.totalBeaconRx); 2839 } 2840 2841 // Simulate adding a LABEL_GOOD WifiUsabilityStats addGoodWifiUsabilityStats(WifiLinkLayerStats start)2842 private WifiLinkLayerStats addGoodWifiUsabilityStats(WifiLinkLayerStats start) { 2843 WifiInfo info = mock(WifiInfo.class); 2844 when(info.getRssi()).thenReturn(nextRandInt()); 2845 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 2846 WifiLinkLayerStats stats = start; 2847 for (int i = 0; i < WifiMetrics.NUM_WIFI_USABILITY_STATS_ENTRIES_PER_WIFI_GOOD; i++) { 2848 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats); 2849 stats = nextRandomStats(stats); 2850 } 2851 return stats; 2852 } 2853 2854 // Simulate adding a LABEL_BAD WifiUsabilityStats addBadWifiUsabilityStats(WifiLinkLayerStats start)2855 private WifiLinkLayerStats addBadWifiUsabilityStats(WifiLinkLayerStats start) { 2856 WifiInfo info = mock(WifiInfo.class); 2857 when(info.getRssi()).thenReturn(nextRandInt()); 2858 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 2859 WifiLinkLayerStats stats1 = start; 2860 WifiLinkLayerStats stats2 = nextRandomStats(stats1); 2861 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats1); 2862 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats2); 2863 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 2864 WifiUsabilityStats.TYPE_DATA_STALL_BAD_TX, -1); 2865 return nextRandomStats(stats2); 2866 } 2867 2868 /** 2869 * Verify that updateWifiUsabilityStatsEntries correctly converts the inputs into 2870 * a WifiUsabilityStatsEntry Object and then stores it. 2871 * 2872 * Verify that the converted metrics proto contains pairs of WifiUsabilityStats with 2873 * LABEL_GOOD and LABEL_BAD 2874 * @throws Exception 2875 */ 2876 @Test testUpdateWifiUsabilityStatsEntries()2877 public void testUpdateWifiUsabilityStatsEntries() throws Exception { 2878 WifiInfo info = mock(WifiInfo.class); 2879 when(info.getRssi()).thenReturn(nextRandInt()); 2880 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 2881 when(info.getRxLinkSpeedMbps()).thenReturn(nextRandInt()); 2882 when(info.getBSSID()).thenReturn("Wifi"); 2883 when(info.getFrequency()).thenReturn(5745); 2884 2885 int signalStrengthDbm = -50; 2886 int signalStrengthDb = -10; 2887 boolean isSameRegisteredCell = true; 2888 CellularLinkLayerStats cellularStats = new CellularLinkLayerStats(); 2889 cellularStats.setIsSameRegisteredCell(isSameRegisteredCell); 2890 cellularStats.setDataNetworkType(TelephonyManager.NETWORK_TYPE_LTE); 2891 cellularStats.setSignalStrengthDbm(signalStrengthDbm); 2892 cellularStats.setSignalStrengthDb(signalStrengthDb); 2893 when(mCellularLinkLayerStatsCollector.update()).thenReturn(cellularStats); 2894 2895 WifiLinkLayerStats stats1 = nextRandomStats(new WifiLinkLayerStats()); 2896 WifiLinkLayerStats stats2 = nextRandomStats(stats1); 2897 mWifiMetrics.incrementWifiScoreCount(60); 2898 mWifiMetrics.incrementWifiUsabilityScoreCount(2, 55, 15); 2899 mWifiMetrics.logLinkProbeSuccess(nextRandInt(), nextRandInt(), nextRandInt(), 12); 2900 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats1); 2901 mWifiMetrics.incrementWifiScoreCount(58); 2902 mWifiMetrics.incrementWifiUsabilityScoreCount(3, 56, 15); 2903 mWifiMetrics.logLinkProbeFailure(nextRandInt(), nextRandInt(), 2904 nextRandInt(), nextRandInt()); 2905 mWifiMetrics.enterDeviceMobilityState(DEVICE_MOBILITY_STATE_HIGH_MVMT); 2906 2907 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats2); 2908 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 2909 WifiUsabilityStats.TYPE_DATA_STALL_BAD_TX, -1); 2910 2911 // Add 2 LABEL_GOOD but only 1 should remain in the converted proto 2912 WifiLinkLayerStats statsGood = addGoodWifiUsabilityStats(nextRandomStats(stats2)); 2913 statsGood.timeStampInMs += WifiMetrics.MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS; 2914 addGoodWifiUsabilityStats(statsGood); 2915 2916 dumpProtoAndDeserialize(); 2917 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 2918 assertEquals(WifiUsabilityStats.LABEL_GOOD, mDecodedProto.wifiUsabilityStatsList[0].label); 2919 assertEquals(WifiUsabilityStats.LABEL_BAD, mDecodedProto.wifiUsabilityStatsList[1].label); 2920 assertUsabilityStatsAssignment(info, stats1, 2921 mDecodedProto.wifiUsabilityStatsList[1].stats[0]); 2922 assertUsabilityStatsAssignment(info, stats2, 2923 mDecodedProto.wifiUsabilityStatsList[1].stats[1]); 2924 2925 assertEquals(2, mDecodedProto.wifiUsabilityStatsList[1].stats[0].seqNumToFramework); 2926 assertEquals(3, mDecodedProto.wifiUsabilityStatsList[1].stats[1].seqNumToFramework); 2927 assertEquals(0, mDecodedProto.wifiUsabilityStatsList[1].stats[0].seqNumInsideFramework); 2928 assertEquals(1, mDecodedProto.wifiUsabilityStatsList[1].stats[1].seqNumInsideFramework); 2929 assertEquals(60, mDecodedProto.wifiUsabilityStatsList[1].stats[0].wifiScore); 2930 assertEquals(58, mDecodedProto.wifiUsabilityStatsList[1].stats[1].wifiScore); 2931 assertEquals(55, mDecodedProto.wifiUsabilityStatsList[1].stats[0].wifiUsabilityScore); 2932 assertEquals(56, mDecodedProto.wifiUsabilityStatsList[1].stats[1].wifiUsabilityScore); 2933 assertEquals(15, mDecodedProto.wifiUsabilityStatsList[1].stats[0].predictionHorizonSec); 2934 assertEquals(true, mDecodedProto.wifiUsabilityStatsList[1].stats[0].isSameBssidAndFreq); 2935 assertEquals(android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_SUCCESS, 2936 mDecodedProto.wifiUsabilityStatsList[1].stats[0].probeStatusSinceLastUpdate); 2937 assertEquals(android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_FAILURE, 2938 mDecodedProto.wifiUsabilityStatsList[1].stats[1].probeStatusSinceLastUpdate); 2939 assertEquals(android.net.wifi.WifiUsabilityStatsEntry.PROBE_STATUS_NO_PROBE, 2940 mDecodedProto.wifiUsabilityStatsList[0].stats[0].probeStatusSinceLastUpdate); 2941 assertEquals(12, 2942 mDecodedProto.wifiUsabilityStatsList[1].stats[0].probeElapsedTimeSinceLastUpdateMs); 2943 assertEquals(Integer.MAX_VALUE, mDecodedProto.wifiUsabilityStatsList[1] 2944 .stats[1].probeElapsedTimeSinceLastUpdateMs); 2945 assertEquals(-1, mDecodedProto.wifiUsabilityStatsList[0] 2946 .stats[0].probeElapsedTimeSinceLastUpdateMs); 2947 assertEquals(WifiUsabilityStatsEntry.NETWORK_TYPE_LTE, 2948 mDecodedProto.wifiUsabilityStatsList[0].stats[0].cellularDataNetworkType); 2949 assertEquals(signalStrengthDbm, 2950 mDecodedProto.wifiUsabilityStatsList[0].stats[0].cellularSignalStrengthDbm); 2951 assertEquals(signalStrengthDb, 2952 mDecodedProto.wifiUsabilityStatsList[0].stats[0].cellularSignalStrengthDb); 2953 assertEquals(isSameRegisteredCell, 2954 mDecodedProto.wifiUsabilityStatsList[0].stats[0].isSameRegisteredCell); 2955 assertEquals(DEVICE_MOBILITY_STATE_HIGH_MVMT, mDecodedProto.wifiUsabilityStatsList[1] 2956 .stats[mDecodedProto.wifiUsabilityStatsList[1].stats.length - 1] 2957 .deviceMobilityState); 2958 } 2959 2960 /** 2961 * Verify that when there are no WifiUsability events the generated proto also contains no 2962 * such information. 2963 * @throws Exception 2964 */ 2965 @Test testWifiUsabilityStatsZeroEvents()2966 public void testWifiUsabilityStatsZeroEvents() throws Exception { 2967 dumpProtoAndDeserialize(); 2968 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 2969 } 2970 2971 /** 2972 * Verify that we discard a WifiUsabilityStats with LABEL_GOOD if there is no corresponding 2973 * LABEL_BAD 2974 * @throws Exception 2975 */ 2976 @Test testWifiUsabilityStatsIgnoreSingleLabelGood()2977 public void testWifiUsabilityStatsIgnoreSingleLabelGood() throws Exception { 2978 addGoodWifiUsabilityStats(new WifiLinkLayerStats()); 2979 dumpProtoAndDeserialize(); 2980 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 2981 } 2982 2983 /** 2984 * Verify that we discard a WifiUsabilityStats with LABEL_BAD if there is no corresponding 2985 * LABEL_GOOD 2986 * @throws Exception 2987 */ 2988 @Test testWifiUsabilityStatsIgnoreSingleLabelBad()2989 public void testWifiUsabilityStatsIgnoreSingleLabelBad() throws Exception { 2990 addBadWifiUsabilityStats(new WifiLinkLayerStats()); 2991 dumpProtoAndDeserialize(); 2992 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 2993 } 2994 2995 /** 2996 * Verify that the buffer for WifiUsabilityStats does not exceed the max length. 2997 * Do this by trying to add more WifiUsabilityStats than the max length and then 2998 * verifying that the decoded proto's length does not exceed the max length. 2999 * 3000 * Also verify that the length for the list of WifiUsabilityStatsEntry is capped. 3001 * @throws Exception 3002 */ 3003 @Test testWifiUsabilityStatsBufferSizeIsCapped()3004 public void testWifiUsabilityStatsBufferSizeIsCapped() throws Exception { 3005 // simulate adding LABEL_GOOD WifiUsabilityStats 1 time over the max limit 3006 WifiLinkLayerStats stats = new WifiLinkLayerStats(); 3007 for (int j = 0; j < WifiMetrics.MAX_WIFI_USABILITY_STATS_LIST_SIZE_PER_TYPE + 1; j++) { 3008 stats = addGoodWifiUsabilityStats(stats); 3009 stats = addBadWifiUsabilityStats(stats); 3010 stats.timeStampInMs += WifiMetrics.MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS; 3011 } 3012 dumpProtoAndDeserialize(); 3013 assertEquals(2 * WifiMetrics.MAX_WIFI_USABILITY_STATS_PER_TYPE_TO_UPLOAD, 3014 mDecodedProto.wifiUsabilityStatsList.length); 3015 for (int i = 0; i < WifiMetrics.MAX_WIFI_USABILITY_STATS_PER_TYPE_TO_UPLOAD; i++) { 3016 assertEquals(WifiMetrics.MAX_WIFI_USABILITY_STATS_ENTRIES_LIST_SIZE, 3017 mDecodedProto.wifiUsabilityStatsList[2 * i].stats.length); 3018 assertEquals(2, mDecodedProto.wifiUsabilityStatsList[2 * i + 1].stats.length); 3019 } 3020 } 3021 3022 /** 3023 * Verify that LABEL_GOOD stats are not generated more frequently than 3024 * |MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS| 3025 * @throws Exception 3026 */ 3027 @Test testWifiUsabilityStatsLabelGoodHasMinimumPeriod()3028 public void testWifiUsabilityStatsLabelGoodHasMinimumPeriod() throws Exception { 3029 // simulate adding LABEL_GOOD WifiUsabilityStats 1 time over the max limit 3030 WifiLinkLayerStats stats = new WifiLinkLayerStats(); 3031 for (int j = 0; j < 2; j++) { 3032 stats = addGoodWifiUsabilityStats(stats); 3033 stats = addBadWifiUsabilityStats(stats); 3034 } 3035 dumpProtoAndDeserialize(); 3036 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 3037 } 3038 3039 /** 3040 * Verify that LABEL_BAD stats are not generated more frequently than |MIN_DATA_STALL_WAIT_MS| 3041 * @throws Exception 3042 */ 3043 @Test testWifiUsabilityStatsLabelBadNotGeneratedGapLessThanMinimum()3044 public void testWifiUsabilityStatsLabelBadNotGeneratedGapLessThanMinimum() throws Exception { 3045 // simulate adding two LABEL_GOOD WifiUsabilityStats 3046 WifiInfo info = mock(WifiInfo.class); 3047 when(info.getRssi()).thenReturn(nextRandInt()); 3048 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3049 WifiLinkLayerStats stats1 = new WifiLinkLayerStats(); 3050 WifiLinkLayerStats stats2 = new WifiLinkLayerStats(); 3051 stats1 = addGoodWifiUsabilityStats(stats1); 3052 stats2.timeStampInMs = stats1.timeStampInMs 3053 + WifiMetrics.MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS; 3054 addGoodWifiUsabilityStats(stats2); 3055 3056 WifiLinkLayerStats stats3 = new WifiLinkLayerStats(); 3057 WifiLinkLayerStats stats4 = new WifiLinkLayerStats(); 3058 for (int i = 0; i < WifiMetrics.MAX_WIFI_USABILITY_STATS_ENTRIES_LIST_SIZE - 1; i++) { 3059 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats3); 3060 stats3 = nextRandomStats(stats3); 3061 } 3062 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats3); 3063 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 3064 WifiUsabilityStats.TYPE_DATA_STALL_BAD_TX, -1); 3065 for (int i = 0; i < WifiMetrics.MAX_WIFI_USABILITY_STATS_ENTRIES_LIST_SIZE - 1; i++) { 3066 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats4); 3067 stats4 = nextRandomStats(stats4); 3068 } 3069 stats4.timeStampInMs = stats3.timeStampInMs - 1 + WifiMetrics.MIN_DATA_STALL_WAIT_MS; 3070 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats4); 3071 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 3072 WifiUsabilityStats.TYPE_DATA_STALL_BAD_TX, -1); 3073 dumpProtoAndDeserialize(); 3074 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 3075 } 3076 3077 /** 3078 * Verify that LABEL_BAD stats are generated if timestamp gap is larger than 3079 * |MIN_DATA_STALL_WAIT_MS| 3080 * @throws Exception 3081 */ 3082 @Test testWifiUsabilityStatsLabelBadGeneratedGapLargerThanMinimum()3083 public void testWifiUsabilityStatsLabelBadGeneratedGapLargerThanMinimum() throws Exception { 3084 // simulate adding two LABEL_GOOD WifiUsabilityStats 3085 WifiInfo info = mock(WifiInfo.class); 3086 when(info.getRssi()).thenReturn(nextRandInt()); 3087 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3088 WifiLinkLayerStats stats1 = new WifiLinkLayerStats(); 3089 WifiLinkLayerStats stats2 = new WifiLinkLayerStats(); 3090 stats1 = addGoodWifiUsabilityStats(stats1); 3091 stats2.timeStampInMs = stats1.timeStampInMs 3092 + WifiMetrics.MIN_WIFI_GOOD_USABILITY_STATS_PERIOD_MS; 3093 addGoodWifiUsabilityStats(stats2); 3094 3095 WifiLinkLayerStats stats3 = new WifiLinkLayerStats(); 3096 WifiLinkLayerStats stats4 = new WifiLinkLayerStats(); 3097 for (int i = 0; i < WifiMetrics.MAX_WIFI_USABILITY_STATS_ENTRIES_LIST_SIZE - 1; i++) { 3098 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats3); 3099 stats3 = nextRandomStats(stats3); 3100 } 3101 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats3); 3102 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 3103 WifiUsabilityStats.TYPE_DATA_STALL_BAD_TX, -1); 3104 for (int i = 0; i < WifiMetrics.MAX_WIFI_USABILITY_STATS_ENTRIES_LIST_SIZE - 1; i++) { 3105 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats4); 3106 stats4 = nextRandomStats(stats4); 3107 } 3108 stats4.timeStampInMs = stats3.timeStampInMs + 1 + WifiMetrics.MIN_DATA_STALL_WAIT_MS; 3109 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats4); 3110 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 3111 WifiUsabilityStats.TYPE_DATA_STALL_BAD_TX, -1); 3112 dumpProtoAndDeserialize(); 3113 assertEquals(4, mDecodedProto.wifiUsabilityStatsList.length); 3114 } 3115 3116 /** 3117 * Tests device mobility state metrics as states are changed. 3118 */ 3119 @Test testDeviceMobilityStateMetrics_changeState()3120 public void testDeviceMobilityStateMetrics_changeState() throws Exception { 3121 // timeMs is initialized to 0 by the setUp() method 3122 long timeMs = 1000; 3123 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3124 mWifiMetrics.enterDeviceMobilityState(DEVICE_MOBILITY_STATE_STATIONARY); 3125 3126 timeMs += 2000; 3127 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3128 mWifiMetrics.enterDeviceMobilityState(DEVICE_MOBILITY_STATE_LOW_MVMT); 3129 3130 dumpProtoAndDeserialize(); 3131 3132 DeviceMobilityStatePnoScanStats[] expected = { 3133 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_UNKNOWN, 1, 1000, 0), 3134 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_STATIONARY, 1, 2000, 0), 3135 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_LOW_MVMT, 1, 0, 0) 3136 }; 3137 3138 assertDeviceMobilityStatePnoScanStatsEqual( 3139 expected, mDecodedProto.mobilityStatePnoStatsList); 3140 } 3141 3142 /** 3143 * Tests device mobility state metrics as PNO scans are started and stopped. 3144 */ 3145 @Test testDeviceMobilityStateMetrics_startStopPnoScans()3146 public void testDeviceMobilityStateMetrics_startStopPnoScans() throws Exception { 3147 long timeMs = 1000; 3148 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3149 mWifiMetrics.logPnoScanStart(); 3150 3151 timeMs += 2000; 3152 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3153 mWifiMetrics.logPnoScanStop(); 3154 mWifiMetrics.enterDeviceMobilityState(DEVICE_MOBILITY_STATE_STATIONARY); 3155 mWifiMetrics.logPnoScanStart(); 3156 3157 timeMs += 4000; 3158 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3159 mWifiMetrics.logPnoScanStop(); 3160 3161 timeMs += 8000; 3162 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3163 mWifiMetrics.enterDeviceMobilityState(DEVICE_MOBILITY_STATE_HIGH_MVMT); 3164 3165 dumpProtoAndDeserialize(); 3166 3167 DeviceMobilityStatePnoScanStats[] expected = { 3168 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_UNKNOWN, 3169 1, 1000 + 2000, 2000), 3170 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_STATIONARY, 3171 1, 4000 + 8000, 4000), 3172 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_HIGH_MVMT, 1, 0, 0) 3173 }; 3174 3175 assertDeviceMobilityStatePnoScanStatsEqual( 3176 expected, mDecodedProto.mobilityStatePnoStatsList); 3177 } 3178 3179 /** 3180 * Tests that the initial state is set up correctly. 3181 */ 3182 @Test testDeviceMobilityStateMetrics_initialState()3183 public void testDeviceMobilityStateMetrics_initialState() throws Exception { 3184 dumpProtoAndDeserialize(); 3185 3186 DeviceMobilityStatePnoScanStats[] expected = { 3187 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_UNKNOWN, 1, 0, 0) 3188 }; 3189 3190 assertDeviceMobilityStatePnoScanStatsEqual( 3191 expected, mDecodedProto.mobilityStatePnoStatsList); 3192 } 3193 3194 /** 3195 * Tests that logPnoScanStart() updates the total duration in addition to the PNO duration. 3196 */ 3197 @Test testDeviceMobilityStateMetrics_startPnoScansUpdatesTotalDuration()3198 public void testDeviceMobilityStateMetrics_startPnoScansUpdatesTotalDuration() 3199 throws Exception { 3200 long timeMs = 1000; 3201 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3202 mWifiMetrics.logPnoScanStart(); 3203 3204 dumpProtoAndDeserialize(); 3205 3206 DeviceMobilityStatePnoScanStats[] expected = { 3207 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_UNKNOWN, 1, 1000, 0) 3208 }; 3209 3210 assertDeviceMobilityStatePnoScanStatsEqual( 3211 expected, mDecodedProto.mobilityStatePnoStatsList); 3212 } 3213 3214 /** 3215 * Tests that logPnoScanStop() updates the total duration in addition to the PNO duration. 3216 */ 3217 @Test testDeviceMobilityStateMetrics_stopPnoScansUpdatesTotalDuration()3218 public void testDeviceMobilityStateMetrics_stopPnoScansUpdatesTotalDuration() 3219 throws Exception { 3220 long timeMs = 1000; 3221 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3222 mWifiMetrics.logPnoScanStart(); 3223 3224 timeMs += 2000; 3225 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 3226 mWifiMetrics.logPnoScanStop(); 3227 3228 dumpProtoAndDeserialize(); 3229 3230 DeviceMobilityStatePnoScanStats[] expected = { 3231 buildDeviceMobilityStatePnoScanStats(DEVICE_MOBILITY_STATE_UNKNOWN, 3232 1, 1000 + 2000, 2000) 3233 }; 3234 3235 assertDeviceMobilityStatePnoScanStatsEqual( 3236 expected, mDecodedProto.mobilityStatePnoStatsList); 3237 } 3238 3239 /** 3240 * Verify that clients should be notified of activity in case Wifi stats get updated. 3241 */ 3242 @Test testClientNotification()3243 public void testClientNotification() throws RemoteException { 3244 // Register Client for verification. 3245 ArgumentCaptor<android.net.wifi.WifiUsabilityStatsEntry> usabilityStats = 3246 ArgumentCaptor.forClass(android.net.wifi.WifiUsabilityStatsEntry.class); 3247 mWifiMetrics.addOnWifiUsabilityListener(mAppBinder, mOnWifiUsabilityStatsListener, 3248 TEST_WIFI_USABILITY_STATS_LISTENER_IDENTIFIER); 3249 WifiInfo info = mock(WifiInfo.class); 3250 when(info.getRssi()).thenReturn(nextRandInt()); 3251 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3252 3253 CellularLinkLayerStats cellularStats = new CellularLinkLayerStats(); 3254 cellularStats.setIsSameRegisteredCell(false); 3255 cellularStats.setDataNetworkType(TelephonyManager.NETWORK_TYPE_UMTS); 3256 cellularStats.setSignalStrengthDbm(-100); 3257 cellularStats.setSignalStrengthDb(-20); 3258 when(mCellularLinkLayerStatsCollector.update()).thenReturn(cellularStats); 3259 3260 WifiLinkLayerStats linkLayerStats = nextRandomStats(new WifiLinkLayerStats()); 3261 mWifiMetrics.updateWifiUsabilityStatsEntries(info, linkLayerStats); 3262 3263 // Client should get the stats. 3264 verify(mOnWifiUsabilityStatsListener).onWifiUsabilityStats(anyInt(), anyBoolean(), 3265 usabilityStats.capture()); 3266 assertEquals(usabilityStats.getValue().getTotalRadioOnTimeMillis(), linkLayerStats.on_time); 3267 assertEquals(usabilityStats.getValue().getTotalTxBad(), linkLayerStats.lostmpdu_be 3268 + linkLayerStats.lostmpdu_bk + linkLayerStats.lostmpdu_vi 3269 + linkLayerStats.lostmpdu_vo); 3270 assertEquals(usabilityStats.getValue().getTimeStampMillis(), linkLayerStats.timeStampInMs); 3271 assertEquals(usabilityStats.getValue().getTotalRoamScanTimeMillis(), 3272 linkLayerStats.on_time_roam_scan); 3273 assertEquals(usabilityStats.getValue().getCellularDataNetworkType(), 3274 TelephonyManager.NETWORK_TYPE_UMTS); 3275 assertEquals(usabilityStats.getValue().getCellularSignalStrengthDbm(), -100); 3276 assertEquals(usabilityStats.getValue().getCellularSignalStrengthDb(), -20); 3277 } 3278 3279 /** 3280 * Verify that remove client should be handled 3281 */ 3282 @Test testRemoveClient()3283 public void testRemoveClient() throws RemoteException { 3284 // Register Client for verification. 3285 mWifiMetrics.addOnWifiUsabilityListener(mAppBinder, mOnWifiUsabilityStatsListener, 3286 TEST_WIFI_USABILITY_STATS_LISTENER_IDENTIFIER); 3287 mWifiMetrics.removeOnWifiUsabilityListener(TEST_WIFI_USABILITY_STATS_LISTENER_IDENTIFIER); 3288 verify(mAppBinder).unlinkToDeath(any(), anyInt()); 3289 3290 WifiInfo info = mock(WifiInfo.class); 3291 when(info.getRssi()).thenReturn(nextRandInt()); 3292 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3293 WifiLinkLayerStats linkLayerStats = nextRandomStats(new WifiLinkLayerStats()); 3294 mWifiMetrics.updateWifiUsabilityStatsEntries(info, linkLayerStats); 3295 3296 verify(mOnWifiUsabilityStatsListener, never()).onWifiUsabilityStats(anyInt(), 3297 anyBoolean(), any()); 3298 } 3299 3300 /** 3301 * Verify that WifiMetrics adds for death notification on adding client. 3302 */ 3303 @Test testAddsForBinderDeathOnAddClient()3304 public void testAddsForBinderDeathOnAddClient() throws Exception { 3305 mWifiMetrics.addOnWifiUsabilityListener(mAppBinder, mOnWifiUsabilityStatsListener, 3306 TEST_WIFI_USABILITY_STATS_LISTENER_IDENTIFIER); 3307 verify(mAppBinder).linkToDeath(any(IBinder.DeathRecipient.class), anyInt()); 3308 } 3309 3310 /** 3311 * Verify that client fails to get message when listener add failed. 3312 */ 3313 @Test testAddsListenerFailureOnLinkToDeath()3314 public void testAddsListenerFailureOnLinkToDeath() throws Exception { 3315 doThrow(new RemoteException()) 3316 .when(mAppBinder).linkToDeath(any(IBinder.DeathRecipient.class), anyInt()); 3317 mWifiMetrics.addOnWifiUsabilityListener(mAppBinder, mOnWifiUsabilityStatsListener, 3318 TEST_WIFI_USABILITY_STATS_LISTENER_IDENTIFIER); 3319 verify(mAppBinder).linkToDeath(any(IBinder.DeathRecipient.class), anyInt()); 3320 3321 WifiInfo info = mock(WifiInfo.class); 3322 when(info.getRssi()).thenReturn(nextRandInt()); 3323 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3324 WifiLinkLayerStats linkLayerStats = nextRandomStats(new WifiLinkLayerStats()); 3325 mWifiMetrics.updateWifiUsabilityStatsEntries(info, linkLayerStats); 3326 3327 // Client should not get any message listener add failed. 3328 verify(mOnWifiUsabilityStatsListener, never()).onWifiUsabilityStats(anyInt(), 3329 anyBoolean(), any()); 3330 } 3331 3332 /** 3333 * Verify that the label and the triggerType of Wifi usability stats are saved correctly 3334 * during firmware alert is triggered. 3335 * @throws Exception 3336 */ 3337 @Test verifyFirmwareAlertUpdatesWifiUsabilityMetrics()3338 public void verifyFirmwareAlertUpdatesWifiUsabilityMetrics() throws Exception { 3339 WifiInfo info = mock(WifiInfo.class); 3340 when(info.getRssi()).thenReturn(nextRandInt()); 3341 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3342 long eventTimeMs = nextRandInt(); 3343 when(mClock.getElapsedSinceBootMillis()).thenReturn(eventTimeMs); 3344 WifiLinkLayerStats stats1 = nextRandomStats(new WifiLinkLayerStats()); 3345 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats1); 3346 3347 // Add 1 LABEL_GOOD 3348 WifiLinkLayerStats statsGood = addGoodWifiUsabilityStats(nextRandomStats(stats1)); 3349 // Firmware alert occurs 3350 mWifiMetrics.logFirmwareAlert(2); 3351 3352 dumpProtoAndDeserialize(); 3353 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 3354 3355 WifiUsabilityStats[] statsList = mDecodedProto.wifiUsabilityStatsList; 3356 assertEquals(WifiUsabilityStats.LABEL_GOOD, statsList[0].label); 3357 assertEquals(WifiUsabilityStats.LABEL_BAD, statsList[1].label); 3358 assertEquals(WifiIsUnusableEvent.TYPE_FIRMWARE_ALERT, statsList[1].triggerType); 3359 assertEquals(eventTimeMs, statsList[1].timeStampMs); 3360 assertEquals(2, statsList[1].firmwareAlertCode); 3361 } 3362 3363 /** 3364 * Verify that the label and the triggerType of Wifi usability stats are saved correctly 3365 * during Wifi data stall is triggered. 3366 * @throws Exception 3367 */ 3368 @Test verifyWifiDataStallUpdatesWifiUsabilityMetrics()3369 public void verifyWifiDataStallUpdatesWifiUsabilityMetrics() throws Exception { 3370 WifiInfo info = mock(WifiInfo.class); 3371 when(info.getRssi()).thenReturn(nextRandInt()); 3372 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3373 long eventTimeMs = nextRandInt(); 3374 when(mClock.getElapsedSinceBootMillis()).thenReturn(eventTimeMs); 3375 WifiLinkLayerStats stats1 = nextRandomStats(new WifiLinkLayerStats()); 3376 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats1); 3377 3378 // Add 1 LABEL_GOOD 3379 WifiLinkLayerStats statsGood = addGoodWifiUsabilityStats(nextRandomStats(stats1)); 3380 // Wifi data stall occurs 3381 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 3382 WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX, -1); 3383 3384 dumpProtoAndDeserialize(); 3385 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 3386 WifiUsabilityStats[] statsList = mDecodedProto.wifiUsabilityStatsList; 3387 assertEquals(WifiUsabilityStats.LABEL_BAD, statsList[1].label); 3388 assertEquals(WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX, statsList[1].triggerType); 3389 assertEquals(-1, statsList[1].firmwareAlertCode); 3390 assertEquals(eventTimeMs, statsList[1].timeStampMs); 3391 } 3392 3393 /** 3394 * Test the generation of 'WifiConfigStoreIODuration' read histograms. 3395 */ 3396 @Test testWifiConfigStoreReadDurationsHistogramGeneration()3397 public void testWifiConfigStoreReadDurationsHistogramGeneration() throws Exception { 3398 mWifiMetrics.noteWifiConfigStoreReadDuration(10); 3399 mWifiMetrics.noteWifiConfigStoreReadDuration(20); 3400 mWifiMetrics.noteWifiConfigStoreReadDuration(100); 3401 mWifiMetrics.noteWifiConfigStoreReadDuration(90); 3402 mWifiMetrics.noteWifiConfigStoreReadDuration(130); 3403 mWifiMetrics.noteWifiConfigStoreReadDuration(250); 3404 mWifiMetrics.noteWifiConfigStoreReadDuration(600); 3405 3406 dumpProtoAndDeserialize(); 3407 3408 assertEquals(5, mDecodedProto.wifiConfigStoreIo.readDurations.length); 3409 assertEquals(0, mDecodedProto.wifiConfigStoreIo.writeDurations.length); 3410 3411 assertEquals(Integer.MIN_VALUE, 3412 mDecodedProto.wifiConfigStoreIo.readDurations[0].rangeStartMs); 3413 assertEquals(50, mDecodedProto.wifiConfigStoreIo.readDurations[0].rangeEndMs); 3414 assertEquals(2, mDecodedProto.wifiConfigStoreIo.readDurations[0].count); 3415 3416 assertEquals(50, mDecodedProto.wifiConfigStoreIo.readDurations[1].rangeStartMs); 3417 assertEquals(100, mDecodedProto.wifiConfigStoreIo.readDurations[1].rangeEndMs); 3418 assertEquals(1, mDecodedProto.wifiConfigStoreIo.readDurations[1].count); 3419 3420 assertEquals(100, mDecodedProto.wifiConfigStoreIo.readDurations[2].rangeStartMs); 3421 assertEquals(150, mDecodedProto.wifiConfigStoreIo.readDurations[2].rangeEndMs); 3422 assertEquals(2, mDecodedProto.wifiConfigStoreIo.readDurations[2].count); 3423 3424 assertEquals(200, mDecodedProto.wifiConfigStoreIo.readDurations[3].rangeStartMs); 3425 assertEquals(300, mDecodedProto.wifiConfigStoreIo.readDurations[3].rangeEndMs); 3426 assertEquals(1, mDecodedProto.wifiConfigStoreIo.readDurations[3].count); 3427 3428 assertEquals(300, mDecodedProto.wifiConfigStoreIo.readDurations[4].rangeStartMs); 3429 assertEquals(Integer.MAX_VALUE, 3430 mDecodedProto.wifiConfigStoreIo.readDurations[4].rangeEndMs); 3431 assertEquals(1, mDecodedProto.wifiConfigStoreIo.readDurations[4].count); 3432 } 3433 3434 /** 3435 * Test the generation of 'WifiConfigStoreIODuration' write histograms. 3436 */ 3437 @Test testWifiConfigStoreWriteDurationsHistogramGeneration()3438 public void testWifiConfigStoreWriteDurationsHistogramGeneration() throws Exception { 3439 mWifiMetrics.noteWifiConfigStoreWriteDuration(10); 3440 mWifiMetrics.noteWifiConfigStoreWriteDuration(40); 3441 mWifiMetrics.noteWifiConfigStoreWriteDuration(60); 3442 mWifiMetrics.noteWifiConfigStoreWriteDuration(90); 3443 mWifiMetrics.noteWifiConfigStoreWriteDuration(534); 3444 mWifiMetrics.noteWifiConfigStoreWriteDuration(345); 3445 3446 dumpProtoAndDeserialize(); 3447 3448 assertEquals(0, mDecodedProto.wifiConfigStoreIo.readDurations.length); 3449 assertEquals(3, mDecodedProto.wifiConfigStoreIo.writeDurations.length); 3450 3451 assertEquals(Integer.MIN_VALUE, 3452 mDecodedProto.wifiConfigStoreIo.writeDurations[0].rangeStartMs); 3453 assertEquals(50, mDecodedProto.wifiConfigStoreIo.writeDurations[0].rangeEndMs); 3454 assertEquals(2, mDecodedProto.wifiConfigStoreIo.writeDurations[0].count); 3455 3456 assertEquals(50, mDecodedProto.wifiConfigStoreIo.writeDurations[1].rangeStartMs); 3457 assertEquals(100, mDecodedProto.wifiConfigStoreIo.writeDurations[1].rangeEndMs); 3458 assertEquals(2, mDecodedProto.wifiConfigStoreIo.writeDurations[1].count); 3459 3460 assertEquals(300, mDecodedProto.wifiConfigStoreIo.writeDurations[2].rangeStartMs); 3461 assertEquals(Integer.MAX_VALUE, 3462 mDecodedProto.wifiConfigStoreIo.writeDurations[2].rangeEndMs); 3463 assertEquals(2, mDecodedProto.wifiConfigStoreIo.writeDurations[2].count); 3464 } 3465 3466 /** 3467 * Test link probe metrics. 3468 */ 3469 @Test testLogLinkProbeMetrics()3470 public void testLogLinkProbeMetrics() throws Exception { 3471 mWifiMetrics.logLinkProbeSuccess(10000, -75, 50, 5); 3472 mWifiMetrics.logLinkProbeFailure(30000, -80, 10, 3473 WifiNative.SEND_MGMT_FRAME_ERROR_NO_ACK); 3474 mWifiMetrics.logLinkProbeSuccess(3000, -71, 160, 12); 3475 mWifiMetrics.logLinkProbeFailure(40000, -80, 6, 3476 WifiNative.SEND_MGMT_FRAME_ERROR_NO_ACK); 3477 mWifiMetrics.logLinkProbeSuccess(5000, -73, 160, 10); 3478 mWifiMetrics.logLinkProbeFailure(2000, -78, 6, 3479 WifiNative.SEND_MGMT_FRAME_ERROR_TIMEOUT); 3480 3481 dumpProtoAndDeserialize(); 3482 3483 StaEvent[] expected = { 3484 buildLinkProbeSuccessStaEvent(5), 3485 buildLinkProbeFailureStaEvent(LinkProbeStats.LINK_PROBE_FAILURE_REASON_NO_ACK), 3486 buildLinkProbeSuccessStaEvent(12), 3487 buildLinkProbeFailureStaEvent(LinkProbeStats.LINK_PROBE_FAILURE_REASON_NO_ACK), 3488 buildLinkProbeSuccessStaEvent(10), 3489 buildLinkProbeFailureStaEvent(LinkProbeStats.LINK_PROBE_FAILURE_REASON_TIMEOUT) 3490 }; 3491 assertLinkProbeStaEventsEqual(expected, mDecodedProto.staEventList); 3492 3493 LinkProbeStats linkProbeStats = mDecodedProto.linkProbeStats; 3494 3495 Int32Count[] expectedSuccessRssiHistogram = { 3496 buildInt32Count(-75, 1), 3497 buildInt32Count(-73, 1), 3498 buildInt32Count(-71, 1), 3499 }; 3500 assertKeyCountsEqual(expectedSuccessRssiHistogram, 3501 linkProbeStats.successRssiCounts); 3502 3503 Int32Count[] expectedFailureRssiHistogram = { 3504 buildInt32Count(-80, 2), 3505 buildInt32Count(-78, 1), 3506 }; 3507 assertKeyCountsEqual(expectedFailureRssiHistogram, 3508 linkProbeStats.failureRssiCounts); 3509 3510 Int32Count[] expectedSuccessLinkSpeedHistogram = { 3511 buildInt32Count(50, 1), 3512 buildInt32Count(160, 2) 3513 }; 3514 assertKeyCountsEqual(expectedSuccessLinkSpeedHistogram, 3515 linkProbeStats.successLinkSpeedCounts); 3516 3517 Int32Count[] expectedFailureLinkSpeedHistogram = { 3518 buildInt32Count(6, 2), 3519 buildInt32Count(10, 1) 3520 }; 3521 assertKeyCountsEqual(expectedFailureLinkSpeedHistogram, 3522 linkProbeStats.failureLinkSpeedCounts); 3523 3524 HistogramBucketInt32[] expectedSuccessTimeSinceLastTxSuccessSecondsHistogram = { 3525 buildHistogramBucketInt32(Integer.MIN_VALUE, 5, 1), 3526 buildHistogramBucketInt32(5, 15, 2) 3527 }; 3528 assertHistogramBucketsEqual(expectedSuccessTimeSinceLastTxSuccessSecondsHistogram, 3529 linkProbeStats.successSecondsSinceLastTxSuccessHistogram); 3530 3531 HistogramBucketInt32[] expectedFailureTimeSinceLastTxSuccessSecondsHistogram = { 3532 buildHistogramBucketInt32(Integer.MIN_VALUE, 5, 1), 3533 buildHistogramBucketInt32(15, 45, 2) 3534 }; 3535 assertHistogramBucketsEqual(expectedFailureTimeSinceLastTxSuccessSecondsHistogram, 3536 linkProbeStats.failureSecondsSinceLastTxSuccessHistogram); 3537 3538 HistogramBucketInt32[] expectedSuccessElapsedTimeMsHistogram = { 3539 buildHistogramBucketInt32(5, 10, 1), 3540 buildHistogramBucketInt32(10, 15, 2), 3541 }; 3542 assertHistogramBucketsEqual(expectedSuccessElapsedTimeMsHistogram, 3543 linkProbeStats.successElapsedTimeMsHistogram); 3544 3545 LinkProbeFailureReasonCount[] expectedFailureReasonCount = { 3546 buildLinkProbeFailureReasonCount( 3547 LinkProbeStats.LINK_PROBE_FAILURE_REASON_NO_ACK, 2), 3548 buildLinkProbeFailureReasonCount( 3549 LinkProbeStats.LINK_PROBE_FAILURE_REASON_TIMEOUT, 1), 3550 }; 3551 assertLinkProbeFailureReasonCountsEqual(expectedFailureReasonCount, 3552 linkProbeStats.failureReasonCounts); 3553 } 3554 3555 /** 3556 * Tests counting the number of link probes triggered per day for each experiment. 3557 */ 3558 @Test testIncrementLinkProbeExperimentProbeCount()3559 public void testIncrementLinkProbeExperimentProbeCount() throws Exception { 3560 String experimentId1 = "screenOnDelay=6000,noTxDelay=3000,delayBetweenProbes=9000," 3561 + "rssiThreshold=-70,linkSpeedThreshold=15,"; 3562 mWifiMetrics.incrementLinkProbeExperimentProbeCount(experimentId1); 3563 3564 String experimentId2 = "screenOnDelay=9000,noTxDelay=12000,delayBetweenProbes=15000," 3565 + "rssiThreshold=-72,linkSpeedThreshold=20,"; 3566 mWifiMetrics.incrementLinkProbeExperimentProbeCount(experimentId2); 3567 mWifiMetrics.incrementLinkProbeExperimentProbeCount(experimentId2); 3568 3569 dumpProtoAndDeserialize(); 3570 3571 ExperimentProbeCounts[] actual = mDecodedProto.linkProbeStats.experimentProbeCounts; 3572 3573 ExperimentProbeCounts[] expected = { 3574 buildExperimentProbeCounts(experimentId1, 1), 3575 buildExperimentProbeCounts(experimentId2, 2) 3576 }; 3577 3578 assertExperimentProbeCountsEqual(expected, actual); 3579 } 3580 3581 /** 3582 * Tests logNetworkSelectionDecision() 3583 */ 3584 @Test testLogNetworkSelectionDecision()3585 public void testLogNetworkSelectionDecision() throws Exception { 3586 mWifiMetrics.logNetworkSelectionDecision(1, 2, true, 6); 3587 mWifiMetrics.logNetworkSelectionDecision(1, 2, false, 1); 3588 mWifiMetrics.logNetworkSelectionDecision(1, 2, true, 6); 3589 mWifiMetrics.logNetworkSelectionDecision(1, 2, true, 2); 3590 mWifiMetrics.logNetworkSelectionDecision(3, 2, false, 15); 3591 mWifiMetrics.logNetworkSelectionDecision(1, 2, false, 6); 3592 mWifiMetrics.logNetworkSelectionDecision(1, 4, true, 2); 3593 3594 dumpProtoAndDeserialize(); 3595 3596 assertEquals(3, mDecodedProto.networkSelectionExperimentDecisionsList.length); 3597 3598 NetworkSelectionExperimentDecisions exp12 = 3599 findUniqueNetworkSelectionExperimentDecisions(1, 2); 3600 Int32Count[] exp12SameExpected = { 3601 buildInt32Count(2, 1), 3602 buildInt32Count(6, 2) 3603 }; 3604 assertKeyCountsEqual(exp12SameExpected, exp12.sameSelectionNumChoicesCounter); 3605 Int32Count[] exp12DiffExpected = { 3606 buildInt32Count(1, 1), 3607 buildInt32Count(6, 1) 3608 }; 3609 assertKeyCountsEqual(exp12DiffExpected, exp12.differentSelectionNumChoicesCounter); 3610 3611 NetworkSelectionExperimentDecisions exp32 = 3612 findUniqueNetworkSelectionExperimentDecisions(3, 2); 3613 Int32Count[] exp32SameExpected = {}; 3614 assertKeyCountsEqual(exp32SameExpected, exp32.sameSelectionNumChoicesCounter); 3615 Int32Count[] exp32DiffExpected = { 3616 buildInt32Count( 3617 WifiMetrics.NetworkSelectionExperimentResults.MAX_CHOICES, 1) 3618 }; 3619 assertKeyCountsEqual(exp32DiffExpected, exp32.differentSelectionNumChoicesCounter); 3620 3621 NetworkSelectionExperimentDecisions exp14 = 3622 findUniqueNetworkSelectionExperimentDecisions(1, 4); 3623 Int32Count[] exp14SameExpected = { 3624 buildInt32Count(2, 1) 3625 }; 3626 assertKeyCountsEqual(exp14SameExpected, exp14.sameSelectionNumChoicesCounter); 3627 Int32Count[] exp14DiffExpected = {}; 3628 assertKeyCountsEqual(exp14DiffExpected, exp14.differentSelectionNumChoicesCounter); 3629 } 3630 3631 /** 3632 * Test the generation of 'WifiNetworkRequestApiLog' message. 3633 */ 3634 @Test testWifiNetworkRequestApiLog()3635 public void testWifiNetworkRequestApiLog() throws Exception { 3636 mWifiMetrics.incrementNetworkRequestApiNumRequest(); 3637 mWifiMetrics.incrementNetworkRequestApiNumRequest(); 3638 mWifiMetrics.incrementNetworkRequestApiNumRequest(); 3639 3640 mWifiMetrics.incrementNetworkRequestApiMatchSizeHistogram(7); 3641 mWifiMetrics.incrementNetworkRequestApiMatchSizeHistogram(0); 3642 mWifiMetrics.incrementNetworkRequestApiMatchSizeHistogram(1); 3643 3644 mWifiMetrics.incrementNetworkRequestApiNumConnectSuccess(); 3645 3646 mWifiMetrics.incrementNetworkRequestApiNumUserApprovalBypass(); 3647 mWifiMetrics.incrementNetworkRequestApiNumUserApprovalBypass(); 3648 3649 mWifiMetrics.incrementNetworkRequestApiNumUserReject(); 3650 3651 mWifiMetrics.incrementNetworkRequestApiNumApps(); 3652 3653 dumpProtoAndDeserialize(); 3654 3655 assertEquals(3, mDecodedProto.wifiNetworkRequestApiLog.numRequest); 3656 assertEquals(1, mDecodedProto.wifiNetworkRequestApiLog.numConnectSuccess); 3657 assertEquals(2, mDecodedProto.wifiNetworkRequestApiLog.numUserApprovalBypass); 3658 assertEquals(1, mDecodedProto.wifiNetworkRequestApiLog.numUserReject); 3659 assertEquals(1, mDecodedProto.wifiNetworkRequestApiLog.numApps); 3660 3661 HistogramBucketInt32[] expectedNetworkMatchSizeHistogram = { 3662 buildHistogramBucketInt32(0, 1, 1), 3663 buildHistogramBucketInt32(1, 5, 1), 3664 buildHistogramBucketInt32(5, 10, 1) 3665 }; 3666 assertHistogramBucketsEqual(expectedNetworkMatchSizeHistogram, 3667 mDecodedProto.wifiNetworkRequestApiLog.networkMatchSizeHistogram); 3668 } 3669 3670 /** 3671 * Test the generation of 'WifiNetworkSuggestionApiLog' message. 3672 */ 3673 @Test testWifiNetworkSuggestionApiLog()3674 public void testWifiNetworkSuggestionApiLog() throws Exception { 3675 mWifiMetrics.incrementNetworkSuggestionApiNumModification(); 3676 mWifiMetrics.incrementNetworkSuggestionApiNumModification(); 3677 mWifiMetrics.incrementNetworkSuggestionApiNumModification(); 3678 mWifiMetrics.incrementNetworkSuggestionApiNumModification(); 3679 3680 mWifiMetrics.incrementNetworkSuggestionApiNumConnectSuccess(); 3681 mWifiMetrics.incrementNetworkSuggestionApiNumConnectSuccess(); 3682 3683 mWifiMetrics.incrementNetworkSuggestionApiNumConnectFailure(); 3684 3685 mWifiMetrics.noteNetworkSuggestionApiListSizeHistogram(new ArrayList<Integer>() {{ 3686 add(5); 3687 add(100); 3688 add(50); 3689 add(120); 3690 }}); 3691 // Second update should overwrite the prevous write. 3692 mWifiMetrics.noteNetworkSuggestionApiListSizeHistogram(new ArrayList<Integer>() {{ 3693 add(7); 3694 add(110); 3695 add(40); 3696 add(60); 3697 }}); 3698 3699 dumpProtoAndDeserialize(); 3700 3701 assertEquals(4, mDecodedProto.wifiNetworkSuggestionApiLog.numModification); 3702 assertEquals(2, mDecodedProto.wifiNetworkSuggestionApiLog.numConnectSuccess); 3703 assertEquals(1, mDecodedProto.wifiNetworkSuggestionApiLog.numConnectFailure); 3704 3705 HistogramBucketInt32[] expectedNetworkListSizeHistogram = { 3706 buildHistogramBucketInt32(5, 20, 1), 3707 buildHistogramBucketInt32(20, 50, 1), 3708 buildHistogramBucketInt32(50, 100, 1), 3709 buildHistogramBucketInt32(100, 500, 1), 3710 }; 3711 assertHistogramBucketsEqual(expectedNetworkListSizeHistogram, 3712 mDecodedProto.wifiNetworkSuggestionApiLog.networkListSizeHistogram); 3713 } 3714 findUniqueNetworkSelectionExperimentDecisions( int experiment1Id, int experiment2Id)3715 private NetworkSelectionExperimentDecisions findUniqueNetworkSelectionExperimentDecisions( 3716 int experiment1Id, int experiment2Id) { 3717 NetworkSelectionExperimentDecisions result = null; 3718 for (NetworkSelectionExperimentDecisions d 3719 : mDecodedProto.networkSelectionExperimentDecisionsList) { 3720 if (d.experiment1Id == experiment1Id && d.experiment2Id == experiment2Id) { 3721 assertNull("duplicate found!", result); 3722 result = d; 3723 } 3724 } 3725 assertNotNull("not found!", result); 3726 return result; 3727 } 3728 3729 /** 3730 * Verify that the label and the triggerType of Wifi usability stats are saved correctly 3731 * during IP reachability lost message is received. 3732 * @throws Exception 3733 */ 3734 @Test verifyIpReachabilityLostUpdatesWifiUsabilityMetrics()3735 public void verifyIpReachabilityLostUpdatesWifiUsabilityMetrics() throws Exception { 3736 WifiInfo info = mock(WifiInfo.class); 3737 when(info.getRssi()).thenReturn(nextRandInt()); 3738 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3739 long eventTimeMs = nextRandInt(); 3740 when(mClock.getElapsedSinceBootMillis()).thenReturn(eventTimeMs); 3741 WifiLinkLayerStats stats1 = nextRandomStats(new WifiLinkLayerStats()); 3742 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats1); 3743 3744 // Add 1 LABEL_GOOD 3745 WifiLinkLayerStats statsGood = addGoodWifiUsabilityStats(nextRandomStats(stats1)); 3746 // IP reachability lost occurs 3747 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 3748 WifiUsabilityStats.TYPE_IP_REACHABILITY_LOST, -1); 3749 3750 dumpProtoAndDeserialize(); 3751 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 3752 WifiUsabilityStats[] statsList = mDecodedProto.wifiUsabilityStatsList; 3753 assertEquals(WifiUsabilityStats.LABEL_BAD, statsList[1].label); 3754 assertEquals(WifiUsabilityStats.TYPE_IP_REACHABILITY_LOST, statsList[1].triggerType); 3755 assertEquals(eventTimeMs, statsList[1].timeStampMs); 3756 } 3757 3758 /** 3759 * Test the WifiLock active session statistics 3760 */ 3761 @Test testWifiLockActiveSession()3762 public void testWifiLockActiveSession() throws Exception { 3763 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 100000); 3764 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 10000); 3765 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 10000000); 3766 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 1000); 3767 3768 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 90000); 3769 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 900000); 3770 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 9000); 3771 mWifiMetrics.addWifiLockActiveSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 20000000); 3772 3773 dumpProtoAndDeserialize(); 3774 3775 assertEquals(10111000, mDecodedProto.wifiLockStats.highPerfActiveTimeMs); 3776 assertEquals(20999000, mDecodedProto.wifiLockStats.lowLatencyActiveTimeMs); 3777 3778 HistogramBucketInt32[] expectedHighPerfHistogram = { 3779 buildHistogramBucketInt32(1, 10, 1), 3780 buildHistogramBucketInt32(10, 60, 1), 3781 buildHistogramBucketInt32(60, 600, 1), 3782 buildHistogramBucketInt32(3600, Integer.MAX_VALUE, 1), 3783 }; 3784 3785 HistogramBucketInt32[] expectedLowLatencyHistogram = { 3786 buildHistogramBucketInt32(1, 10, 1), 3787 buildHistogramBucketInt32(60, 600, 1), 3788 buildHistogramBucketInt32(600, 3600, 1), 3789 buildHistogramBucketInt32(3600, Integer.MAX_VALUE, 1), 3790 }; 3791 3792 assertHistogramBucketsEqual(expectedHighPerfHistogram, 3793 mDecodedProto.wifiLockStats.highPerfActiveSessionDurationSecHistogram); 3794 3795 assertHistogramBucketsEqual(expectedLowLatencyHistogram, 3796 mDecodedProto.wifiLockStats.lowLatencyActiveSessionDurationSecHistogram); 3797 } 3798 3799 /** 3800 * Test the WifiLock acquisition session statistics 3801 */ 3802 @Test testWifiLockAcqSession()3803 public void testWifiLockAcqSession() throws Exception { 3804 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 100000); 3805 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 10000); 3806 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 10000000); 3807 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_HIGH_PERF, 1000); 3808 3809 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 90000); 3810 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 900000); 3811 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 9000); 3812 mWifiMetrics.addWifiLockAcqSession(WifiManager.WIFI_MODE_FULL_LOW_LATENCY, 20000000); 3813 3814 dumpProtoAndDeserialize(); 3815 3816 HistogramBucketInt32[] expectedHighPerfHistogram = { 3817 buildHistogramBucketInt32(1, 10, 1), 3818 buildHistogramBucketInt32(10, 60, 1), 3819 buildHistogramBucketInt32(60, 600, 1), 3820 buildHistogramBucketInt32(3600, Integer.MAX_VALUE, 1), 3821 }; 3822 3823 HistogramBucketInt32[] expectedLowLatencyHistogram = { 3824 buildHistogramBucketInt32(1, 10, 1), 3825 buildHistogramBucketInt32(60, 600, 1), 3826 buildHistogramBucketInt32(600, 3600, 1), 3827 buildHistogramBucketInt32(3600, Integer.MAX_VALUE, 1), 3828 }; 3829 3830 assertHistogramBucketsEqual(expectedHighPerfHistogram, 3831 mDecodedProto.wifiLockStats.highPerfLockAcqDurationSecHistogram); 3832 3833 assertHistogramBucketsEqual(expectedLowLatencyHistogram, 3834 mDecodedProto.wifiLockStats.lowLatencyLockAcqDurationSecHistogram); 3835 } 3836 3837 /** 3838 * Verify that LABEL_GOOD stats are generated if Wifi score breaches low and there 3839 * is no WifiIsUnusableEvent in MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS millis 3840 * @throws Exception 3841 */ 3842 @Test testGoodStatsAreGeneratedByWifiScoreBreachLow()3843 public void testGoodStatsAreGeneratedByWifiScoreBreachLow() throws Exception { 3844 // The elapsed time falls into the interval for adding good stats 3845 createTestForDataCollectionByScoreBreach( 3846 WifiMetrics.MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS + 1, 3847 false, true); 3848 dumpProtoAndDeserialize(); 3849 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 3850 } 3851 3852 /** 3853 * Verify that LABEL_GOOD stats are not generated if Wifi score breaches low and the checking 3854 * time is less than MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS millis 3855 * @throws Exception 3856 */ 3857 @Test testGoodStatsAreNotGeneratedByWifiScoreBreachLow()3858 public void testGoodStatsAreNotGeneratedByWifiScoreBreachLow() throws Exception { 3859 // The elapsed time is shorter than necessary to add good stats 3860 createTestForDataCollectionByScoreBreach( 3861 WifiMetrics.MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS - 1, 3862 false, true); 3863 dumpProtoAndDeserialize(); 3864 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 3865 } 3866 3867 /** 3868 * Verify that LABEL_GOOD stats are not generated if Wifi score breaches low and the checking 3869 * time is greater than VALIDITY_PERIOD_OF_SCORE_BREACH_LOW_MS 3870 * @throws Exception 3871 */ 3872 @Test testGoodStatsAreNotGeneratedIfWifiScoreBreachExpires()3873 public void testGoodStatsAreNotGeneratedIfWifiScoreBreachExpires() throws Exception { 3874 // The Wifi score breaching expires for adding good stats 3875 createTestForDataCollectionByScoreBreach( 3876 WifiMetrics.VALIDITY_PERIOD_OF_SCORE_BREACH_LOW_MS + 1, 3877 false, true); 3878 dumpProtoAndDeserialize(); 3879 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 3880 } 3881 3882 /** 3883 * Verify that LABEL_GOOD stats are not generated if Wifi score breaches low and there is 3884 * WifiIsUnusableEvent occured within MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS millis 3885 * @throws Exception 3886 */ 3887 @Test testGoodStatsAreNotGeneratedIfBadEventOccured()3888 public void testGoodStatsAreNotGeneratedIfBadEventOccured() throws Exception { 3889 // The elapsed time falls into the interval for adding good stats and bad event occurs 3890 createTestForDataCollectionByScoreBreach( 3891 WifiMetrics.MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS + 1, 3892 true, true); 3893 dumpProtoAndDeserialize(); 3894 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 3895 } 3896 3897 /** 3898 * Verify that LABEL_GOOD stats are generated if Wifi usability score breaches low and there 3899 * is no WifiIsUnusableEvent in MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS millis 3900 * @throws Exception 3901 */ 3902 @Test testGoodStatsAreGeneratedByWifiUsabilityScoreBreachLow()3903 public void testGoodStatsAreGeneratedByWifiUsabilityScoreBreachLow() throws Exception { 3904 // The elapsed time falls into the interval for adding good stats 3905 createTestForDataCollectionByScoreBreach( 3906 WifiMetrics.MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS + 1, 3907 false, false); 3908 dumpProtoAndDeserialize(); 3909 assertEquals(2, mDecodedProto.wifiUsabilityStatsList.length); 3910 } 3911 3912 /** 3913 * Verify that LABEL_GOOD stats are not generated if Wifi usability score breaches low and 3914 * the checking time is less than MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS millis 3915 * @throws Exception 3916 */ 3917 @Test testGoodStatsAreNotGeneratedByWifiUsabilityScoreBreachLow()3918 public void testGoodStatsAreNotGeneratedByWifiUsabilityScoreBreachLow() throws Exception { 3919 // The elapsed time is shorter than necessary to add good stats 3920 createTestForDataCollectionByScoreBreach( 3921 WifiMetrics.MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS - 1, 3922 false, false); 3923 dumpProtoAndDeserialize(); 3924 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 3925 } 3926 3927 /** 3928 * Verify that LABEL_GOOD stats are not generated if Wifi usability score breaches low and 3929 * the checking time is greater than VALIDITY_PERIOD_OF_SCORE_BREACH_LOW_MS 3930 * @throws Exception 3931 */ 3932 @Test testGoodStatsAreNotGeneratedIfWifiUsabilityScoreBreachExpires()3933 public void testGoodStatsAreNotGeneratedIfWifiUsabilityScoreBreachExpires() throws Exception { 3934 // The Wifi usability score breaching expires for adding good stats 3935 createTestForDataCollectionByScoreBreach( 3936 WifiMetrics.VALIDITY_PERIOD_OF_SCORE_BREACH_LOW_MS + 1, 3937 false, false); 3938 dumpProtoAndDeserialize(); 3939 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 3940 } 3941 3942 /** 3943 * Verify that LABEL_GOOD stats are not generated if Wifi usability score breaches low and there 3944 * is WifiIsUnusableEvent occured within MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS millis 3945 * @throws Exception 3946 */ 3947 @Test testGoodStatsAreNotGeneratedIfBadEventOccuredForUsabilityScore()3948 public void testGoodStatsAreNotGeneratedIfBadEventOccuredForUsabilityScore() throws Exception { 3949 // The elapsed time falls into the interval for adding good stats and bad event occurs 3950 createTestForDataCollectionByScoreBreach( 3951 WifiMetrics.MIN_SCORE_BREACH_TO_GOOD_STATS_WAIT_TIME_MS + 1, 3952 true, false); 3953 dumpProtoAndDeserialize(); 3954 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 3955 } 3956 3957 /** 3958 * Verify that incrementNumWifiToggles increments the corrects fields based on input. 3959 */ 3960 @Test testIncrementNumWifiToggles()3961 public void testIncrementNumWifiToggles() throws Exception { 3962 mWifiMetrics.incrementNumWifiToggles(true, true); 3963 for (int i = 0; i < 2; i++) { 3964 mWifiMetrics.incrementNumWifiToggles(true, false); 3965 } 3966 for (int i = 0; i < 3; i++) { 3967 mWifiMetrics.incrementNumWifiToggles(false, true); 3968 } 3969 for (int i = 0; i < 4; i++) { 3970 mWifiMetrics.incrementNumWifiToggles(false, false); 3971 } 3972 dumpProtoAndDeserialize(); 3973 assertEquals(1, mDecodedProto.wifiToggleStats.numToggleOnPrivileged); 3974 assertEquals(2, mDecodedProto.wifiToggleStats.numToggleOffPrivileged); 3975 assertEquals(3, mDecodedProto.wifiToggleStats.numToggleOnNormal); 3976 assertEquals(4, mDecodedProto.wifiToggleStats.numToggleOffNormal); 3977 } 3978 3979 3980 /** 3981 * Create a test to verify data collection logic triggered by score breaching low 3982 * @param elapsedTimeAfterBreach The elapsed time after score breaches low 3983 * @param isThereBadEvent Whether there is a bad event happened after score breaches low 3984 * @param isWifiScore Whether it is Wifi score or not that breaches the threshold 3985 */ createTestForDataCollectionByScoreBreach( long elapsedTimeAfterBreach, boolean isThereBadEvent, boolean isWifiScore)3986 private void createTestForDataCollectionByScoreBreach( 3987 long elapsedTimeAfterBreach, boolean isThereBadEvent, boolean isWifiScore) { 3988 WifiInfo info = mock(WifiInfo.class); 3989 when(info.getRssi()).thenReturn(nextRandInt()); 3990 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 3991 WifiLinkLayerStats stats2 = new WifiLinkLayerStats(); 3992 mWifiMetrics.setWifiState(WifiMetricsProto.WifiLog.WIFI_ASSOCIATED); 3993 3994 addOneBadWifiUsabilityStats(info); 3995 if (isWifiScore) { 3996 stats2 = wifiScoreBreachesLow(info, stats2); 3997 } else { 3998 stats2 = wifiUsabilityScoreBreachesLow(info, stats2); 3999 } 4000 if (isThereBadEvent) { 4001 mWifiMetrics.logWifiIsUnusableEvent(WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX, -1); 4002 } 4003 when(mClock.getElapsedSinceBootMillis()).thenReturn(elapsedTimeAfterBreach); 4004 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats2); 4005 } 4006 4007 // Simulate adding one LABEL_BAD WifiUsabilityStats addOneBadWifiUsabilityStats(WifiInfo info)4008 private void addOneBadWifiUsabilityStats(WifiInfo info) { 4009 WifiLinkLayerStats stats1 = new WifiLinkLayerStats(); 4010 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats1); 4011 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 4012 WifiUsabilityStats.TYPE_DATA_STALL_BAD_TX, -1); 4013 } 4014 4015 // Simulate that Wifi score breaches low wifiScoreBreachesLow(WifiInfo info, WifiLinkLayerStats stats2)4016 private WifiLinkLayerStats wifiScoreBreachesLow(WifiInfo info, WifiLinkLayerStats stats2) { 4017 int upper = WifiMetrics.LOW_WIFI_SCORE + 7; 4018 int lower = WifiMetrics.LOW_WIFI_SCORE - 8; 4019 mWifiMetrics.incrementWifiScoreCount(upper); 4020 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats2); 4021 stats2 = nextRandomStats(stats2); 4022 long timeMs = 0; 4023 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 4024 // Wifi score breaches low 4025 mWifiMetrics.incrementWifiScoreCount(lower); 4026 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats2); 4027 stats2 = nextRandomStats(stats2); 4028 return stats2; 4029 } 4030 4031 // Simulate that Wifi usability score breaches low wifiUsabilityScoreBreachesLow(WifiInfo info, WifiLinkLayerStats stats2)4032 private WifiLinkLayerStats wifiUsabilityScoreBreachesLow(WifiInfo info, 4033 WifiLinkLayerStats stats2) { 4034 int upper = WifiMetrics.LOW_WIFI_USABILITY_SCORE + 7; 4035 int lower = WifiMetrics.LOW_WIFI_USABILITY_SCORE - 8; 4036 mWifiMetrics.incrementWifiUsabilityScoreCount(1, upper, 30); 4037 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats2); 4038 stats2 = nextRandomStats(stats2); 4039 long timeMs = 0; 4040 when(mClock.getElapsedSinceBootMillis()).thenReturn(timeMs); 4041 // Wifi usability score breaches low 4042 mWifiMetrics.incrementWifiUsabilityScoreCount(2, lower, 30); 4043 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats2); 4044 stats2 = nextRandomStats(stats2); 4045 return stats2; 4046 } 4047 4048 /** 4049 * Verify the counts of passpoint profile type are correct. 4050 * @param profileTypes type and count of installed passpoint profiles 4051 */ assertPasspointProfileTypeCount(PasspointProfileTypeCount[] profileTypes)4052 private void assertPasspointProfileTypeCount(PasspointProfileTypeCount[] profileTypes) { 4053 for (PasspointProfileTypeCount passpointProfileType : profileTypes) { 4054 switch(passpointProfileType.eapMethodType) { 4055 case PasspointProfileTypeCount.TYPE_EAP_AKA: 4056 assertEquals(NUM_EAP_AKA_TYPE, passpointProfileType.count); 4057 break; 4058 case PasspointProfileTypeCount.TYPE_EAP_AKA_PRIME: 4059 assertEquals(NUM_EAP_AKA_PRIME_TYPE, passpointProfileType.count); 4060 break; 4061 case PasspointProfileTypeCount.TYPE_EAP_SIM: 4062 assertEquals(NUM_EAP_SIM_TYPE, passpointProfileType.count); 4063 break; 4064 case PasspointProfileTypeCount.TYPE_EAP_TLS: 4065 assertEquals(NUM_EAP_TLS_TYPE, passpointProfileType.count); 4066 break; 4067 case PasspointProfileTypeCount.TYPE_EAP_TTLS: 4068 assertEquals(NUM_EAP_TTLS_TYPE, passpointProfileType.count); 4069 break; 4070 default: 4071 fail("unknown type counted"); 4072 } 4073 } 4074 } 4075 4076 /** 4077 * Verify that the LABEL_BAD Wifi usability stats are not saved if screen state is off. 4078 * @throws Exception 4079 */ 4080 @Test verifyLabelBadStatsAreNotSavedIfScreenIsOff()4081 public void verifyLabelBadStatsAreNotSavedIfScreenIsOff() throws Exception { 4082 mWifiMetrics.setScreenState(false); 4083 WifiInfo info = mock(WifiInfo.class); 4084 when(info.getRssi()).thenReturn(nextRandInt()); 4085 when(info.getLinkSpeed()).thenReturn(nextRandInt()); 4086 WifiLinkLayerStats stats1 = nextRandomStats(new WifiLinkLayerStats()); 4087 mWifiMetrics.updateWifiUsabilityStatsEntries(info, stats1); 4088 4089 // Add 1 LABEL_GOOD 4090 WifiLinkLayerStats statsGood = addGoodWifiUsabilityStats(nextRandomStats(stats1)); 4091 // IP reachability lost occurs 4092 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 4093 WifiUsabilityStats.TYPE_IP_REACHABILITY_LOST, -1); 4094 // Wifi data stall occurs 4095 mWifiMetrics.addToWifiUsabilityStatsList(WifiUsabilityStats.LABEL_BAD, 4096 WifiIsUnusableEvent.TYPE_DATA_STALL_BAD_TX, -1); 4097 // Firmware alert occurs 4098 mWifiMetrics.logFirmwareAlert(2); 4099 4100 dumpProtoAndDeserialize(); 4101 assertEquals(0, mDecodedProto.wifiUsabilityStatsList.length); 4102 } 4103 } 4104